@@ -1896,13 +1896,17 @@ namespace Cpp {
1896
1896
void make_narg_ctor (const FunctionDecl* FD, const unsigned N,
1897
1897
std::ostringstream& typedefbuf,
1898
1898
std::ostringstream& callbuf,
1899
- const std::string& class_name, int indent_level) {
1899
+ const std::string& class_name, int indent_level, bool array = false ) {
1900
1900
// Make a code string that follows this pattern:
1901
1901
//
1902
1902
// ClassName(args...)
1903
+ // OR
1904
+ // ClassName[nary](args...) // array of objects
1903
1905
//
1904
-
1905
- callbuf << class_name << " (" ;
1906
+
1907
+ callbuf << class_name;
1908
+ if (array) callbuf << " [nary]" ;
1909
+ callbuf << " (" ;
1906
1910
for (unsigned i = 0U ; i < N; ++i) {
1907
1911
const ParmVarDecl* PVD = FD->getParamDecl (i);
1908
1912
QualType Ty = PVD->getType ();
@@ -2085,16 +2089,39 @@ namespace Cpp {
2085
2089
std::ostringstream& buf, int indent_level) {
2086
2090
// Make a code string that follows this pattern:
2087
2091
//
2088
- // (*(ClassName**)ret) = (obj) ?
2089
- // new (*(ClassName**)ret) ClassName(args...) : new ClassName(args...);
2090
- //
2092
+ // // array of objects construction
2093
+ // if (nary > 1) {
2094
+ // (*(ClassName**)ret) = (obj) ? new (*(ClassName**)ret) ClassName[nary](args...) : new ClassName[nary](args...);
2095
+ // }
2096
+ // else {
2097
+ // (*(ClassName**)ret) = (obj) ? new (*(ClassName**)ret) ClassName(args...) : new ClassName(args...);
2098
+ // }
2091
2099
{
2092
2100
std::ostringstream typedefbuf;
2093
2101
std::ostringstream callbuf;
2094
2102
//
2095
2103
// Write the return value assignment part.
2096
2104
//
2097
2105
indent (callbuf, indent_level);
2106
+ callbuf << " if (nary > 1) {\n " ;
2107
+ indent (callbuf, indent_level);
2108
+ callbuf << " (*(" << class_name << " **)ret) = " ;
2109
+ callbuf << " (obj) ? new (*(" << class_name << " **)ret) " ;
2110
+ make_narg_ctor (FD, N, typedefbuf, callbuf, class_name, indent_level, true );
2111
+
2112
+ callbuf << " : new " ;
2113
+ //
2114
+ // Write the actual expression.
2115
+ //
2116
+ make_narg_ctor (FD, N, typedefbuf, callbuf, class_name, indent_level, true );
2117
+ //
2118
+ // End the new expression statement.
2119
+ //
2120
+ callbuf << " ;\n " ;
2121
+ indent (callbuf, indent_level);
2122
+ callbuf << " }\n " ;
2123
+ callbuf << " else {\n " ;
2124
+ indent (callbuf, indent_level);
2098
2125
callbuf << " (*(" << class_name << " **)ret) = " ;
2099
2126
callbuf << " (obj) ? new (*(" << class_name << " **)ret) " ;
2100
2127
make_narg_ctor (FD, N, typedefbuf, callbuf, class_name, indent_level);
@@ -2108,6 +2135,8 @@ namespace Cpp {
2108
2135
// End the new expression statement.
2109
2136
//
2110
2137
callbuf << " ;\n " ;
2138
+ indent (callbuf, --indent_level);
2139
+ callbuf << " }\n " ;
2111
2140
//
2112
2141
// Output the whole new expression and return statement.
2113
2142
//
@@ -2626,7 +2655,7 @@ namespace Cpp {
2626
2655
" __attribute__((annotate(\" __cling__ptrcheck(off)\" )))\n "
2627
2656
" extern \" C\" void " ;
2628
2657
buf << wrapper_name;
2629
- buf << " (void* obj, int nargs, void** args, void* ret)\n "
2658
+ buf << " (void* obj, int nargs, void** args, void* ret, unsigned long nary )\n "
2630
2659
" {\n " ;
2631
2660
++indent_level;
2632
2661
if (min_args == num_params) {
@@ -3577,17 +3606,19 @@ namespace Cpp {
3577
3606
}
3578
3607
}
3579
3608
3580
- TCppObject_t Allocate (TCppScope_t scope) {
3581
- return (TCppObject_t)::operator new (Cpp::SizeOf (scope));
3609
+ TCppObject_t Allocate (TCppScope_t scope, TCppIndex_t count ) {
3610
+ return (TCppObject_t)::operator new (Cpp::SizeOf (scope) * count );
3582
3611
}
3583
3612
3584
- void Deallocate (TCppScope_t scope, TCppObject_t address) {
3585
- ::operator delete (address);
3613
+ void Deallocate (TCppScope_t scope, TCppObject_t address, TCppIndex_t count)
3614
+ {
3615
+ size_t bytes = Cpp::SizeOf (scope) * count;
3616
+ ::operator delete (address, bytes);
3586
3617
}
3587
3618
3588
3619
// FIXME: Add optional arguments to the operator new.
3589
3620
TCppObject_t Construct (compat::Interpreter& interp, TCppScope_t scope,
3590
- void * arena /* =nullptr*/ ) {
3621
+ void * arena /* =nullptr*/ , TCppIndex_t count /* =1UL */ ) {
3591
3622
auto * Class = (Decl*) scope;
3592
3623
// FIXME: Diagnose.
3593
3624
if (!HasDefaultConstructor (Class))
@@ -3596,7 +3627,7 @@ namespace Cpp {
3596
3627
auto * const Ctor = GetDefaultConstructor (interp, Class);
3597
3628
if (JitCall JC = MakeFunctionCallable (&interp, Ctor)) {
3598
3629
if (arena) {
3599
- JC.Invoke (&arena, {}, (void *)~0 ); // Tell Invoke to use placement new.
3630
+ JC.Invoke (&arena, {}, (void *)~0 , count ); // Tell Invoke to use placement new.
3600
3631
return arena;
3601
3632
}
3602
3633
@@ -3607,22 +3638,22 @@ namespace Cpp {
3607
3638
return nullptr ;
3608
3639
}
3609
3640
3610
- TCppObject_t Construct (TCppScope_t scope, void * arena /* =nullptr*/ ) {
3611
- return Construct (getInterp (), scope, arena);
3641
+ TCppObject_t Construct (TCppScope_t scope, void * arena /* =nullptr*/ , TCppIndex_t count /* =0UL */ ) {
3642
+ return Construct (getInterp (), scope, arena, count );
3612
3643
}
3613
3644
3614
3645
void Destruct (compat::Interpreter& interp, TCppObject_t This, Decl* Class,
3615
- bool withFree) {
3646
+ bool withFree, TCppIndex_t nary ) {
3616
3647
if (auto wrapper = make_dtor_wrapper (interp, Class)) {
3617
- (*wrapper)(This, /* nary= */ 0 , withFree);
3648
+ (*wrapper)(This, nary, withFree);
3618
3649
return ;
3619
3650
}
3620
3651
// FIXME: Diagnose.
3621
3652
}
3622
3653
3623
- void Destruct (TCppObject_t This, TCppScope_t scope, bool withFree /* =true*/ ) {
3654
+ void Destruct (TCppObject_t This, TCppScope_t scope, bool withFree /* =true*/ , TCppIndex_t count /* =1UL */ ) {
3624
3655
auto * Class = static_cast <Decl*>(scope);
3625
- Destruct (getInterp (), This, Class, withFree);
3656
+ Destruct (getInterp (), This, Class, withFree, count );
3626
3657
}
3627
3658
3628
3659
class StreamCaptureInfo {
0 commit comments