Skip to content

Commit 9f1c76b

Browse files
committed
Use the Default default implementation more often
1 parent 0db209a commit 9f1c76b

43 files changed

Lines changed: 191 additions & 480 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

‎cpp2rust/converter/converter.cpp‎

Lines changed: 23 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -641,33 +641,35 @@ bool Converter::RecordDerivesDefault(const clang::RecordDecl *decl) {
641641
}
642642

643643
for (auto f : decl->fields()) {
644-
if (f->hasInClassInitializer()) {
644+
if (f->hasInClassInitializer() || !TypeDerivesDefault(f->getType())) {
645645
return false;
646646
}
647+
}
647648

648-
// Records that contain function pointer do not derive Default
649-
if (auto ptr_ty = f->getType()->getAs<clang::PointerType>()) {
650-
if (ptr_ty->getPointeeType()->isFunctionType()) {
651-
return false;
652-
}
653-
}
649+
return true;
650+
}
654651

655-
// Records that contain std::array do not derive Default
656-
if (Printer::ToString(ctx_, f->getType()).contains("std::array")) {
657-
return false;
658-
}
652+
bool Converter::TypeDerivesDefault(clang::QualType qual_type) {
653+
// Rust only implements Default for arrays of up to 32 elements
654+
if (auto *array_type = ctx_.getAsConstantArrayType(qual_type)) {
655+
return array_type->getSize().ule(32) &&
656+
TypeDerivesDefault(array_type->getElementType());
657+
}
658+
if (qual_type->isArrayType()) {
659+
return false;
660+
}
659661

660-
// Records that contain C arrays do not derive Default
661-
if (f->getType()->isArrayType()) {
662-
return false;
663-
}
662+
// Types that need a custom array initializer (e.g., std::array, which is
663+
// translated to Vec)
664+
if (!GetArrayDefaultAsString(qual_type).empty()) {
665+
return false;
666+
}
664667

665-
// Records that contain libc types do not derive Default
666-
if (auto record = f->getType()->getAsRecordDecl()) {
667-
if (ctx_.getSourceManager().isInSystemHeader(record->getLocation()) &&
668-
f->getType().isPODType(ctx_)) {
669-
return false;
670-
}
668+
// libc types do not implement Default
669+
if (auto record = qual_type->getAsRecordDecl()) {
670+
if (ctx_.getSourceManager().isInSystemHeader(record->getLocation()) &&
671+
qual_type.isPODType(ctx_)) {
672+
return false;
671673
}
672674
}
673675

‎cpp2rust/converter/converter.h‎

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -732,6 +732,8 @@ class Converter : public clang::RecursiveASTVisitor<Converter> {
732732

733733
virtual bool RecordDerivesDefault(const clang::RecordDecl *decl);
734734

735+
virtual bool TypeDerivesDefault(clang::QualType qual_type);
736+
735737
bool RecordDerivesCopy(const clang::RecordDecl *decl) const;
736738

737739
bool IsPassThroughRule(clang::Expr *expr) const;

‎cpp2rust/converter/models/converter_refcount.cpp‎

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2295,6 +2295,11 @@ ConverterRefCount::GetStructAttributes(const clang::RecordDecl *decl) {
22952295
return attrs;
22962296
}
22972297

2298+
bool ConverterRefCount::TypeDerivesDefault(clang::QualType qual_type) {
2299+
// Arrays are translated to Value<Box<[T]>>, whose Default is empty
2300+
return !qual_type->isArrayType() && Converter::TypeDerivesDefault(qual_type);
2301+
}
2302+
22982303
std::string ConverterRefCount::ConvertVarInitValue(clang::QualType qual_type,
22992304
clang::Expr *expr) {
23002305
if (auto lambda = clang::dyn_cast<clang::LambdaExpr>(

‎cpp2rust/converter/models/converter_refcount.h‎

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -229,6 +229,8 @@ class ConverterRefCount final : public Converter {
229229
std::vector<const char *>
230230
GetStructAttributes(const clang::RecordDecl *decl) override;
231231

232+
bool TypeDerivesDefault(clang::QualType qual_type) override;
233+
232234
bool Convert(clang::QualType qual_type) override;
233235
bool
234236
Convert(clang::Expr *expr,

‎tests/multi-file/defaulted_move_cross_tu/out/unsafe/defaulted_move_cross_tu.rs‎

Lines changed: 1 addition & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ use std::io::{Read, Seek, Write};
77
use std::os::fd::{AsFd, FromRawFd, IntoRawFd};
88
use std::rc::Rc;
99
#[repr(C)]
10-
#[derive()]
10+
#[derive(Default)]
1111
pub struct S {
1212
pub v: Vec<i32>,
1313
pub n: [i32; 2],
@@ -42,14 +42,6 @@ impl S {
4242
return &mut (*(self as *mut S));
4343
}
4444
}
45-
impl Default for S {
46-
fn default() -> Self {
47-
S {
48-
v: Default::default(),
49-
n: [0_i32; 2],
50-
}
51-
}
52-
}
5345
pub unsafe fn sum_0(s: *const S) -> i32 {
5446
return ((((*s).v.len() as i32) + ((*s).n[(0) as usize])) + ((*s).n[(1) as usize]));
5547
}

‎tests/unit/default.cpp‎

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,23 @@ struct Pointers {
66
int x5;
77
};
88

9+
struct SmallArrays {
10+
int a[32];
11+
int (*f)(int);
12+
int (*fs[2])(int);
13+
Pointers p[2];
14+
};
15+
16+
struct BigArray {
17+
int a[33];
18+
};
19+
920
int main() {
1021
Pointers *default_pointers = new Pointers[10];
1122
delete[] default_pointers;
23+
SmallArrays *small = new SmallArrays[2];
24+
delete[] small;
25+
BigArray *big = new BigArray[2];
26+
delete[] big;
1227
return 0;
1328
}

‎tests/unit/out/refcount/default.rs‎

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,54 @@ impl Default for Pointers {
4343
}
4444
}
4545
}
46+
#[derive(DeepClone, Record, ByteRepr, VaArg, FnPtrArg)]
47+
#[byte_size(440)]
48+
pub struct SmallArrays {
49+
#[offset(0)]
50+
#[byte_size(128)]
51+
pub a: Value<Box<[i32]>>,
52+
#[offset(128)]
53+
#[byte_size(8)]
54+
pub f: FnPtr<fn(i32) -> i32>,
55+
#[offset(136)]
56+
#[byte_size(16)]
57+
pub fs: Value<Box<[FnPtr<fn(i32) -> i32>]>>,
58+
#[offset(152)]
59+
#[byte_size(288)]
60+
pub p: Value<Box<[Pointers]>>,
61+
}
62+
impl Default for SmallArrays {
63+
fn default() -> Self {
64+
SmallArrays {
65+
a: Rc::new(RefCell::new((0..32).map(|_| 0_i32).collect::<Box<[i32]>>())),
66+
f: FnPtr::<fn(i32) -> i32>::null(),
67+
fs: Rc::new(RefCell::new(
68+
(0..2)
69+
.map(|_| FnPtr::<fn(i32) -> i32>::null())
70+
.collect::<Box<[FnPtr<fn(i32) -> i32>]>>(),
71+
)),
72+
p: Rc::new(RefCell::new(
73+
(0..2)
74+
.map(|_| <Pointers>::default())
75+
.collect::<Box<[Pointers]>>(),
76+
)),
77+
}
78+
}
79+
}
80+
#[derive(DeepClone, Record, ByteRepr, VaArg, FnPtrArg)]
81+
#[byte_size(132)]
82+
pub struct BigArray {
83+
#[offset(0)]
84+
#[byte_size(132)]
85+
pub a: Value<Box<[i32]>>,
86+
}
87+
impl Default for BigArray {
88+
fn default() -> Self {
89+
BigArray {
90+
a: Rc::new(RefCell::new((0..33).map(|_| 0_i32).collect::<Box<[i32]>>())),
91+
}
92+
}
93+
}
4694
pub fn main() {
4795
__cpp2rust_init_globals();
4896
std::process::exit(main_0());
@@ -54,6 +102,18 @@ fn main_0() -> i32 {
54102
.collect::<Box<[Pointers]>>(),
55103
)));
56104
(*default_pointers.borrow()).delete();
105+
let small: Value<Ptr<SmallArrays>> = Rc::new(RefCell::new(Ptr::alloc_array(
106+
(0..2_usize)
107+
.map(|_| <SmallArrays>::default())
108+
.collect::<Box<[SmallArrays]>>(),
109+
)));
110+
(*small.borrow()).delete();
111+
let big: Value<Ptr<BigArray>> = Rc::new(RefCell::new(Ptr::alloc_array(
112+
(0..2_usize)
113+
.map(|_| <BigArray>::default())
114+
.collect::<Box<[BigArray]>>(),
115+
)));
116+
(*big.borrow()).delete();
57117
return 0;
58118
}
59119
pub fn __cpp2rust_init_globals() {}

‎tests/unit/out/refcount/default_in_statics.rs‎

Lines changed: 1 addition & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ impl Default for Outer {
6060
}
6161
}
6262
}
63-
#[derive(Clone, Record, ByteRepr, VaArg, FnPtrArg)]
63+
#[derive(Clone, Record, ByteRepr, VaArg, FnPtrArg, Default)]
6464
#[byte_size(40)]
6565
pub struct Foo {
6666
#[offset(0)]
@@ -78,17 +78,6 @@ pub struct Foo {
7878
#[offset(32)]
7979
pub n: i32,
8080
}
81-
impl Default for Foo {
82-
fn default() -> Self {
83-
Foo {
84-
s1: Ptr::<u8>::null(),
85-
s2: Ptr::<u8>::null(),
86-
fn1: FnPtr::<fn(i32) -> i32>::null(),
87-
fn2: FnPtr::<fn(i32) -> i32>::null(),
88-
n: 0_i32,
89-
}
90-
}
91-
}
9281
thread_local!(
9382
pub static static_fn_0: Value<FnPtr<fn(i32) -> i32>> =
9483
Rc::new(RefCell::new(FnPtr::<fn(i32) -> i32>::null()));

‎tests/unit/out/refcount/fn_ptr_struct.rs‎

Lines changed: 1 addition & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ use std::io::prelude::*;
66
use std::io::{Read, Seek, Write};
77
use std::os::fd::AsFd;
88
use std::rc::{Rc, Weak};
9-
#[derive(Clone, Record, ByteRepr, VaArg, FnPtrArg)]
9+
#[derive(Clone, Record, ByteRepr, VaArg, FnPtrArg, Default)]
1010
#[byte_size(16)]
1111
pub struct Handler {
1212
#[offset(0)]
@@ -15,14 +15,6 @@ pub struct Handler {
1515
#[byte_size(8)]
1616
pub cb: FnPtr<fn(i32) -> i32>,
1717
}
18-
impl Default for Handler {
19-
fn default() -> Self {
20-
Handler {
21-
tag: 0_i32,
22-
cb: FnPtr::<fn(i32) -> i32>::null(),
23-
}
24-
}
25-
}
2618
pub fn double_it_0(x: i32) -> i32 {
2719
let x: Value<i32> = Rc::new(RefCell::new(x));
2820
return ((*x.borrow()) * 2);

‎tests/unit/out/refcount/fn_ptr_vtable.rs‎

Lines changed: 1 addition & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ use std::io::prelude::*;
66
use std::io::{Read, Seek, Write};
77
use std::os::fd::AsFd;
88
use std::rc::{Rc, Weak};
9-
#[derive(Clone, Record, ByteRepr, VaArg, FnPtrArg)]
9+
#[derive(Clone, Record, ByteRepr, VaArg, FnPtrArg, Default)]
1010
#[byte_size(24)]
1111
pub struct Vtable {
1212
#[offset(0)]
@@ -19,15 +19,6 @@ pub struct Vtable {
1919
#[byte_size(8)]
2020
pub destroy: FnPtr<fn(AnyPtr)>,
2121
}
22-
impl Default for Vtable {
23-
fn default() -> Self {
24-
Vtable {
25-
create: FnPtr::<fn(i32) -> AnyPtr>::null(),
26-
get: FnPtr::<fn(AnyPtr) -> i32>::null(),
27-
destroy: FnPtr::<fn(AnyPtr)>::null(),
28-
}
29-
}
30-
}
3122
thread_local!(
3223
pub static storage_0: Value<i32> = Rc::new(RefCell::new(0_i32));
3324
);

0 commit comments

Comments
 (0)