diff options
| author | Niko Matsakis <niko@alum.mit.edu> | 2012-01-11 21:31:36 -0800 |
|---|---|---|
| committer | Niko Matsakis <niko@alum.mit.edu> | 2012-01-12 13:47:38 -0800 |
| commit | e55aa6e5ef60369710d8b2e6f512b2ef84a8c548 (patch) | |
| tree | fdb6e14395d7b7a95903bcfb6fab91a5fbf02d42 | |
| parent | f4a3a3b8780d88e013a8916eea6cc9a8c2c5d890 (diff) | |
| download | rust-e55aa6e5ef60369710d8b2e6f512b2ef84a8c548.tar.gz rust-e55aa6e5ef60369710d8b2e6f512b2ef84a8c548.zip | |
free uniq data we encounter on the sweep, walk thru them otherwise
| -rw-r--r-- | src/comp/middle/shape.rs | 34 | ||||
| -rw-r--r-- | src/rt/rust_cc.cpp | 225 | ||||
| -rw-r--r-- | src/rt/rust_shape.cpp | 116 | ||||
| -rw-r--r-- | src/rt/rust_shape.h | 316 | ||||
| -rw-r--r-- | src/rt/rust_upcall.cpp | 2 | ||||
| -rw-r--r-- | src/test/run-pass/uniq-fn-leak.rs | 2 |
6 files changed, 433 insertions, 262 deletions
diff --git a/src/comp/middle/shape.rs b/src/comp/middle/shape.rs index 51bba4514b4..3f7c6cefca1 100644 --- a/src/comp/middle/shape.rs +++ b/src/comp/middle/shape.rs @@ -46,13 +46,18 @@ const shape_vec: u8 = 11u8; const shape_tag: u8 = 12u8; const shape_box: u8 = 13u8; const shape_struct: u8 = 17u8; -const shape_fn: u8 = 18u8; +const shape_box_fn: u8 = 18u8; const shape_obj: u8 = 19u8; const shape_res: u8 = 20u8; const shape_var: u8 = 21u8; const shape_uniq: u8 = 22u8; const shape_opaque_closure_ptr: u8 = 23u8; // the closure itself. const shape_iface: u8 = 24u8; +const shape_uniq_fn: u8 = 25u8; +const shape_stack_fn: u8 = 26u8; +const shape_bare_fn: u8 = 27u8; +const shape_tydesc: u8 = 28u8; +const shape_send_tydesc: u8 = 29u8; // FIXME: This is a bad API in trans_common. fn C_u8(n: u8) -> ValueRef { ret trans_common::C_u8(n as uint); } @@ -267,6 +272,14 @@ fn s_variant_tag_t(tcx: ty_ctxt) -> u8 { ret s_int(tcx); } +fn s_tydesc(_tcx: ty_ctxt) -> u8 { + ret shape_tydesc; +} + +fn s_send_tydesc(_tcx: ty_ctxt) -> u8 { + ret shape_send_tydesc; +} + fn mk_ctxt(llmod: ModuleRef) -> ctxt { let llshapetablesty = trans_common::T_named_struct("shapes"); let llshapetables = @@ -305,8 +318,10 @@ fn shape_of(ccx: @crate_ctxt, t: ty::t, ty_param_map: [uint], ty::ty_bot. { s += [shape_u8]; } ty::ty_int(ast::ty_i.) { s += [s_int(ccx.tcx)]; } ty::ty_float(ast::ty_f.) { s += [s_float(ccx.tcx)]; } - ty::ty_uint(ast::ty_u.) | ty::ty_ptr(_) | ty::ty_type. | - ty::ty_send_type. | ty::ty_native(_) { s += [s_uint(ccx.tcx)]; } + ty::ty_uint(ast::ty_u.) | ty::ty_ptr(_) | + ty::ty_native(_) { s += [s_uint(ccx.tcx)]; } + ty::ty_type. { s += [s_tydesc(ccx.tcx)]; } + ty::ty_send_type. { s += [s_send_tydesc(ccx.tcx)]; } ty::ty_int(ast::ty_i8.) { s += [shape_i8]; } ty::ty_uint(ast::ty_u16.) { s += [shape_u16]; } ty::ty_int(ast::ty_i16.) { s += [shape_i16]; } @@ -418,8 +433,17 @@ fn shape_of(ccx: @crate_ctxt, t: ty::t, ty_param_map: [uint], } } } - ty::ty_fn(_) { - s += [shape_fn]; + ty::ty_fn({proto: ast::proto_box., _}) { + s += [shape_box_fn]; + } + ty::ty_fn({proto: ast::proto_uniq., _}) { + s += [shape_uniq_fn]; + } + ty::ty_fn({proto: ast::proto_block., _}) { + s += [shape_stack_fn]; + } + ty::ty_fn({proto: ast::proto_bare., _}) { + s += [shape_bare_fn]; } ty::ty_opaque_closure_ptr(_) { s += [shape_opaque_closure_ptr]; diff --git a/src/rt/rust_cc.cpp b/src/rt/rust_cc.cpp index 06a66366f78..1f99fe98f71 100644 --- a/src/rt/rust_cc.cpp +++ b/src/rt/rust_cc.cpp @@ -18,6 +18,9 @@ // collection. #define RUST_CC_FREQUENCY 5000 +// defined in rust_upcall.cpp: +void upcall_s_free_shared_type_desc(type_desc *td); + namespace cc { // Internal reference count computation @@ -70,7 +73,7 @@ class irc : public shape::data<irc,shape::ptr> { in_tables, in_data), ircs(in_ircs) {} - void walk_vec(bool is_pod, uint16_t sp_size) { + void walk_vec2(bool is_pod, uint16_t sp_size) { if (is_pod || shape::get_dp<void *>(dp) == NULL) return; // There can't be any outbound pointers from this. @@ -86,47 +89,63 @@ class irc : public shape::data<irc,shape::ptr> { } } - void walk_tag(shape::tag_info &tinfo, uint32_t tag_variant) { - shape::data<irc,shape::ptr>::walk_variant(tinfo, tag_variant); + void walk_tag2(shape::tag_info &tinfo, uint32_t tag_variant) { + shape::data<irc,shape::ptr>::walk_variant1(tinfo, tag_variant); } - void walk_box() { - shape::data<irc,shape::ptr>::walk_box_contents(); + void walk_box2() { + shape::data<irc,shape::ptr>::walk_box_contents1(); } - void walk_fn() { - // Record an irc for the environment box, but don't descend - // into it since it will be walked via the box's allocation - dp += sizeof(void *); // skip code pointer - uint8_t * box_ptr = shape::bump_dp<uint8_t *>(dp); - shape::ptr ref_count_dp(box_ptr); - maybe_record_irc(ref_count_dp); + void walk_uniq2() { + shape::data<irc,shape::ptr>::walk_uniq_contents1(); + } + + void walk_fn2(char code) { + switch (code) { + case shape::SHAPE_BOX_FN: { + // Record an irc for the environment box, but don't descend + // into it since it will be walked via the box's allocation + shape::bump_dp<void*>(dp); // skip over the code ptr + walk_box2(); // walk over the environment ptr + break; + } + case shape::SHAPE_BARE_FN: // Does not close over data. + case shape::SHAPE_STACK_FN: // Not reachable from heap. + case shape::SHAPE_UNIQ_FN: break; /* Can only close over sendable + * (and hence acyclic) data */ + default: abort(); + } } - void walk_obj() { + void walk_obj2() { dp += sizeof(void *); // skip vtable uint8_t *box_ptr = shape::bump_dp<uint8_t *>(dp); shape::ptr ref_count_dp(box_ptr); maybe_record_irc(ref_count_dp); } - void walk_iface() { - //shape::data<irc,shape::ptr>::walk_iface_contents(dp); - shape::data<irc,shape::ptr>::walk_box_contents(); + void walk_iface2() { + walk_box2(); } - void walk_res(const shape::rust_fn *dtor, unsigned n_params, - const shape::type_param *params, const uint8_t *end_sp, - bool live) { + void walk_tydesc2(char) { + } + + void walk_res2(const shape::rust_fn *dtor, unsigned n_params, + const shape::type_param *params, const uint8_t *end_sp, + bool live) { while (this->sp != end_sp) { this->walk(); align = true; } } - void walk_subcontext(irc &sub) { sub.walk(); } + void walk_subcontext2(irc &sub) { sub.walk(); } - void walk_box_contents(irc &sub, shape::ptr &ref_count_dp) { + void walk_uniq_contents2(irc &sub) { sub.walk(); } + + void walk_box_contents2(irc &sub, shape::ptr &ref_count_dp) { maybe_record_irc(ref_count_dp); // Do not traverse the contents of this box; it's in the allocation @@ -153,28 +172,28 @@ class irc : public shape::data<irc,shape::ptr> { } } - void walk_struct(const uint8_t *end_sp) { + void walk_struct2(const uint8_t *end_sp) { while (this->sp != end_sp) { this->walk(); align = true; } } - void walk_variant(shape::tag_info &tinfo, uint32_t variant_id, + void walk_variant2(shape::tag_info &tinfo, uint32_t variant_id, const std::pair<const uint8_t *,const uint8_t *> variant_ptr_and_end); template<typename T> - inline void walk_number() { /* no-op */ } + inline void walk_number2() { /* no-op */ } public: static void compute_ircs(rust_task *task, irc_map &ircs); }; void -irc::walk_variant(shape::tag_info &tinfo, uint32_t variant_id, - const std::pair<const uint8_t *,const uint8_t *> - variant_ptr_and_end) { +irc::walk_variant2(shape::tag_info &tinfo, uint32_t variant_id, + const std::pair<const uint8_t *,const uint8_t *> + variant_ptr_and_end) { irc sub(*this, variant_ptr_and_end.first, tinfo.params); assert(variant_id < 256); // FIXME: Temporary sanity check. @@ -305,7 +324,7 @@ class mark : public shape::data<mark,shape::ptr> { in_tables, in_data), marked(in_marked) {} - void walk_vec(bool is_pod, uint16_t sp_size) { + void walk_vec2(bool is_pod, uint16_t sp_size) { if (is_pod || shape::get_dp<void *>(dp) == NULL) return; // There can't be any outbound pointers from this. @@ -321,23 +340,39 @@ class mark : public shape::data<mark,shape::ptr> { } } - void walk_tag(shape::tag_info &tinfo, uint32_t tag_variant) { - shape::data<mark,shape::ptr>::walk_variant(tinfo, tag_variant); + void walk_tag2(shape::tag_info &tinfo, uint32_t tag_variant) { + shape::data<mark,shape::ptr>::walk_variant1(tinfo, tag_variant); } - void walk_box() { - shape::data<mark,shape::ptr>::walk_box_contents(); + void walk_box2() { + shape::data<mark,shape::ptr>::walk_box_contents1(); } - void walk_fn() { - shape::data<mark,shape::ptr>::walk_fn_contents(dp); + void walk_uniq2() { + shape::data<mark,shape::ptr>::walk_uniq_contents1(); } - void walk_obj() { - shape::data<mark,shape::ptr>::walk_obj_contents(dp); + void walk_fn2(char code) { + switch (code) { + case shape::SHAPE_BOX_FN: { + // Record an irc for the environment box, but don't descend + // into it since it will be walked via the box's allocation + shape::data<mark,shape::ptr>::walk_fn_contents1(dp); + break; + } + case shape::SHAPE_BARE_FN: // Does not close over data. + case shape::SHAPE_STACK_FN: // Not reachable from heap. + case shape::SHAPE_UNIQ_FN: break; /* Can only close over sendable + * (and hence acyclic) data */ + default: abort(); + } } - void walk_res(const shape::rust_fn *dtor, unsigned n_params, + void walk_obj2() { + shape::data<mark,shape::ptr>::walk_obj_contents1(dp); + } + + void walk_res2(const shape::rust_fn *dtor, unsigned n_params, const shape::type_param *params, const uint8_t *end_sp, bool live) { while (this->sp != end_sp) { @@ -346,9 +381,18 @@ class mark : public shape::data<mark,shape::ptr> { } } - void walk_subcontext(mark &sub) { sub.walk(); } + void walk_iface2() { + walk_box2(); + } + + void walk_tydesc2(char) { + } - void walk_box_contents(mark &sub, shape::ptr &ref_count_dp) { + void walk_subcontext2(mark &sub) { sub.walk(); } + + void walk_uniq_contents2(mark &sub) { sub.walk(); } + + void walk_box_contents2(mark &sub, shape::ptr &ref_count_dp) { if (!ref_count_dp) return; @@ -359,19 +403,19 @@ class mark : public shape::data<mark,shape::ptr> { sub.walk(); } - void walk_struct(const uint8_t *end_sp) { + void walk_struct2(const uint8_t *end_sp) { while (this->sp != end_sp) { this->walk(); align = true; } } - void walk_variant(shape::tag_info &tinfo, uint32_t variant_id, + void walk_variant2(shape::tag_info &tinfo, uint32_t variant_id, const std::pair<const uint8_t *,const uint8_t *> variant_ptr_and_end); template<typename T> - inline void walk_number() { /* no-op */ } + inline void walk_number2() { /* no-op */ } public: static void do_mark(rust_task *task, const std::vector<void *> &roots, @@ -379,7 +423,7 @@ public: }; void -mark::walk_variant(shape::tag_info &tinfo, uint32_t variant_id, +mark::walk_variant2(shape::tag_info &tinfo, uint32_t variant_id, const std::pair<const uint8_t *,const uint8_t *> variant_ptr_and_end) { mark sub(*this, variant_ptr_and_end.first, tinfo.params); @@ -470,13 +514,13 @@ class sweep : public shape::data<sweep,shape::ptr> { : shape::data<sweep,shape::ptr>(in_task, in_align, in_sp, in_params, in_tables, in_data) {} - void walk_vec(bool is_pod, uint16_t sp_size) { + void walk_vec2(bool is_pod, uint16_t sp_size) { void *vec = shape::get_dp<void *>(dp); - walk_vec(is_pod, get_vec_data_range(dp)); + walk_vec2(is_pod, get_vec_data_range(dp)); task->kernel->free(vec); } - void walk_vec(bool is_pod, + void walk_vec2(bool is_pod, const std::pair<shape::ptr,shape::ptr> &data_range) { sweep sub(*this, data_range.first); shape::ptr data_end = sub.end_dp = data_range.second; @@ -486,50 +530,99 @@ class sweep : public shape::data<sweep,shape::ptr> { } } - void walk_tag(shape::tag_info &tinfo, uint32_t tag_variant) { - shape::data<sweep,shape::ptr>::walk_variant(tinfo, tag_variant); - } - - void walk_box() { - shape::data<sweep,shape::ptr>::walk_box_contents(); + void walk_tag2(shape::tag_info &tinfo, uint32_t tag_variant) { + shape::data<sweep,shape::ptr>::walk_variant1(tinfo, tag_variant); + } + + void walk_uniq2() { + void *x = *((void **)dp); + // free contents first: + shape::data<sweep,shape::ptr>::walk_uniq_contents1(); + // now free the ptr: + task->kernel->free(x); + } + + void walk_box2() { + shape::data<sweep,shape::ptr>::walk_box_contents1(); + } + + void walk_fn2(char code) { + switch (code) { + case shape::SHAPE_UNIQ_FN: { + fn_env_pair pair = *(fn_env_pair*)dp; + + // free closed over data: + // + // FIXME--this is a bit sketchy, since there is an + // embedded tydesc that we will be using to walk the + // data, but it will be freed as we walk. In the + // generated code we pull this desc out and free it + // later. We may well want to do the same. However, + // since all we use from the descr. is the "shape", I + // think we're ok. + shape::data<sweep,shape::ptr>::walk_fn_contents1(dp); + + // now free the ptr: + task->kernel->free(pair.env); + break; + } + case shape::SHAPE_BOX_FN: { + // the box will be visited separately: + shape::bump_dp<void*>(dp); // skip over the code ptr + walk_box2(); // walk over the environment ptr + break; + } + case shape::SHAPE_BARE_FN: // Does not close over data. + case shape::SHAPE_STACK_FN: break; // Not reachable from heap. + default: abort(); + } } - void walk_fn() { + void walk_obj2() { return; } - void walk_obj() { - return; + void walk_iface2() { + walk_box2(); } - void walk_iface() { - //shape::data<sweep,shape::ptr>::walk_iface_contents(dp); - shape::data<sweep,shape::ptr>::walk_box_contents(); + void walk_tydesc2(char kind) { + type_desc *td = *(type_desc **)dp; + switch(kind) { + case shape::SHAPE_TYDESC: + break; + case shape::SHAPE_SEND_TYDESC: + upcall_s_free_shared_type_desc(td); + break; + default: abort(); + } } - void walk_res(const shape::rust_fn *dtor, unsigned n_params, - const shape::type_param *params, const uint8_t *end_sp, - bool live) { + void walk_res2(const shape::rust_fn *dtor, unsigned n_params, + const shape::type_param *params, const uint8_t *end_sp, + bool live) { while (this->sp != end_sp) { this->walk(); align = true; } } - void walk_subcontext(sweep &sub) { sub.walk(); } + void walk_subcontext2(sweep &sub) { sub.walk(); } + + void walk_uniq_contents2(sweep &sub) { sub.walk(); } - void walk_box_contents(sweep &sub, shape::ptr &ref_count_dp) { + void walk_box_contents2(sweep &sub, shape::ptr &ref_count_dp) { return; } - void walk_struct(const uint8_t *end_sp) { + void walk_struct2(const uint8_t *end_sp) { while (this->sp != end_sp) { this->walk(); align = true; } } - void walk_variant(shape::tag_info &tinfo, uint32_t variant_id, + void walk_variant2(shape::tag_info &tinfo, uint32_t variant_id, const std::pair<const uint8_t *,const uint8_t *> variant_ptr_and_end) { sweep sub(*this, variant_ptr_and_end.first, tinfo.params); @@ -542,7 +635,7 @@ class sweep : public shape::data<sweep,shape::ptr> { } template<typename T> - inline void walk_number() { /* no-op */ } + inline void walk_number2() { /* no-op */ } public: static void do_sweep(rust_task *task, const std::set<void *> &marked); diff --git a/src/rt/rust_shape.cpp b/src/rt/rust_shape.cpp index ee7e389dc77..b7ab591ce04 100644 --- a/src/rt/rust_shape.cpp +++ b/src/rt/rust_shape.cpp @@ -73,7 +73,7 @@ type_param::from_obj_shape(const uint8_t *sp, ptr dp, arena &arena) { // A shape printer, useful for debugging void -print::walk_tag(tag_info &tinfo) { +print::walk_tag1(tag_info &tinfo) { DPRINT("tag%u", tinfo.tag_id); if (!tinfo.n_params) return; @@ -94,7 +94,7 @@ print::walk_tag(tag_info &tinfo) { } void -print::walk_struct(const uint8_t *end_sp) { +print::walk_struct1(const uint8_t *end_sp) { DPRINT("("); bool first = true; @@ -110,8 +110,8 @@ print::walk_struct(const uint8_t *end_sp) { } void -print::walk_res(const rust_fn *dtor, unsigned n_params, - const type_param *params, const uint8_t *end_sp) { +print::walk_res1(const rust_fn *dtor, unsigned n_params, + const type_param *params, const uint8_t *end_sp) { DPRINT("res@%p", dtor); // Print type parameters. @@ -151,7 +151,7 @@ print::walk_res(const rust_fn *dtor, unsigned n_params, } void -print::walk_var(uint8_t param_index) { +print::walk_var1(uint8_t param_index) { DPRINT("%c=", 'T' + param_index); const type_param *param = ¶ms[param_index]; @@ -160,25 +160,25 @@ print::walk_var(uint8_t param_index) { } template<> -void print::walk_number<uint8_t>() { DPRINT("u8"); } +void print::walk_number1<uint8_t>() { DPRINT("u8"); } template<> -void print::walk_number<uint16_t>() { DPRINT("u16"); } +void print::walk_number1<uint16_t>() { DPRINT("u16"); } template<> -void print::walk_number<uint32_t>() { DPRINT("u32"); } +void print::walk_number1<uint32_t>() { DPRINT("u32"); } template<> -void print::walk_number<uint64_t>() { DPRINT("u64"); } +void print::walk_number1<uint64_t>() { DPRINT("u64"); } template<> -void print::walk_number<int8_t>() { DPRINT("i8"); } +void print::walk_number1<int8_t>() { DPRINT("i8"); } template<> -void print::walk_number<int16_t>() { DPRINT("i16"); } +void print::walk_number1<int16_t>() { DPRINT("i16"); } template<> -void print::walk_number<int32_t>() { DPRINT("i32"); } +void print::walk_number1<int32_t>() { DPRINT("i32"); } template<> -void print::walk_number<int64_t>() { DPRINT("i64"); } +void print::walk_number1<int64_t>() { DPRINT("i64"); } template<> -void print::walk_number<float>() { DPRINT("f32"); } +void print::walk_number1<float>() { DPRINT("f32"); } template<> -void print::walk_number<double>() { DPRINT("f64"); } +void print::walk_number1<double>() { DPRINT("f64"); } void @@ -225,13 +225,13 @@ size_of::compute_tag_size(tag_info &tinfo) { } void -size_of::walk_tag(tag_info &tinfo) { +size_of::walk_tag1(tag_info &tinfo) { compute_tag_size(*this, tinfo); sa = tinfo.tag_sa; } void -size_of::walk_struct(const uint8_t *end_sp) { +size_of::walk_struct1(const uint8_t *end_sp) { size_align struct_sa(0, 1); bool first = true; @@ -264,21 +264,21 @@ class cmp : public data<cmp,ptr_pair> { friend class data<cmp,ptr_pair>; private: - void walk_vec(bool is_pod, - const std::pair<ptr_pair,ptr_pair> &data_range); + void walk_vec2(bool is_pod, + const std::pair<ptr_pair,ptr_pair> &data_range); - inline void walk_subcontext(cmp &sub) { + inline void walk_subcontext2(cmp &sub) { sub.walk(); result = sub.result; } - inline void walk_box_contents(cmp &sub, ptr_pair &ref_count_dp) { + inline void walk_box_contents2(cmp &sub, ptr_pair &ref_count_dp) { sub.align = true; sub.walk(); result = sub.result; } - inline void walk_uniq_contents(cmp &sub) { + inline void walk_uniq_contents2(cmp &sub) { sub.align = true; sub.walk(); result = sub.result; @@ -338,32 +338,36 @@ public: in_dp), result(0) {} - void walk_vec(bool is_pod, uint16_t sp_size) { - walk_vec(is_pod, get_vec_data_range(dp)); + void walk_vec2(bool is_pod, uint16_t sp_size) { + walk_vec2(is_pod, get_vec_data_range(dp)); } - void walk_box() { - data<cmp,ptr_pair>::walk_box_contents(); + void walk_box2() { + data<cmp,ptr_pair>::walk_box_contents1(); } - void walk_uniq() { - data<cmp,ptr_pair>::walk_uniq_contents(); + void walk_uniq2() { + data<cmp,ptr_pair>::walk_uniq_contents1(); } - void walk_fn() { return cmp_two_pointers(); } - void walk_obj() { return cmp_two_pointers(); } + void walk_iface2() { + data<cmp,ptr_pair>::walk_box_contents1(); + } + + void walk_fn2(char) { return cmp_two_pointers(); } + void walk_obj2() { return cmp_two_pointers(); } - void walk_tag(tag_info &tinfo, const data_pair<tag_variant_t> &tag_variants); - void walk_struct(const uint8_t *end_sp); - void walk_res(const rust_fn *dtor, uint16_t n_ty_params, - const type_param *ty_params_sp, const uint8_t *end_sp, - const data_pair<uintptr_t> &live); - void walk_variant(tag_info &tinfo, tag_variant_t variant_id, - const std::pair<const uint8_t *,const uint8_t *> - variant_ptr_and_end); + void walk_tag2(tag_info &tinfo, const data_pair<tag_variant_t> &tag_variants); + void walk_struct2(const uint8_t *end_sp); + void walk_res2(const rust_fn *dtor, uint16_t n_ty_params, + const type_param *ty_params_sp, const uint8_t *end_sp, + const data_pair<uintptr_t> &live); + void walk_variant2(tag_info &tinfo, tag_variant_t variant_id, + const std::pair<const uint8_t *,const uint8_t *> + variant_ptr_and_end); template<typename T> - void walk_number() { cmp_number(get_dp<T>(dp)); } + void walk_number2() { cmp_number(get_dp<T>(dp)); } }; template<> @@ -372,7 +376,7 @@ void cmp::cmp_number<int32_t>(const data_pair<int32_t> &nums) { } void -cmp::walk_vec(bool is_pod, const std::pair<ptr_pair,ptr_pair> &data_range) { +cmp::walk_vec2(bool is_pod, const std::pair<ptr_pair,ptr_pair> &data_range) { cmp sub(*this, data_range.first); ptr_pair data_end = sub.end_dp = data_range.second; while (!result && sub.dp < data_end) { @@ -390,15 +394,15 @@ cmp::walk_vec(bool is_pod, const std::pair<ptr_pair,ptr_pair> &data_range) { } void -cmp::walk_tag(tag_info &tinfo, const data_pair<tag_variant_t> &tag_variants) { +cmp::walk_tag2(tag_info &tinfo, const data_pair<tag_variant_t> &tag_variants) { cmp_number(tag_variants); if (result != 0) return; - data<cmp,ptr_pair>::walk_variant(tinfo, tag_variants.fst); + data<cmp,ptr_pair>::walk_variant1(tinfo, tag_variants.fst); } void -cmp::walk_struct(const uint8_t *end_sp) { +cmp::walk_struct2(const uint8_t *end_sp) { while (!result && this->sp != end_sp) { this->walk(); align = true; @@ -406,16 +410,16 @@ cmp::walk_struct(const uint8_t *end_sp) { } void -cmp::walk_res(const rust_fn *dtor, uint16_t n_ty_params, +cmp::walk_res2(const rust_fn *dtor, uint16_t n_ty_params, const type_param *ty_params_sp, const uint8_t *end_sp, const data_pair<uintptr_t> &live) { abort(); // TODO } void -cmp::walk_variant(tag_info &tinfo, tag_variant_t variant_id, - const std::pair<const uint8_t *,const uint8_t *> - variant_ptr_and_end) { +cmp::walk_variant2(tag_info &tinfo, tag_variant_t variant_id, + const std::pair<const uint8_t *,const uint8_t *> + variant_ptr_and_end) { cmp sub(*this, variant_ptr_and_end.first, tinfo.params); const uint8_t *variant_end = variant_ptr_and_end.second; @@ -430,7 +434,7 @@ cmp::walk_variant(tag_info &tinfo, tag_variant_t variant_id, // Polymorphic logging, for convenience void -log::walk_string(const std::pair<ptr,ptr> &data) { +log::walk_string2(const std::pair<ptr,ptr> &data) { out << prefix << "\"" << std::hex; ptr subdp = data.first; @@ -447,7 +451,7 @@ log::walk_string(const std::pair<ptr,ptr> &data) { } void -log::walk_struct(const uint8_t *end_sp) { +log::walk_struct2(const uint8_t *end_sp) { out << prefix << "("; prefix = ""; @@ -463,10 +467,10 @@ log::walk_struct(const uint8_t *end_sp) { } void -log::walk_vec(bool is_pod, const std::pair<ptr,ptr> &data) { +log::walk_vec2(bool is_pod, const std::pair<ptr,ptr> &data) { if (peek() == SHAPE_U8) { sp++; // It's a string. We handle this ourselves. - walk_string(data); + walk_string2(data); return; } @@ -485,9 +489,9 @@ log::walk_vec(bool is_pod, const std::pair<ptr,ptr> &data) { } void -log::walk_variant(tag_info &tinfo, tag_variant_t variant_id, - const std::pair<const uint8_t *,const uint8_t *> - variant_ptr_and_end) { +log::walk_variant2(tag_info &tinfo, tag_variant_t variant_id, + const std::pair<const uint8_t *,const uint8_t *> + variant_ptr_and_end) { log sub(*this, variant_ptr_and_end.first, tinfo.params); const uint8_t *variant_end = variant_ptr_and_end.second; @@ -503,8 +507,8 @@ log::walk_variant(tag_info &tinfo, tag_variant_t variant_id, } void -log::walk_res(const rust_fn *dtor, unsigned n_params, - const type_param *params, const uint8_t *end_sp, bool live) { +log::walk_res2(const rust_fn *dtor, unsigned n_params, + const type_param *params, const uint8_t *end_sp, bool live) { out << prefix << "res"; if (this->sp == end_sp) diff --git a/src/rt/rust_shape.h b/src/rt/rust_shape.h index 0def948223f..b4efae9e704 100644 --- a/src/rt/rust_shape.h +++ b/src/rt/rust_shape.h @@ -46,12 +46,17 @@ const uint8_t SHAPE_VEC = 11u; const uint8_t SHAPE_TAG = 12u; const uint8_t SHAPE_BOX = 13u; const uint8_t SHAPE_STRUCT = 17u; -const uint8_t SHAPE_FN = 18u; +const uint8_t SHAPE_BOX_FN = 18u; const uint8_t SHAPE_OBJ = 19u; const uint8_t SHAPE_RES = 20u; const uint8_t SHAPE_VAR = 21u; const uint8_t SHAPE_UNIQ = 22u; const uint8_t SHAPE_IFACE = 24u; +const uint8_t SHAPE_UNIQ_FN = 25u; +const uint8_t SHAPE_STACK_FN = 26u; +const uint8_t SHAPE_BARE_FN = 27u; +const uint8_t SHAPE_TYDESC = 28u; +const uint8_t SHAPE_SEND_TYDESC = 29u; #ifdef _LP64 const uint8_t SHAPE_PTR = SHAPE_U64; @@ -247,13 +252,13 @@ protected: inline size_align get_size_align(const uint8_t *&addr); private: - void walk_vec(); - void walk_tag(); - void walk_box(); - void walk_uniq(); - void walk_struct(); - void walk_res(); - void walk_var(); + void walk_vec0(); + void walk_tag0(); + void walk_box0(); + void walk_uniq0(); + void walk_struct0(); + void walk_res0(); + void walk_var0(); }; @@ -357,34 +362,40 @@ public: // Traversals #define WALK_NUMBER(c_type) \ - static_cast<T *>(this)->template walk_number<c_type>() + static_cast<T *>(this)->template walk_number1<c_type>() #define WALK_SIMPLE(method) static_cast<T *>(this)->method() template<typename T> void ctxt<T>::walk() { - switch (*sp++) { - case SHAPE_U8: WALK_NUMBER(uint8_t); break; - case SHAPE_U16: WALK_NUMBER(uint16_t); break; - case SHAPE_U32: WALK_NUMBER(uint32_t); break; - case SHAPE_U64: WALK_NUMBER(uint64_t); break; - case SHAPE_I8: WALK_NUMBER(int8_t); break; - case SHAPE_I16: WALK_NUMBER(int16_t); break; - case SHAPE_I32: WALK_NUMBER(int32_t); break; - case SHAPE_I64: WALK_NUMBER(int64_t); break; - case SHAPE_F32: WALK_NUMBER(float); break; - case SHAPE_F64: WALK_NUMBER(double); break; - case SHAPE_VEC: walk_vec(); break; - case SHAPE_TAG: walk_tag(); break; - case SHAPE_BOX: walk_box(); break; - case SHAPE_STRUCT: walk_struct(); break; - case SHAPE_FN: WALK_SIMPLE(walk_fn); break; - case SHAPE_OBJ: WALK_SIMPLE(walk_obj); break; - case SHAPE_RES: walk_res(); break; - case SHAPE_VAR: walk_var(); break; - case SHAPE_UNIQ: walk_uniq(); break; - case SHAPE_IFACE: WALK_SIMPLE(walk_iface); break; - default: abort(); + char s = *sp++; + switch (s) { + case SHAPE_U8: WALK_NUMBER(uint8_t); break; + case SHAPE_U16: WALK_NUMBER(uint16_t); break; + case SHAPE_U32: WALK_NUMBER(uint32_t); break; + case SHAPE_U64: WALK_NUMBER(uint64_t); break; + case SHAPE_I8: WALK_NUMBER(int8_t); break; + case SHAPE_I16: WALK_NUMBER(int16_t); break; + case SHAPE_I32: WALK_NUMBER(int32_t); break; + case SHAPE_I64: WALK_NUMBER(int64_t); break; + case SHAPE_F32: WALK_NUMBER(float); break; + case SHAPE_F64: WALK_NUMBER(double); break; + case SHAPE_VEC: walk_vec0(); break; + case SHAPE_TAG: walk_tag0(); break; + case SHAPE_BOX: walk_box0(); break; + case SHAPE_STRUCT: walk_struct0(); break; + case SHAPE_OBJ: WALK_SIMPLE(walk_obj1); break; + case SHAPE_RES: walk_res0(); break; + case SHAPE_VAR: walk_var0(); break; + case SHAPE_UNIQ: walk_uniq0(); break; + case SHAPE_IFACE: WALK_SIMPLE(walk_iface1); break; + case SHAPE_BOX_FN: + case SHAPE_UNIQ_FN: + case SHAPE_STACK_FN: + case SHAPE_BARE_FN: static_cast<T*>(this)->walk_fn1(s); break; + case SHAPE_SEND_TYDESC: + case SHAPE_TYDESC: static_cast<T*>(this)->walk_tydesc1(s); break; + default: abort(); } } @@ -420,20 +431,20 @@ ctxt<T>::get_variant_sp(tag_info &tinfo, tag_variant_t variant_id) { template<typename T> void -ctxt<T>::walk_vec() { +ctxt<T>::walk_vec0() { bool is_pod = *sp++; uint16_t sp_size = get_u16_bump(sp); const uint8_t *end_sp = sp + sp_size; - static_cast<T *>(this)->walk_vec(is_pod, sp_size); + static_cast<T *>(this)->walk_vec1(is_pod, sp_size); sp = end_sp; } template<typename T> void -ctxt<T>::walk_tag() { +ctxt<T>::walk_tag0() { tag_info tinfo; tinfo.tag_id = get_u16_bump(sp); @@ -465,45 +476,45 @@ ctxt<T>::walk_tag() { tinfo.params = params; // Call to the implementation. - static_cast<T *>(this)->walk_tag(tinfo); + static_cast<T *>(this)->walk_tag1(tinfo); } template<typename T> void -ctxt<T>::walk_box() { +ctxt<T>::walk_box0() { uint16_t sp_size = get_u16_bump(sp); const uint8_t *end_sp = sp + sp_size; - static_cast<T *>(this)->walk_box(); + static_cast<T *>(this)->walk_box1(); sp = end_sp; } template<typename T> void -ctxt<T>::walk_uniq() { +ctxt<T>::walk_uniq0() { uint16_t sp_size = get_u16_bump(sp); const uint8_t *end_sp = sp + sp_size; - static_cast<T *>(this)->walk_uniq(); + static_cast<T *>(this)->walk_uniq1(); sp = end_sp; } template<typename T> void -ctxt<T>::walk_struct() { +ctxt<T>::walk_struct0() { uint16_t sp_size = get_u16_bump(sp); const uint8_t *end_sp = sp + sp_size; - static_cast<T *>(this)->walk_struct(end_sp); + static_cast<T *>(this)->walk_struct1(end_sp); sp = end_sp; } template<typename T> void -ctxt<T>::walk_res() { +ctxt<T>::walk_res0() { uint16_t dtor_offset = get_u16_bump(sp); const rust_fn **resources = reinterpret_cast<const rust_fn **>(tables->resources); @@ -523,16 +534,16 @@ ctxt<T>::walk_res() { uint16_t sp_size = get_u16_bump(sp); const uint8_t *end_sp = sp + sp_size; - static_cast<T *>(this)->walk_res(dtor, n_ty_params, params, end_sp); + static_cast<T *>(this)->walk_res1(dtor, n_ty_params, params, end_sp); sp = end_sp; } template<typename T> void -ctxt<T>::walk_var() { +ctxt<T>::walk_var0() { uint8_t param = *sp++; - static_cast<T *>(this)->walk_var(param); + static_cast<T *>(this)->walk_var1(param); } // A shape printer, useful for debugging @@ -553,26 +564,44 @@ public: const rust_shape_tables *in_tables) : ctxt<print>(in_task, in_align, in_sp, in_params, in_tables) {} - void walk_tag(tag_info &tinfo); - void walk_struct(const uint8_t *end_sp); - void walk_res(const rust_fn *dtor, unsigned n_params, - const type_param *params, const uint8_t *end_sp); - void walk_var(uint8_t param); + void walk_tag1(tag_info &tinfo); + void walk_struct1(const uint8_t *end_sp); + void walk_res1(const rust_fn *dtor, unsigned n_params, + const type_param *params, const uint8_t *end_sp); + void walk_var1(uint8_t param); - void walk_vec(bool is_pod, uint16_t sp_size) { + void walk_vec1(bool is_pod, uint16_t sp_size) { DPRINT("vec<"); walk(); DPRINT(">"); } - void walk_box() { - DPRINT("box<"); walk(); DPRINT(">"); + void walk_uniq1() { + DPRINT("~<"); walk(); DPRINT(">"); + } + void walk_box1() { + DPRINT("@<"); walk(); DPRINT(">"); } - void walk_fn() { DPRINT("fn"); } - void walk_obj() { DPRINT("obj"); } - void walk_iface() { DPRINT("iface"); } - void walk_closure(); + void walk_fn1(char kind) { + switch(kind) { + case SHAPE_BARE_FN: DPRINT("fn"); break; + case SHAPE_BOX_FN: DPRINT("fn@"); break; + case SHAPE_UNIQ_FN: DPRINT("fn~"); break; + case SHAPE_STACK_FN: DPRINT("fn&"); break; + default: abort(); + } + } + void walk_obj1() { DPRINT("obj"); } + void walk_iface1() { DPRINT("iface"); } + + void walk_tydesc1(char kind) { + switch(kind) { + case SHAPE_TYDESC: DPRINT("tydesc"); break; + case SHAPE_SEND_TYDESC: DPRINT("send-tydesc"); break; + default: abort(); + } + } template<typename T> - void walk_number() {} + void walk_number1() {} template<typename T> static void print_cx(const T *cx) { @@ -608,33 +637,35 @@ public: const rust_shape_tables *in_tables = NULL) : ctxt<size_of>(other, in_sp, in_params, in_tables) {} - void walk_tag(tag_info &tinfo); - void walk_struct(const uint8_t *end_sp); + void walk_tag1(tag_info &tinfo); + void walk_struct1(const uint8_t *end_sp); - void walk_box() { sa.set(sizeof(void *), sizeof(void *)); } - void walk_fn() { sa.set(sizeof(void *)*2, sizeof(void *)); } - void walk_obj() { sa.set(sizeof(void *)*2, sizeof(void *)); } - void walk_iface() { sa.set(sizeof(void *), sizeof(void *)); } - void walk_closure(); + void walk_uniq1() { sa.set(sizeof(void *), sizeof(void *)); } + void walk_box1() { sa.set(sizeof(void *), sizeof(void *)); } + void walk_fn1(char) { sa.set(sizeof(void *)*2, sizeof(void *)); } + void walk_obj1() { sa.set(sizeof(void *)*2, sizeof(void *)); } + void walk_iface1() { sa.set(sizeof(void *), sizeof(void *)); } + void walk_tydesc1(char) { sa.set(sizeof(void *), sizeof(void *)); } + void walk_closure1(); - void walk_vec(bool is_pod, uint16_t sp_size) { + void walk_vec1(bool is_pod, uint16_t sp_size) { sa.set(sizeof(void *), sizeof(void *)); } - void walk_var(uint8_t param_index) { + void walk_var1(uint8_t param_index) { const type_param *param = ¶ms[param_index]; size_of sub(*this, param->shape, param->params, param->tables); sub.walk(); sa = sub.sa; } - void walk_res(const rust_fn *dtor, unsigned n_params, - const type_param *params, const uint8_t *end_sp) { + void walk_res1(const rust_fn *dtor, unsigned n_params, + const type_param *params, const uint8_t *end_sp) { abort(); // TODO } template<typename T> - void walk_number() { sa.set(sizeof(T), alignof<T>()); } + void walk_number1() { sa.set(sizeof(T), alignof<T>()); } void compute_tag_size(tag_info &tinfo); @@ -819,12 +850,12 @@ public: protected: U end_dp; - void walk_box_contents(); - void walk_uniq_contents(); - void walk_fn_contents(ptr &dp); - void walk_obj_contents(ptr &dp); - void walk_iface_contents(ptr &dp); - void walk_variant(tag_info &tinfo, tag_variant_t variant); + void walk_box_contents1(); + void walk_uniq_contents1(); + void walk_fn_contents1(ptr &dp); + void walk_obj_contents1(ptr &dp); + void walk_iface_contents1(ptr &dp); + void walk_variant1(tag_info &tinfo, tag_variant_t variant); static std::pair<uint8_t *,uint8_t *> get_vec_data_range(ptr dp); static std::pair<ptr_pair,ptr_pair> get_vec_data_range(ptr_pair &dp); @@ -840,87 +871,100 @@ public: dp(in_dp), end_dp() {} - void walk_tag(tag_info &tinfo); + void walk_tag1(tag_info &tinfo); - void walk_struct(const uint8_t *end_sp) { - static_cast<T *>(this)->walk_struct(end_sp); + void walk_struct1(const uint8_t *end_sp) { + static_cast<T *>(this)->walk_struct2(end_sp); } - void walk_vec(bool is_pod, uint16_t sp_size) { - DATA_SIMPLE(void *, walk_vec(is_pod, sp_size)); + void walk_vec1(bool is_pod, uint16_t sp_size) { + DATA_SIMPLE(void *, walk_vec2(is_pod, sp_size)); } - void walk_box() { DATA_SIMPLE(void *, walk_box()); } + void walk_box1() { DATA_SIMPLE(void *, walk_box2()); } - void walk_uniq() { DATA_SIMPLE(void *, walk_uniq()); } + void walk_uniq1() { DATA_SIMPLE(void *, walk_uniq2()); } - void walk_fn() { + void walk_fn1(char code) { ALIGN_TO(alignof<void *>()); U next_dp = dp + sizeof(void *) * 2; - static_cast<T *>(this)->walk_fn(); + static_cast<T *>(this)->walk_fn2(code); dp = next_dp; } - void walk_obj() { + void walk_obj1() { ALIGN_TO(alignof<void *>()); U next_dp = dp + sizeof(void *) * 2; - static_cast<T *>(this)->walk_obj(); + static_cast<T *>(this)->walk_obj2(); + dp = next_dp; + } + + void walk_iface1() { + ALIGN_TO(alignof<void *>()); + U next_dp = dp + sizeof(void *); + static_cast<T *>(this)->walk_iface2(); dp = next_dp; } - void walk_iface() { + void walk_tydesc1(char kind) { ALIGN_TO(alignof<void *>()); U next_dp = dp + sizeof(void *); - static_cast<T *>(this)->walk_iface(); + static_cast<T *>(this)->walk_tydesc2(kind); dp = next_dp; } - void walk_res(const rust_fn *dtor, unsigned n_params, - const type_param *params, const uint8_t *end_sp) { + void walk_res1(const rust_fn *dtor, unsigned n_params, + const type_param *params, const uint8_t *end_sp) { typename U::template data<uintptr_t>::t live = bump_dp<uintptr_t>(dp); // Delegate to the implementation. - static_cast<T *>(this)->walk_res(dtor, n_params, params, end_sp, + static_cast<T *>(this)->walk_res2(dtor, n_params, params, end_sp, live); } - void walk_var(uint8_t param_index) { + void walk_var1(uint8_t param_index) { const type_param *param = &this->params[param_index]; T sub(*static_cast<T *>(this), param->shape, param->params, param->tables); - static_cast<T *>(this)->walk_subcontext(sub); + static_cast<T *>(this)->walk_subcontext2(sub); dp = sub.dp; } - template<typename W> - void walk_number() { DATA_SIMPLE(W, walk_number<W>()); } + template<typename WN> + void walk_number1() { + //DATA_SIMPLE(W, walk_number2<W>()); + ALIGN_TO(alignof<WN>()); + U end_dp = dp + sizeof(WN); + T* t = static_cast<T *>(this); + t->template walk_number2<WN>(); + dp = end_dp; + } }; template<typename T,typename U> void -data<T,U>::walk_box_contents() { +data<T,U>::walk_box_contents1() { typename U::template data<uint8_t *>::t box_ptr = bump_dp<uint8_t *>(dp); - U ref_count_dp(box_ptr); T sub(*static_cast<T *>(this), ref_count_dp + sizeof(ref_cnt_t)); - static_cast<T *>(this)->walk_box_contents(sub, ref_count_dp); + static_cast<T *>(this)->walk_box_contents2(sub, ref_count_dp); } template<typename T,typename U> void -data<T,U>::walk_uniq_contents() { +data<T,U>::walk_uniq_contents1() { typename U::template data<uint8_t *>::t box_ptr = bump_dp<uint8_t *>(dp); U data_ptr(box_ptr); T sub(*static_cast<T *>(this), data_ptr); - static_cast<T *>(this)->walk_uniq_contents(sub); + static_cast<T *>(this)->walk_uniq_contents2(sub); } template<typename T,typename U> void -data<T,U>::walk_variant(tag_info &tinfo, tag_variant_t variant_id) { +data<T,U>::walk_variant1(tag_info &tinfo, tag_variant_t variant_id) { std::pair<const uint8_t *,const uint8_t *> variant_ptr_and_end = this->get_variant_sp(tinfo, variant_id); - static_cast<T *>(this)->walk_variant(tinfo, variant_id, - variant_ptr_and_end); + static_cast<T *>(this)->walk_variant2(tinfo, variant_id, + variant_ptr_and_end); } template<typename T,typename U> @@ -943,7 +987,7 @@ data<T,U>::get_vec_data_range(ptr_pair &dp) { template<typename T,typename U> void -data<T,U>::walk_tag(tag_info &tinfo) { +data<T,U>::walk_tag1(tag_info &tinfo) { size_of::compute_tag_size(*this, tinfo); if (tinfo.variant_count > 1) @@ -957,14 +1001,14 @@ data<T,U>::walk_tag(tag_info &tinfo) { else tag_variant = 0; - static_cast<T *>(this)->walk_tag(tinfo, tag_variant); + static_cast<T *>(this)->walk_tag2(tinfo, tag_variant); dp = end_dp; } template<typename T,typename U> void -data<T,U>::walk_fn_contents(ptr &dp) { +data<T,U>::walk_fn_contents1(ptr &dp) { fn_env_pair pair = bump_dp<fn_env_pair>(dp); if (!pair.env) return; @@ -982,7 +1026,7 @@ data<T,U>::walk_fn_contents(ptr &dp) { template<typename T,typename U> void -data<T,U>::walk_obj_contents(ptr &dp) { +data<T,U>::walk_obj_contents1(ptr &dp) { dp += sizeof(void *); // Skip over the vtable. uint8_t *box_ptr = bump_dp<uint8_t *>(dp); @@ -1003,7 +1047,7 @@ data<T,U>::walk_obj_contents(ptr &dp) { template<typename T,typename U> void -data<T,U>::walk_iface_contents(ptr &dp) { +data<T,U>::walk_iface_contents1(ptr &dp) { uint8_t *box_ptr = bump_dp<uint8_t *>(dp); if (!box_ptr) return; U ref_count_dp(box_ptr); @@ -1017,7 +1061,7 @@ data<T,U>::walk_iface_contents(ptr &dp) { T sub(*static_cast<T *>(this), valtydesc->shape + 5, NULL, NULL, value_dp); sub.align = true; - static_cast<T *>(this)->walk_box_contents(sub, ref_count_dp); + static_cast<T *>(this)->walk_box_contents2(sub, ref_count_dp); } // Polymorphic logging, for convenience @@ -1067,52 +1111,56 @@ private: out(other.out), prefix("") {} - void walk_vec(bool is_pod, uint16_t sp_size) { + void walk_vec2(bool is_pod, uint16_t sp_size) { if (!get_dp<void *>(dp)) out << prefix << "(null)"; else - walk_vec(is_pod, get_vec_data_range(dp)); + walk_vec2(is_pod, get_vec_data_range(dp)); } - void walk_tag(tag_info &tinfo, tag_variant_t tag_variant) { + void walk_tag2(tag_info &tinfo, tag_variant_t tag_variant) { out << prefix << "tag" << tag_variant; - data<log,ptr>::walk_variant(tinfo, tag_variant); + data<log,ptr>::walk_variant1(tinfo, tag_variant); } - void walk_box() { + void walk_box2() { out << prefix << "@"; prefix = ""; - data<log,ptr>::walk_box_contents(); + data<log,ptr>::walk_box_contents1(); } - void walk_uniq() { + void walk_uniq2() { out << prefix << "~"; prefix = ""; - data<log,ptr>::walk_uniq_contents(); + data<log,ptr>::walk_uniq_contents1(); } - void walk_fn() { + void walk_fn2(char kind) { out << prefix << "fn"; prefix = ""; - data<log,ptr>::walk_fn_contents(dp); + data<log,ptr>::walk_fn_contents1(dp); } - void walk_obj() { + void walk_obj2() { out << prefix << "obj"; prefix = ""; - data<log,ptr>::walk_obj_contents(dp); + data<log,ptr>::walk_obj_contents1(dp); } - void walk_iface() { + void walk_iface2() { out << prefix << "iface("; prefix = ""; - data<log,ptr>::walk_iface_contents(dp); + data<log,ptr>::walk_iface_contents1(dp); out << prefix << ")"; } - void walk_subcontext(log &sub) { sub.walk(); } + void walk_tydesc2(char kind) { + out << prefix << "tydesc"; + } + + void walk_subcontext2(log &sub) { sub.walk(); } - void walk_box_contents(log &sub, ptr &ref_count_dp) { + void walk_box_contents2(log &sub, ptr &ref_count_dp) { out << prefix; if (!ref_count_dp) { out << "(null)"; @@ -1122,23 +1170,23 @@ private: } } - void walk_uniq_contents(log &sub) { + void walk_uniq_contents2(log &sub) { out << prefix; sub.align = true; sub.walk(); } - void walk_struct(const uint8_t *end_sp); - void walk_vec(bool is_pod, const std::pair<ptr,ptr> &data); - void walk_variant(tag_info &tinfo, tag_variant_t variant_id, + void walk_struct2(const uint8_t *end_sp); + void walk_vec2(bool is_pod, const std::pair<ptr,ptr> &data); + void walk_variant2(tag_info &tinfo, tag_variant_t variant_id, const std::pair<const uint8_t *,const uint8_t *> variant_ptr_and_end); - void walk_string(const std::pair<ptr,ptr> &data); - void walk_res(const rust_fn *dtor, unsigned n_params, - const type_param *params, const uint8_t *end_sp, bool live); + void walk_string2(const std::pair<ptr,ptr> &data); + void walk_res2(const rust_fn *dtor, unsigned n_params, + const type_param *params, const uint8_t *end_sp, bool live); template<typename T> - inline void walk_number() { + inline void walk_number2() { out << prefix; fmt_number(out, get_dp<T>(dp)); } diff --git a/src/rt/rust_upcall.cpp b/src/rt/rust_upcall.cpp index 423287e017e..12ef28065bd 100644 --- a/src/rt/rust_upcall.cpp +++ b/src/rt/rust_upcall.cpp @@ -279,7 +279,7 @@ upcall_create_shared_type_desc(type_desc *td) { */ void upcall_s_free_shared_type_desc(type_desc *td) -{ +{ // n.b.: invoked from rust_cc.cpp as well as generated code rust_task *task = rust_scheduler::get_task(); LOG_UPCALL_ENTRY(task); diff --git a/src/test/run-pass/uniq-fn-leak.rs b/src/test/run-pass/uniq-fn-leak.rs index 7c9a6e7aca5..adf13c49a1e 100644 --- a/src/test/run-pass/uniq-fn-leak.rs +++ b/src/test/run-pass/uniq-fn-leak.rs @@ -6,12 +6,14 @@ type pointy = { mutable a : maybe_pointy, + c : ~int, d : sendfn()->(), }; fn empty_pointy() -> @pointy { ret @{ mutable a : none, + c : ~22, d : sendfn()->(){}, } } |
