From 0e91298fd1d16de9bc0c11b9ccf0dcd7e43603a2 Mon Sep 17 00:00:00 2001 From: gingerBill Date: Sun, 8 Jul 2018 11:03:56 +0100 Subject: [PATCH] Rename `free` to `delete` for non pointer types --- core/mem/alloc.odin | 54 ++++++++++++-------- core/os/os.odin | 2 +- core/runtime/core.odin | 43 +++++++--------- core/runtime/internal.odin | 8 +-- examples/demo/demo.odin | 5 +- src/check_expr.cpp | 17 +++++++ src/ir.cpp | 101 ++++++++++++++++++++----------------- src/parser.cpp | 2 +- 8 files changed, 130 insertions(+), 102 deletions(-) diff --git a/core/mem/alloc.odin b/core/mem/alloc.odin index 4e9c4ce11..68789c41a 100644 --- a/core/mem/alloc.odin +++ b/core/mem/alloc.odin @@ -32,7 +32,7 @@ free_ptr_with_allocator :: inline proc(a: Allocator, ptr: rawptr, loc := #caller a.procedure(a.data, Allocator_Mode.Free, 0, 0, ptr, 0, 0, loc); } -free_ptr :: inline proc(ptr: rawptr, loc := #caller_location) do free_ptr_with_allocator(context.allocator, ptr); +free :: inline proc(ptr: rawptr, loc := #caller_location) do free_ptr_with_allocator(context.allocator, ptr); free_all :: inline proc(loc := #caller_location) { a := context.allocator; @@ -46,34 +46,46 @@ resize :: inline proc(ptr: rawptr, old_size, new_size: int, alignment: int = DEF } -free_string :: proc(str: string, loc := #caller_location) { - free_ptr(raw_data(str), loc); +delete_string :: proc(str: string, loc := #caller_location) { + free(raw_data(str), loc); } -free_cstring :: proc(str: cstring, loc := #caller_location) { - free_ptr((^byte)(str), loc); +delete_cstring :: proc(str: cstring, loc := #caller_location) { + free((^byte)(str), loc); } -free_dynamic_array :: proc(array: $T/[dynamic]$E, loc := #caller_location) { - free_ptr(raw_data(array), loc); +delete_dynamic_array :: proc(array: $T/[dynamic]$E, loc := #caller_location) { + free(raw_data(array), loc); } -free_slice :: proc(array: $T/[]$E, loc := #caller_location) { - free_ptr(raw_data(array), loc); +delete_slice :: proc(array: $T/[]$E, loc := #caller_location) { + free(raw_data(array), loc); } -free_map :: proc(m: $T/map[$K]$V, loc := #caller_location) { +delete_map :: proc(m: $T/map[$K]$V, loc := #caller_location) { raw := transmute(Raw_Map)m; - free_dynamic_array(raw.hashes, loc); - free_ptr(raw.entries.data, loc); + delete_dynamic_array(raw.hashes, loc); + free(raw.entries.data, loc); } -free :: proc[ - free_ptr, - free_string, - free_cstring, - free_dynamic_array, - free_slice, - free_map, + +delete :: proc[ + delete_string, + delete_cstring, + delete_dynamic_array, + delete_slice, + delete_map, ]; +new :: inline proc(T: type, loc := #caller_location) -> ^T { + ptr := (^T)(alloc(size_of(T), align_of(T), loc)); + ptr^ = T{}; + return ptr; +} + +new_clone :: inline proc(data: $T, loc := #caller_location) -> ^T { + ptr := (^T)(alloc(size_of(T), align_of(T), loc)); + ptr^ = data; + return ptr; +} + default_resize_align :: proc(old_memory: rawptr, old_size, new_size, alignment: int, loc := #caller_location) -> rawptr { if old_memory == nil do return alloc(new_size, alignment, loc); @@ -182,8 +194,8 @@ pool_init :: proc(pool: ^Pool, pool_destroy :: proc(using pool: ^Pool) { pool_free_all(pool); - free(unused_blocks); - free(used_blocks); + delete(unused_blocks); + delete(used_blocks); zero(pool, size_of(pool^)); } diff --git a/core/os/os.odin b/core/os/os.odin index 0f6e51b46..714f03b8c 100644 --- a/core/os/os.odin +++ b/core/os/os.odin @@ -34,7 +34,7 @@ read_entire_file :: proc(name: string) -> (data: []byte, success: bool) { bytes_read, read_err := read(fd, data); if read_err != 0 { - free(data); + delete(data); return nil, false; } return data[0..bytes_read], true; diff --git a/core/runtime/core.odin b/core/runtime/core.odin index 7546d6648..d1f9994c0 100644 --- a/core/runtime/core.odin +++ b/core/runtime/core.odin @@ -254,10 +254,10 @@ foreign { assume :: proc(cond: bool) ---; @(link_name="llvm.debugtrap") - __debug_trap :: proc() ---; + debug_trap :: proc() ---; @(link_name="llvm.trap") - __trap :: proc() ---; + trap :: proc() ---; @(link_name="llvm.readcyclecounter") read_cycle_counter :: proc() -> u64 ---; @@ -309,32 +309,25 @@ reserve :: proc[reserve_dynamic_array, reserve_map]; @(builtin) -new :: inline proc(T: type, loc := #caller_location) -> ^T { - ptr := (^T)(mem.alloc(size_of(T), align_of(T), loc)); - ptr^ = T{}; - return ptr; -} +new :: proc[mem.new]; @(builtin) -new_clone :: inline proc(data: $T, loc := #caller_location) -> ^T { - ptr := (^T)(mem.alloc(size_of(T), align_of(T), loc)); - ptr^ = data; - return ptr; -} +new_clone :: proc[mem.new_clone]; @(builtin) -free :: proc[ - mem.free_ptr, - mem.free_string, - mem.free_cstring, - mem.free_dynamic_array, - mem.free_slice, - mem.free_map, +free :: proc[mem.free]; + +@(builtin) +delete :: proc[ + mem.delete_string, + mem.delete_cstring, + mem.delete_dynamic_array, + mem.delete_slice, + mem.delete_map, ]; - @(builtin) clear_map :: inline proc "contextless" (m: ^$T/map[$K]$V) { if m == nil do return; @@ -351,8 +344,8 @@ reserve_map :: proc(m: ^$T/map[$K]$V, capacity: int) { } @(builtin) -delete :: proc(m: ^$T/map[$K]$V, key: K) { - if m != nil do __dynamic_map_delete(__get_map_header(m), __get_map_key(key)); +delete_key :: proc(m: ^$T/map[$K]$V, key: K) { + if m != nil do __dynamic_map_delete_key(__get_map_header(m), __get_map_key(key)); } @@ -436,7 +429,7 @@ assert :: proc "contextless" (condition: bool, message := "", using loc := #call os.write_string(fd, message); } os.write_byte(fd, '\n'); - __debug_trap(); + debug_trap(); } return condition; } @@ -451,7 +444,7 @@ panic :: proc "contextless" (message := "", using loc := #caller_location) { os.write_string(fd, message); } os.write_byte(fd, '\n'); - __debug_trap(); + debug_trap(); } @@ -742,7 +735,7 @@ __dynamic_map_add_entry :: proc(using h: Map_Header, key: Map_Key, loc := #calle return prev; } -__dynamic_map_delete :: proc(using h: Map_Header, key: Map_Key) { +__dynamic_map_delete_key :: proc(using h: Map_Header, key: Map_Key) { fr := __dynamic_map_find(h, key); if fr.entry_index >= 0 { __dynamic_map_erase(h, fr); diff --git a/core/runtime/internal.odin b/core/runtime/internal.odin index 7f38bb7ce..9ef0277db 100644 --- a/core/runtime/internal.odin +++ b/core/runtime/internal.odin @@ -259,7 +259,7 @@ bounds_check_error :: proc "contextless" (file: string, line, column: int, index os.write_string(fd, " is out of bounds range 0.."); __print_i64(fd, i64(count)); os.write_byte(fd, '\n'); - __debug_trap(); + debug_trap(); } slice_expr_error :: proc "contextless" (file: string, line, column: int, lo, hi: int, len: int) { @@ -275,7 +275,7 @@ slice_expr_error :: proc "contextless" (file: string, line, column: int, lo, hi: os.write_string(fd, ".."); __print_i64(fd, i64(len)); os.write_byte(fd, '\n'); - __debug_trap(); + debug_trap(); } dynamic_array_expr_error :: proc "contextless" (file: string, line, column: int, low, high, max: int) { @@ -290,7 +290,7 @@ dynamic_array_expr_error :: proc "contextless" (file: string, line, column: int, os.write_string(fd, ".."); __print_i64(fd, i64(max)); os.write_byte(fd, '\n'); - __debug_trap(); + debug_trap(); } type_assertion_check :: proc "contextless" (ok: bool, file: string, line, column: int, from, to: typeid) { @@ -303,7 +303,7 @@ type_assertion_check :: proc "contextless" (ok: bool, file: string, line, column os.write_string(fd, " to "); __print_typeid(fd, to); os.write_byte(fd, '\n'); - __debug_trap(); + debug_trap(); } __string_decode_rune :: inline proc "contextless" (s: string) -> (rune, int) { diff --git a/examples/demo/demo.odin b/examples/demo/demo.odin index 416950d6c..7106b2438 100644 --- a/examples/demo/demo.odin +++ b/examples/demo/demo.odin @@ -378,6 +378,7 @@ parametric_polymorphism :: proc() { context <- c { old_slots := table.slots; + defer delete(old_slots); cap := max(2*len(table.slots), TABLE_SIZE_MIN); allocate(table, cap); @@ -385,8 +386,6 @@ parametric_polymorphism :: proc() { for s in old_slots do if s.occupied { put(table, s.key, s.value); } - - free(old_slots); } } @@ -515,7 +514,7 @@ threading_example :: proc() { } threads := make([dynamic]^thread.Thread, 0, len(prefix_table)); - defer free(threads); + defer delete(threads); for in prefix_table { if t := thread.create(worker_proc); t != nil { diff --git a/src/check_expr.cpp b/src/check_expr.cpp index 6079fa202..8b3e6dfe7 100644 --- a/src/check_expr.cpp +++ b/src/check_expr.cpp @@ -4496,6 +4496,23 @@ CallArgumentData check_call_arguments(CheckerContext *c, Operand *operand, Type Array procs = proc_group_entities(c, *operand); + if (procs.count == 1) { + Ast *ident = operand->expr; + while (ident->kind == Ast_SelectorExpr) { + Ast *s = ident->SelectorExpr.selector; + ident = s; + } + + Entity *e = procs[0]; + + CallArgumentData data = {}; + CallArgumentError err = call_checker(c, call, e->type, e, operands, CallArgumentMode_ShowErrors, &data); + Entity *entity_to_use = data.gen_entity != nullptr ? data.gen_entity : e; + add_entity_use(c, ident, entity_to_use); + + return data; + } + ValidIndexAndScore *valids = gb_alloc_array(heap_allocator(), ValidIndexAndScore, procs.count); isize valid_count = 0; defer (gb_free(heap_allocator(), valids)); diff --git a/src/ir.cpp b/src/ir.cpp index c5cf04ddb..75fd2c592 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -6581,7 +6581,7 @@ void ir_build_range_string(irProcedure *proc, irValue *expr, Type *val_type, } void ir_build_range_interval(irProcedure *proc, AstBinaryExpr *node, Type *val_type, - irValue **val_, irValue **idx_, irBlock **loop_, irBlock **done_) { + irValue **val_, irValue **idx_, irBlock **loop_, irBlock **done_) { // TODO(bill): How should the behaviour work for lower and upper bounds checking for iteration? // If 'lower' is changed, should 'val' do so or is that not typical behaviour? @@ -6638,6 +6638,58 @@ void ir_build_range_interval(irProcedure *proc, AstBinaryExpr *node, Type *val_t if (done_) *done_ = done; } +void ir_build_range_enum(irProcedure *proc, Type *enum_type, Type *val_type, irValue **val_, irValue **idx_, irBlock **loop_, irBlock **done_) { + Type *t = enum_type; + GB_ASSERT(is_type_enum(t)); + Type *enum_ptr = alloc_type_pointer(t); + t = base_type(t); + Type *core_elem = core_type(t); + i64 enum_count = t->Enum.fields.count; + irValue *max_count = ir_const_int(enum_count); + + irValue *ti = ir_type_info(proc, t); + irValue *variant = ir_emit_struct_ep(proc, ti, 2); + irValue *eti_ptr = ir_emit_conv(proc, variant, t_type_info_enum_ptr); + irValue *values = ir_emit_load(proc, ir_emit_struct_ep(proc, eti_ptr, 2)); + irValue *values_data = ir_slice_elem(proc, values); + + irValue *offset_ = ir_add_local_generated(proc, t_int); + ir_emit_store(proc, offset_, v_zero); + + irBlock *loop = ir_new_block(proc, nullptr, "for.enum.loop"); + ir_emit_jump(proc, loop); + ir_start_block(proc, loop); + + irBlock *body = ir_new_block(proc, nullptr, "for.enum.body"); + irBlock *done = ir_new_block(proc, nullptr, "for.enum.done"); + + irValue *offset = ir_emit_load(proc, offset_); + irValue *cond = ir_emit_comp(proc, Token_Lt, offset, max_count); + ir_emit_if(proc, cond, body, done); + ir_start_block(proc, body); + + irValue *val_ptr = ir_emit_ptr_offset(proc, values_data, offset); + ir_emit_increment(proc, offset_); + + irValue *val = nullptr; + if (val_type != nullptr) { + if (is_type_float(core_elem)) { + irValue *f = ir_emit_load(proc, ir_emit_conv(proc, val_ptr, t_f64_ptr)); + val = ir_emit_conv(proc, f, t); + } else if (is_type_integer(core_elem)) { + irValue *i = ir_emit_load(proc, ir_emit_conv(proc, val_ptr, t_i64_ptr)); + val = ir_emit_conv(proc, i, t); + } else { + GB_PANIC("TODO(bill): enum core type %s", type_to_string(core_elem)); + } + } + + if (val_) *val_ = val; + if (idx_) *idx_ = offset; + if (loop_) *loop_ = loop; + if (done_) *done_ = done; +} + void ir_store_type_case_implicit(irProcedure *proc, Ast *clause, irValue *value) { Entity *e = implicit_entity_of_node(clause); GB_ASSERT(e != nullptr); @@ -7003,52 +7055,7 @@ void ir_build_stmt_internal(irProcedure *proc, Ast *node) { if (is_ast_range(expr)) { ir_build_range_interval(proc, &expr->BinaryExpr, val0_type, &val, &key, &loop, &done); } else if (tav.mode == Addressing_Type) { - TokenPos pos = ast_token(expr).pos; - gbAllocator a = ir_allocator(); - Type *t = tav.type; - GB_ASSERT(is_type_enum(t)); - Type *enum_ptr = alloc_type_pointer(t); - t = base_type(t); - Type *core_elem = core_type(t); - i64 enum_count = t->Enum.fields.count; - irValue *max_count = ir_const_int(enum_count); - - irValue *ti = ir_type_info(proc, t); - irValue *variant = ir_emit_struct_ep(proc, ti, 2); - irValue *eti_ptr = ir_emit_conv(proc, variant, t_type_info_enum_ptr); - irValue *values = ir_emit_load(proc, ir_emit_struct_ep(proc, eti_ptr, 2)); - irValue *values_data = ir_slice_elem(proc, values); - - irValue *offset_ = ir_add_local_generated(proc, t_int); - ir_emit_store(proc, offset_, v_zero); - - loop = ir_new_block(proc, nullptr, "for.enum.loop"); - ir_emit_jump(proc, loop); - ir_start_block(proc, loop); - - irBlock *body = ir_new_block(proc, nullptr, "for.enum.body"); - done = ir_new_block(proc, nullptr, "for.enum.done"); - - irValue *offset = ir_emit_load(proc, offset_); - irValue *cond = ir_emit_comp(proc, Token_Lt, offset, max_count); - ir_emit_if(proc, cond, body, done); - ir_start_block(proc, body); - - irValue *val_ptr = ir_emit_ptr_offset(proc, values_data, offset); - ir_emit_increment(proc, offset_); - - key = offset; - if (val0_type != nullptr) { - if (is_type_float(core_elem)) { - irValue *f = ir_emit_load(proc, ir_emit_conv(proc, val_ptr, t_f64_ptr)); - val = ir_emit_conv(proc, f, t); - } else if (is_type_integer(core_elem)) { - irValue *i = ir_emit_load(proc, ir_emit_conv(proc, val_ptr, t_i64_ptr)); - val = ir_emit_conv(proc, i, t); - } else { - GB_PANIC("TODO(bill): enum core type %s", type_to_string(core_elem)); - } - } + ir_build_range_enum(proc, tav.type, val0_type, &val, &key, &loop, &done); } else { Type *expr_type = type_of_expr(rs->expr); Type *et = base_type(type_deref(expr_type)); diff --git a/src/parser.cpp b/src/parser.cpp index 600c35608..39f67b4c4 100644 --- a/src/parser.cpp +++ b/src/parser.cpp @@ -4292,7 +4292,7 @@ bool parse_file(Parser *p, AstFile *f) { CommentGroup *docs = f->lead_comment; f->package_token = expect_token(f, Token_package); - if (f->error_count > 0) { + if (f->package_token.kind != Token_package) { return false; } Token package_name = expect_token_after(f, Token_Ident, "package");