Skip to content

Commit 7a8f3af

Browse files
committed
handle unsized by-ref values
1 parent 8635445 commit 7a8f3af

1 file changed

Lines changed: 28 additions & 2 deletions

File tree

src/value_and_place.rs

Lines changed: 28 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -204,7 +204,14 @@ impl<'tcx> CValue<'tcx> {
204204
let (field_ptr, field_layout) = codegen_field(fx, ptr, None, layout, field);
205205
CValue::by_ref(field_ptr, field_layout)
206206
}
207-
CValueInner::ByRef(_, Some(_)) => todo!(),
207+
CValueInner::ByRef(ptr, Some(extra)) => {
208+
let (field_ptr, field_layout) = codegen_field(fx, ptr, Some(extra), layout, field);
209+
if fx.tcx.type_has_metadata(field_layout.ty, ty::TypingEnv::fully_monomorphized()) {
210+
CValue::by_ref_unsized(field_ptr, extra, field_layout)
211+
} else {
212+
CValue::by_ref(field_ptr, field_layout)
213+
}
214+
}
208215
}
209216
}
210217

@@ -655,7 +662,26 @@ impl<'tcx> CPlace<'tcx> {
655662
flags,
656663
);
657664
}
658-
CValueInner::ByRef(_, Some(_)) => todo!(),
665+
CValueInner::ByRef(from_ptr, Some(_extra)) => {
666+
// Unsized values shouldn't normally be written into sized places. However,
667+
// if this happens, we can still copy the sized prefix using the destination layout's fixed size.
668+
let from_addr = from_ptr.get_addr(fx);
669+
let to_addr = to_ptr.get_addr(fx);
670+
let src_layout = from.1;
671+
let size = dst_layout.size.bytes();
672+
let src_align = src_layout.align.bytes().try_into().unwrap_or(128);
673+
let dst_align = dst_layout.align.bytes().try_into().unwrap_or(128);
674+
fx.bcx.emit_small_memory_copy(
675+
fx.target_config,
676+
to_addr,
677+
from_addr,
678+
size,
679+
dst_align,
680+
src_align,
681+
true,
682+
flags,
683+
);
684+
}
659685
}
660686
}
661687
}

0 commit comments

Comments
 (0)