C++: switch to getImplicitDestructorCall

This commit is contained in:
Robert Marsh
2024-01-23 17:23:58 +00:00
parent 3a0290b1e8
commit 3970a9fe39
6 changed files with 192 additions and 30 deletions

View File

@@ -310,7 +310,7 @@ class ExprNode extends AstNode {
result.getAst() = expr.getChild(childIndex)
or
exists(int destructorIndex |
result.getAst() = expr.getSyntheticDestructor(destructorIndex) and
result.getAst() = expr.getImplicitDestructorCall(destructorIndex) and
childIndex = destructorIndex + max(int index | exists(expr.getChild(index)) or index = 0) + 1
)
}
@@ -448,7 +448,7 @@ class StmtNode extends AstNode {
)
or
exists(int destructorIndex |
result.getAst() = stmt.getSyntheticDestructor(destructorIndex) and
result.getAst() = stmt.getImplicitDestructorCall(destructorIndex) and
childIndex = destructorIndex + max(int index | exists(stmt.getChild(index)) or index = 0) + 1
)
}
@@ -676,7 +676,7 @@ private string getChildAccessorWithoutConversions(Locatable parent, Element chil
exists(int n | s.getChild(n) = child and result = "getChild(" + n + ")")
or
exists(int n |
s.getSyntheticDestructor(n) = child and result = "getSyntheticDestructor(" + n + ")"
s.getImplicitDestructorCall(n) = child and result = "getImplicitDestructorCall(" + n + ")"
)
)
or
@@ -687,7 +687,7 @@ private string getChildAccessorWithoutConversions(Locatable parent, Element chil
exists(int n | expr.getChild(n) = child and result = "getChild(" + n + ")")
or
exists(int n |
expr.getSyntheticDestructor(n) = child and result = "getSyntheticDestructor(" + n + ")"
expr.getImplicitDestructorCall(n) = child and result = "getImplicitDestructorCall(" + n + ")"
)
)
)

View File

@@ -62,14 +62,14 @@ class Expr extends StmtParent, @expr {
* Gets the `n`th compiler-generated destructor call that is performed after this expression, in
* order of destruction.
*/
DestructorCall getSyntheticDestructor(int n) {
DestructorCall getImplicitDestructorCall(int n) {
synthetic_destructor_call(this, max(int i | synthetic_destructor_call(this, i, _)) - n, result)
}
/**
* Gets a compiler-generated destructor call that is performed after this expression.
*/
DestructorCall getASyntheticDestructor() {
DestructorCall getAnImplicitDestructorCall() {
synthetic_destructor_call(this, _, result)
}

View File

@@ -63,11 +63,11 @@ class Stmt extends StmtParent, @stmt {
* Gets the `n`th compiler-generated destructor call that is performed after this statement, in
* order of destruction.
*/
DestructorCall getSyntheticDestructor(int n) {
DestructorCall getImplicitDestructorCall(int n) {
synthetic_destructor_call(this, max(int i | synthetic_destructor_call(this, i, _)) - n, result)
}
DestructorCall getASyntheticDestructor() {
DestructorCall getAnImplicitDestructorCall() {
synthetic_destructor_call(this, _, result)
}

View File

@@ -63,7 +63,7 @@ destructors.cpp:
# 13| Type = [IntType] int
# 13| Value = [Literal] 130
# 13| ValueCategory = prvalue
# 14| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 14| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 14| Type = [VoidType] void
# 14| ValueCategory = prvalue
# 14| getQualifier(): [VariableAccess] c30
@@ -86,13 +86,13 @@ destructors.cpp:
# 17| Type = [IntType] int
# 17| ValueCategory = prvalue(load)
# 17| getThen(): [GotoStmt] goto ...
# 21| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 21| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 21| Type = [VoidType] void
# 21| ValueCategory = prvalue
# 21| getQualifier(): [VariableAccess] c31
# 21| Type = [Class] C
# 21| ValueCategory = lvalue
# 26| getSyntheticDestructor(1): [DestructorCall] call to ~C
# 26| getImplicitDestructorCall(1): [DestructorCall] call to ~C
# 26| Type = [VoidType] void
# 26| ValueCategory = prvalue
# 26| getQualifier(): [VariableAccess] c20
@@ -118,25 +118,25 @@ destructors.cpp:
# 19| Type = [IntType] int
# 19| ValueCategory = prvalue(load)
# 19| getThen(): [ReturnStmt] return ...
# 21| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 21| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 21| Type = [VoidType] void
# 21| ValueCategory = prvalue
# 21| getQualifier(): [VariableAccess] c32
# 21| Type = [Class] C
# 21| ValueCategory = lvalue
# 21| getSyntheticDestructor(1): [DestructorCall] call to ~C
# 21| getImplicitDestructorCall(1): [DestructorCall] call to ~C
# 21| Type = [VoidType] void
# 21| ValueCategory = prvalue
# 21| getQualifier(): [VariableAccess] c31
# 21| Type = [Class] C
# 21| ValueCategory = lvalue
# 26| getSyntheticDestructor(2): [DestructorCall] call to ~C
# 26| getImplicitDestructorCall(2): [DestructorCall] call to ~C
# 26| Type = [VoidType] void
# 26| ValueCategory = prvalue
# 26| getQualifier(): [VariableAccess] c20
# 26| Type = [Class] C
# 26| ValueCategory = lvalue
# 35| getSyntheticDestructor(3): [DestructorCall] call to ~C
# 35| getImplicitDestructorCall(3): [DestructorCall] call to ~C
# 35| Type = [VoidType] void
# 35| ValueCategory = prvalue
# 35| getQualifier(): [VariableAccess] c10
@@ -157,19 +157,19 @@ destructors.cpp:
# 20| Type = [IntType] int
# 20| Value = [Literal] 133
# 20| ValueCategory = prvalue
# 21| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 21| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 21| Type = [VoidType] void
# 21| ValueCategory = prvalue
# 21| getQualifier(): [VariableAccess] c33
# 21| Type = [Class] C
# 21| ValueCategory = lvalue
# 21| getSyntheticDestructor(1): [DestructorCall] call to ~C
# 21| getImplicitDestructorCall(1): [DestructorCall] call to ~C
# 21| Type = [VoidType] void
# 21| ValueCategory = prvalue
# 21| getQualifier(): [VariableAccess] c32
# 21| Type = [Class] C
# 21| ValueCategory = lvalue
# 21| getSyntheticDestructor(2): [DestructorCall] call to ~C
# 21| getImplicitDestructorCall(2): [DestructorCall] call to ~C
# 21| Type = [VoidType] void
# 21| ValueCategory = prvalue
# 21| getQualifier(): [VariableAccess] c31
@@ -187,7 +187,7 @@ destructors.cpp:
# 23| Type = [IntType] int
# 23| Value = [Literal] 134
# 23| ValueCategory = prvalue
# 24| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 24| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 24| Type = [VoidType] void
# 24| ValueCategory = prvalue
# 24| getQualifier(): [VariableAccess] c34
@@ -204,13 +204,13 @@ destructors.cpp:
# 25| Type = [IntType] int
# 25| Value = [Literal] 121
# 25| ValueCategory = prvalue
# 26| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 26| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 26| Type = [VoidType] void
# 26| ValueCategory = prvalue
# 26| getQualifier(): [VariableAccess] c21
# 26| Type = [Class] C
# 26| ValueCategory = lvalue
# 26| getSyntheticDestructor(1): [DestructorCall] call to ~C
# 26| getImplicitDestructorCall(1): [DestructorCall] call to ~C
# 26| Type = [VoidType] void
# 26| ValueCategory = prvalue
# 26| getQualifier(): [VariableAccess] c20
@@ -228,7 +228,7 @@ destructors.cpp:
# 28| Type = [IntType] int
# 28| Value = [Literal] 122
# 28| ValueCategory = prvalue
# 29| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 29| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 29| Type = [VoidType] void
# 29| ValueCategory = prvalue
# 29| getQualifier(): [VariableAccess] c22
@@ -247,7 +247,7 @@ destructors.cpp:
# 32| Type = [IntType] int
# 32| Value = [Literal] 123
# 32| ValueCategory = prvalue
# 33| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 33| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 33| Type = [VoidType] void
# 33| ValueCategory = prvalue
# 33| getQualifier(): [VariableAccess] c23
@@ -265,13 +265,13 @@ destructors.cpp:
# 34| Value = [Literal] 111
# 34| ValueCategory = prvalue
# 35| getStmt(5): [ReturnStmt] return ...
# 35| getSyntheticDestructor(0): [DestructorCall] call to ~C
# 35| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 35| Type = [VoidType] void
# 35| ValueCategory = prvalue
# 35| getQualifier(): [VariableAccess] c11
# 35| Type = [Class] C
# 35| ValueCategory = lvalue
# 35| getSyntheticDestructor(1): [DestructorCall] call to ~C
# 35| getImplicitDestructorCall(1): [DestructorCall] call to ~C
# 35| Type = [VoidType] void
# 35| ValueCategory = prvalue
# 35| getQualifier(): [VariableAccess] c10
@@ -341,7 +341,7 @@ destructors2.cpp:
# 23| ValueCategory = prvalue(load)
# 23| getThen(): [BlockStmt] { ... }
# 24| getStmt(0): [ReturnStmt] return ...
# 27| getSyntheticDestructor(0): [DestructorCall] call to ~Class2
# 27| getImplicitDestructorCall(0): [DestructorCall] call to ~Class2
# 27| Type = [VoidType] void
# 27| ValueCategory = prvalue
# 27| getQualifier(): [VariableAccess] c
@@ -369,13 +369,13 @@ destructors2.cpp:
# 26| Type = [SpecifiedType] const Class2
# 26| ValueCategory = lvalue
# 27| getStmt(3): [ReturnStmt] return ...
# 27| getSyntheticDestructor(0): [DestructorCall] call to ~Inner
# 27| getImplicitDestructorCall(0): [DestructorCall] call to ~Inner
# 27| Type = [VoidType] void
# 27| ValueCategory = prvalue
# 27| getQualifier(): [VariableAccess] inner
# 27| Type = [NestedClass] Inner
# 27| ValueCategory = lvalue
# 27| getSyntheticDestructor(1): [DestructorCall] call to ~Class2
# 27| getImplicitDestructorCall(1): [DestructorCall] call to ~Class2
# 27| Type = [VoidType] void
# 27| ValueCategory = prvalue
# 27| getQualifier(): [VariableAccess] c

View File

@@ -1,11 +1,11 @@
import cpp
query predicate exprDestructors(Expr e, int i, DestructorCall d, Expr destructed) {
d = e.getSyntheticDestructor(i) and
d = e.getImplicitDestructorCall(i) and
d.getQualifier() = destructed
}
query predicate stmtDestructors(Stmt s, int i, DestructorCall d, Expr destructed) {
d = s.getSyntheticDestructor(i) and
d = s.getImplicitDestructorCall(i) and
d.getQualifier() = destructed
}

View File

@@ -5565,6 +5565,30 @@ ir.cpp:
# 619| Type = [PointerType] const char *
# 619| ValueCategory = prvalue
# 620| getStmt(4): [ReturnStmt] return ...
# 620| getImplicitDestructorCall(0): [DestructorCall] call to ~String
# 620| Type = [VoidType] void
# 620| ValueCategory = prvalue
# 620| getQualifier(): [VariableAccess] s4
# 620| Type = [Struct] String
# 620| ValueCategory = lvalue
# 620| getImplicitDestructorCall(1): [DestructorCall] call to ~String
# 620| Type = [VoidType] void
# 620| ValueCategory = prvalue
# 620| getQualifier(): [VariableAccess] s3
# 620| Type = [Struct] String
# 620| ValueCategory = lvalue
# 620| getImplicitDestructorCall(2): [DestructorCall] call to ~String
# 620| Type = [VoidType] void
# 620| ValueCategory = prvalue
# 620| getQualifier(): [VariableAccess] s2
# 620| Type = [Struct] String
# 620| ValueCategory = lvalue
# 620| getImplicitDestructorCall(3): [DestructorCall] call to ~String
# 620| Type = [VoidType] void
# 620| ValueCategory = prvalue
# 620| getQualifier(): [VariableAccess] s1
# 620| Type = [Struct] String
# 620| ValueCategory = lvalue
# 622| [TopLevelFunction] void CallMethods(String&, String*, String)
# 622| <params>:
# 622| getParameter(0): [Parameter] r
@@ -7312,6 +7336,24 @@ ir.cpp:
# 839| Type = [PointerType] Base *
# 839| ValueCategory = prvalue
# 840| getStmt(34): [ReturnStmt] return ...
# 840| getImplicitDestructorCall(0): [DestructorCall] call to ~Derived
# 840| Type = [VoidType] void
# 840| ValueCategory = prvalue
# 840| getQualifier(): [VariableAccess] d
# 840| Type = [Struct] Derived
# 840| ValueCategory = lvalue
# 840| getImplicitDestructorCall(1): [DestructorCall] call to ~Middle
# 840| Type = [VoidType] void
# 840| ValueCategory = prvalue
# 840| getQualifier(): [VariableAccess] m
# 840| Type = [Struct] Middle
# 840| ValueCategory = lvalue
# 840| getImplicitDestructorCall(2): [DestructorCall] call to ~Base
# 840| Type = [VoidType] void
# 840| ValueCategory = prvalue
# 840| getQualifier(): [VariableAccess] b
# 840| Type = [Struct,VirtualBaseClass] Base
# 840| ValueCategory = lvalue
# 842| [CopyAssignmentOperator] PolymorphicBase& PolymorphicBase::operator=(PolymorphicBase const&)
# 842| <params>:
#-----| getParameter(0): [Parameter] (unnamed parameter 0)
@@ -7475,6 +7517,18 @@ ir.cpp:
# 864| Type = [PointerType] const void *
# 864| ValueCategory = prvalue
# 865| getStmt(10): [ReturnStmt] return ...
# 865| getImplicitDestructorCall(0): [DestructorCall] call to ~PolymorphicDerived
# 865| Type = [VoidType] void
# 865| ValueCategory = prvalue
# 865| getQualifier(): [VariableAccess] d
# 865| Type = [Struct] PolymorphicDerived
# 865| ValueCategory = lvalue
# 865| getImplicitDestructorCall(1): [DestructorCall] call to ~PolymorphicBase
# 865| Type = [VoidType] void
# 865| ValueCategory = prvalue
# 865| getQualifier(): [VariableAccess] b
# 865| Type = [Struct] PolymorphicBase
# 865| ValueCategory = lvalue
# 867| [Constructor] void String::String()
# 867| <params>:
# 867| <initializations>:
@@ -8954,6 +9008,18 @@ ir.cpp:
# 1055| Value = [CStyleCast] 6.0
# 1055| ValueCategory = prvalue
# 1056| getStmt(15): [ReturnStmt] return ...
# 1056| getImplicitDestructorCall(0): [DestructorCall] call to ~<unnamed>
# 1056| Type = [VoidType] void
# 1056| ValueCategory = prvalue
# 1056| getQualifier(): [VariableAccess] lambda_val_explicit
# 1056| Type = [Closure,LocalClass] decltype([...](...){...})
# 1056| ValueCategory = lvalue
# 1056| getImplicitDestructorCall(1): [DestructorCall] call to ~<unnamed>
# 1056| Type = [VoidType] void
# 1056| ValueCategory = prvalue
# 1056| getQualifier(): [VariableAccess] lambda_val
# 1056| Type = [Closure,LocalClass] decltype([...](...){...})
# 1056| ValueCategory = lvalue
# 1041| [CopyAssignmentOperator] (void Lambda(int, String const&))::(lambda [] type at line 1041, col. 23)& (void Lambda(int, String const&))::(lambda [] type at line 1041, col. 23)::operator=((void Lambda(int, String const&))::(lambda [] type at line 1041, col. 23) const&)
# 1041| <params>:
#-----| getParameter(0): [Parameter] (unnamed parameter 0)
@@ -10149,6 +10215,24 @@ ir.cpp:
# 1243| Type = [PointerType] const char *
# 1243| ValueCategory = prvalue(load)
# 1244| getStmt(3): [ReturnStmt] return ...
# 1244| getImplicitDestructorCall(0): [DestructorCall] call to ~String
# 1244| Type = [VoidType] void
# 1244| ValueCategory = prvalue
# 1244| getQualifier(): [VariableAccess] c
# 1244| Type = [Struct] String
# 1244| ValueCategory = lvalue
# 1244| getImplicitDestructorCall(1): [DestructorCall] call to ~String
# 1244| Type = [VoidType] void
# 1244| ValueCategory = prvalue
# 1244| getQualifier(): [VariableAccess] b
# 1244| Type = [Struct] String
# 1244| ValueCategory = lvalue
# 1244| getImplicitDestructorCall(2): [DestructorCall] call to ~String
# 1244| Type = [VoidType] void
# 1244| ValueCategory = prvalue
# 1244| getQualifier(): [VariableAccess] a
# 1244| Type = [Struct] String
# 1244| ValueCategory = lvalue
# 1248| [TopLevelFunction] char* strcpy(char*, char const*)
# 1248| <params>:
# 1248| getParameter(0): [Parameter] destination
@@ -10403,6 +10487,12 @@ ir.cpp:
# 1286| Type = [PointerType] A *
# 1286| ValueCategory = prvalue
# 1287| getStmt(12): [ReturnStmt] return ...
# 1287| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 1287| Type = [VoidType] void
# 1287| ValueCategory = prvalue
# 1287| getQualifier(): [VariableAccess] c
# 1287| Type = [Class] C
# 1287| ValueCategory = lvalue
# 1289| [TopLevelFunction] int missingReturnValue(bool, int)
# 1289| <params>:
# 1289| getParameter(0): [Parameter] b
@@ -10957,6 +11047,12 @@ ir.cpp:
# 1376| Type = [Struct] String
# 1376| ValueCategory = prvalue
# 1377| getStmt(9): [ReturnStmt] return ...
# 1377| getImplicitDestructorCall(0): [DestructorCall] call to ~String
# 1377| Type = [VoidType] void
# 1377| ValueCategory = prvalue
# 1377| getQualifier(): [VariableAccess] s
# 1377| Type = [Struct] String
# 1377| ValueCategory = lvalue
# 1379| [TopLevelFunction] void temporary_destructor_only()
# 1379| <params>:
# 1379| getEntryPoint(): [BlockStmt] { ... }
@@ -11040,6 +11136,18 @@ ir.cpp:
# 1388| Type = [Class] destructor_only
# 1388| ValueCategory = prvalue
# 1389| getStmt(8): [ReturnStmt] return ...
# 1389| getImplicitDestructorCall(0): [DestructorCall] call to ~destructor_only
# 1389| Type = [VoidType] void
# 1389| ValueCategory = prvalue
# 1389| getQualifier(): [VariableAccess] d2
# 1389| Type = [Class] destructor_only
# 1389| ValueCategory = lvalue
# 1389| getImplicitDestructorCall(1): [DestructorCall] call to ~destructor_only
# 1389| Type = [VoidType] void
# 1389| ValueCategory = prvalue
# 1389| getQualifier(): [VariableAccess] d
# 1389| Type = [Class] destructor_only
# 1389| ValueCategory = lvalue
# 1391| [TopLevelFunction] void temporary_copy_constructor()
# 1391| <params>:
# 1391| getEntryPoint(): [BlockStmt] { ... }
@@ -14696,6 +14804,12 @@ ir.cpp:
# 1925| Value = [Literal] 10
# 1925| ValueCategory = prvalue
# 1926| getStmt(7): [ReturnStmt] return ...
# 1926| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 1926| Type = [VoidType] void
# 1926| ValueCategory = prvalue
# 1926| getQualifier(): [VariableAccess] c
# 1926| Type = [Class] C
# 1926| ValueCategory = lvalue
# 1928| [TopLevelFunction] void test_double_assign()
# 1928| <params>:
# 1928| getEntryPoint(): [BlockStmt] { ... }
@@ -15048,6 +15162,12 @@ ir.cpp:
# 1993| Type = [Class] C
# 1993| ValueCategory = lvalue
# 1994| getStmt(3): [ReturnStmt] return ...
# 1994| getImplicitDestructorCall(0): [DestructorCall] call to ~C
# 1994| Type = [VoidType] void
# 1994| ValueCategory = prvalue
# 1994| getQualifier(): [VariableAccess] c
# 1994| Type = [Class] C
# 1994| ValueCategory = lvalue
# 1996| [TopLevelFunction] void TernaryTestInt(bool, int, int, int)
# 1996| <params>:
# 1996| getParameter(0): [Parameter] a
@@ -16062,6 +16182,12 @@ smart_ptr.cpp:
# 12| Type = [CTypedefType,NestedTypedefType] type
# 12| ValueCategory = prvalue(load)
# 13| getStmt(2): [ReturnStmt] return ...
# 13| getImplicitDestructorCall(0): [DestructorCall] call to ~unique_ptr
# 13| Type = [VoidType] void
# 13| ValueCategory = prvalue
# 13| getQualifier(): [VariableAccess] up
# 13| Type = [ClassTemplateInstantiation] unique_ptr<int, default_delete<int>>
# 13| ValueCategory = lvalue
# 15| [TopLevelFunction] void shared_ptr_arg(std::shared_ptr<float>)
# 15| <params>:
# 15| getParameter(0): [Parameter] sp
@@ -16102,6 +16228,12 @@ smart_ptr.cpp:
# 19| Type = [ClassTemplateInstantiation] shared_ptr<float>
# 19| ValueCategory = lvalue
# 20| getStmt(2): [ReturnStmt] return ...
# 20| getImplicitDestructorCall(0): [DestructorCall] call to ~shared_ptr
# 20| Type = [VoidType] void
# 20| ValueCategory = prvalue
# 20| getQualifier(): [VariableAccess] sp
# 20| Type = [ClassTemplateInstantiation] shared_ptr<float>
# 20| ValueCategory = lvalue
# 22| [TopLevelFunction] void shared_ptr_const_int(std::shared_ptr<int const>)
# 22| <params>:
# 22| getParameter(0): [Parameter] (unnamed parameter 0)
@@ -16241,6 +16373,36 @@ smart_ptr.cpp:
# 47| Type = [ClassTemplateInstantiation] shared_ptr<const shared_ptr<const int>>
# 47| ValueCategory = lvalue
# 48| getStmt(10): [ReturnStmt] return ...
# 48| getImplicitDestructorCall(0): [DestructorCall] call to ~shared_ptr
# 48| Type = [VoidType] void
# 48| ValueCategory = prvalue
# 48| getQualifier(): [VariableAccess] sp_const_sp_const_int
# 48| Type = [ClassTemplateInstantiation] shared_ptr<const shared_ptr<const int>>
# 48| ValueCategory = lvalue
# 48| getImplicitDestructorCall(1): [DestructorCall] call to ~shared_ptr
# 48| Type = [VoidType] void
# 48| ValueCategory = prvalue
# 48| getQualifier(): [VariableAccess] sp_const_sp_int
# 48| Type = [ClassTemplateInstantiation] shared_ptr<const shared_ptr<int>>
# 48| ValueCategory = lvalue
# 48| getImplicitDestructorCall(2): [DestructorCall] call to ~shared_ptr
# 48| Type = [VoidType] void
# 48| ValueCategory = prvalue
# 48| getQualifier(): [VariableAccess] sp_sp_const_int
# 48| Type = [ClassTemplateInstantiation] shared_ptr<shared_ptr<const int>>
# 48| ValueCategory = lvalue
# 48| getImplicitDestructorCall(3): [DestructorCall] call to ~shared_ptr
# 48| Type = [VoidType] void
# 48| ValueCategory = prvalue
# 48| getQualifier(): [VariableAccess] sp_const_int_pointer
# 48| Type = [ClassTemplateInstantiation] shared_ptr<int *const>
# 48| ValueCategory = lvalue
# 48| getImplicitDestructorCall(4): [DestructorCall] call to ~shared_ptr
# 48| Type = [VoidType] void
# 48| ValueCategory = prvalue
# 48| getQualifier(): [VariableAccess] sp_const_int
# 48| Type = [ClassTemplateInstantiation] shared_ptr<const int>
# 48| ValueCategory = lvalue
struct_init.cpp:
# 1| [TopLevelFunction] int handler1(void*)
# 1| <params>: