Skip to content

Commit 43765d0

Browse files
committed
VaList -> Ptr<VaArg>
1 parent e87f10e commit 43765d0

3 files changed

Lines changed: 39 additions & 26 deletions

File tree

‎cpp2rust/converter/converter.cpp‎

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,7 @@ bool Converter::VisitRecoveryExpr(clang::RecoveryExpr *expr) {
116116
bool Converter::Convert(clang::QualType qual_type) {
117117
// Catch va_list before desugaring
118118
if (IsVaListType(qual_type)) {
119-
StrCat("VaList");
119+
StrCat("*const VaArg");
120120
return false;
121121
}
122122

@@ -307,7 +307,7 @@ bool Converter::VisitPointerType(clang::PointerType *type) {
307307
}
308308

309309
if (IsVaListType(clang::QualType(type, 0))) {
310-
StrCat("VaList");
310+
StrCat("*const VaArg");
311311
return false;
312312
}
313313

@@ -472,7 +472,8 @@ void Converter::ConvertVaListVarDecl(clang::VarDecl *decl) {
472472
// va_list local variable
473473
StrCat(keyword::kLet);
474474
}
475-
StrCat(keyword_mut_, GetNamedDeclAsString(decl), token::kColon, "VaList");
475+
StrCat(keyword_mut_, GetNamedDeclAsString(decl), token::kColon,
476+
"*const VaArg");
476477
}
477478

478479
bool Converter::NeedsMut(const clang::VarDecl *decl, clang::QualType type,
@@ -1864,7 +1865,7 @@ void Converter::ConvertVariadicArg(clang::Expr *arg) {
18641865
void Converter::ConvertVAArgCall(clang::CallExpr *expr) {
18651866
if (IsBuiltinVaStart(expr)) {
18661867
StrCat(ToString(expr->getArg(0)->IgnoreImpCasts()),
1867-
"= VaList::new(__args)");
1868+
"= __args.as_ptr()");
18681869
return;
18691870
}
18701871
if (IsBuiltinVaEnd(expr)) {
@@ -4244,7 +4245,7 @@ std::string Converter::GetDefaultAsString(clang::QualType qual_type) {
42444245

42454246
if (IsVaListType(qual_type)) {
42464247
computed_expr_type_ = ComputedExprType::FreshValue;
4247-
return "VaList::default()";
4248+
return "::std::ptr::null()";
42484249
}
42494250

42504251
if (auto arr = GetArrayDefaultAsString(qual_type); !arr.empty()) {

‎cpp2rust/converter/models/converter_refcount.cpp‎

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -259,7 +259,7 @@ std::string ConverterRefCount::BoxValue(std::string &&str) const {
259259
bool ConverterRefCount::Convert(clang::QualType qual_type) {
260260
// Catch va_list before desugaring
261261
if (IsVaListType(qual_type)) {
262-
StrCat(BoxType("VaList"));
262+
StrCat(BoxType("Ptr<VaArg>"));
263263
return false;
264264
}
265265

@@ -325,7 +325,7 @@ bool ConverterRefCount::VisitPointerType(clang::PointerType *type) {
325325
}
326326

327327
if (IsVaListType(clang::QualType(type, 0))) {
328-
StrCat("VaList");
328+
StrCat("Ptr<VaArg>");
329329
return false;
330330
}
331331

@@ -792,6 +792,10 @@ void ConverterRefCount::EmitFunctionPreamble(clang::FunctionDecl *decl) {
792792
// name_2)'. We want to get the parameters from the definition if possible,
793793
// i.e. name_2.
794794
PushConversionKind push(*this, ConversionKind::FullRefCount);
795+
if (decl->isVariadic()) {
796+
StrCat("let __args: Value<Box<[VaArg]>> = "
797+
"Rc::new(RefCell::new(__args.into()));");
798+
}
795799
auto params = decl->getDefinition() ? decl->getDefinition()->parameters()
796800
: decl->parameters();
797801
for (auto *param : params) {
@@ -854,7 +858,7 @@ void ConverterRefCount::ConvertVaListVarDecl(clang::VarDecl *decl) {
854858
StrCat(keyword::kLet);
855859
}
856860

857-
StrCat(GetNamedDeclAsString(decl), token::kColon, "Value<VaList>");
861+
StrCat(GetNamedDeclAsString(decl), token::kColon, "Value<Ptr<VaArg>>");
858862
}
859863

860864
bool ConverterRefCount::ConvertVarDeclSkipInit(clang::VarDecl *decl) {
@@ -1283,7 +1287,12 @@ void ConverterRefCount::ConvertPrintf(clang::CallExpr *expr) {
12831287
}
12841288

12851289
bool ConverterRefCount::VisitCallExpr(clang::CallExpr *expr) {
1286-
if (IsBuiltinVaStart(expr) || IsBuiltinVaEnd(expr) || IsBuiltinVaCopy(expr)) {
1290+
if (IsBuiltinVaStart(expr)) {
1291+
StrCat(ToString(expr->getArg(0)->IgnoreImpCasts()),
1292+
"= __args.as_pointer()");
1293+
return false;
1294+
}
1295+
if (IsBuiltinVaEnd(expr) || IsBuiltinVaCopy(expr)) {
12871296
ConvertVAArgCall(expr);
12881297
return false;
12891298
}
@@ -2526,7 +2535,7 @@ std::string ConverterRefCount::GetDefaultAsString(clang::QualType qual_type) {
25262535

25272536
if (IsVaListType(qual_type)) {
25282537
computed_expr_type_ = ComputedExprType::FreshValue;
2529-
return BoxValue("VaList::default()");
2538+
return BoxValue("Ptr::<VaArg>::default()");
25302539
}
25312540

25322541
if (auto arr = GetArrayDefaultAsString(qual_type); !arr.empty()) {

‎libcc2rs/src/va_args.rs‎

Lines changed: 19 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ use std::any::Any;
55
use std::ffi::c_void;
66
use std::rc::Rc;
77

8+
use crate::inc::PrefixInc;
9+
use crate::rc::Ptr;
810
use crate::void::AnyPtr;
911

1012
#[derive(Clone)]
@@ -52,27 +54,28 @@ impl<T: crate::reinterpret::ByteRepr + 'static> From<crate::rc::Ptr<T>> for VaAr
5254
}
5355
}
5456

55-
#[derive(Clone, Default)]
56-
pub struct VaList {
57-
args: Rc<[VaArg]>,
58-
pos: usize,
57+
impl crate::reinterpret::ByteRepr for VaArg {}
58+
59+
impl Ptr<VaArg> {
60+
pub fn arg<T: VaArgGet>(&mut self) -> T {
61+
let val = self.with(T::get);
62+
self.prefix_inc();
63+
val
64+
}
5965
}
6066

61-
impl crate::reinterpret::ByteRepr for VaList {}
67+
pub trait VaArgs {
68+
unsafe fn arg<T: VaArgGet>(&mut self) -> T;
69+
}
6270

63-
impl VaList {
64-
pub fn new(args: &[VaArg]) -> Self {
65-
VaList {
66-
args: Rc::from(args),
67-
pos: 0,
71+
impl VaArgs for *const VaArg {
72+
unsafe fn arg<T: VaArgGet>(&mut self) -> T {
73+
unsafe {
74+
let val = T::get(&**self);
75+
*self = self.add(1);
76+
val
6877
}
6978
}
70-
71-
pub fn arg<T: VaArgGet>(&mut self) -> T {
72-
let val = &self.args[self.pos];
73-
self.pos += 1;
74-
T::get(val)
75-
}
7679
}
7780

7881
pub trait VaArgGet {

0 commit comments

Comments
 (0)