Skip to content

Commit 75f77b5

Browse files
authored
Merge pull request #1532 from zlaski-semmle/zlaski/cpp386
[CPP-386] Add `getCanonicalQLClass()` for AST QL elements.
2 parents 8140b68 + e989eab commit 75f77b5

36 files changed

+7801
-6732
lines changed

cpp/ql/src/semmle/code/cpp/Class.qll

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ class Class extends UserType {
1515
isClass(underlyingElement(this))
1616
}
1717

18+
override string getCanonicalQLClass() { result = "Class" }
19+
1820
/** Gets a child declaration of this class. */
1921
override Declaration getADeclaration() { result = this.getAMember() }
2022

@@ -822,6 +824,9 @@ class LocalClass extends Class {
822824
isLocal()
823825
}
824826

827+
override string getCanonicalQLClass()
828+
{ not this instanceof LocalStruct and result = "LocalClass" }
829+
825830
override Function getEnclosingAccessHolder() {
826831
result = this.getEnclosingFunction()
827832
}
@@ -835,6 +840,9 @@ class NestedClass extends Class {
835840
this.isMember()
836841
}
837842

843+
override string getCanonicalQLClass()
844+
{ not this instanceof NestedStruct and result = "NestedClass" }
845+
838846
/** Holds if this member is private. */
839847
predicate isPrivate() { this.hasSpecifier("private") }
840848

@@ -854,6 +862,8 @@ class AbstractClass extends Class {
854862
AbstractClass() {
855863
exists(PureVirtualFunction f| this.getAMemberFunction() = f)
856864
}
865+
866+
override string getCanonicalQLClass() { result = "AbstractClass" }
857867
}
858868

859869
/**
@@ -866,6 +876,8 @@ class TemplateClass extends Class {
866876
result.isConstructedFrom(this) and
867877
exists(result.getATemplateArgument())
868878
}
879+
880+
override string getCanonicalQLClass() { result = "TemplateClass" }
869881
}
870882

871883
/**
@@ -878,6 +890,8 @@ class ClassTemplateInstantiation extends Class {
878890
tc.getAnInstantiation() = this
879891
}
880892

893+
override string getCanonicalQLClass() { result = "ClassTemplateInstantiation" }
894+
881895
/**
882896
* Gets the class template from which this instantiation was instantiated.
883897
*
@@ -909,6 +923,8 @@ abstract class ClassTemplateSpecialization extends Class {
909923
and count(TemplateParameter tp | tp = result.getATemplateArgument()) =
910924
count(int i | exists(result.getTemplateArgument(i)))
911925
}
926+
927+
override string getCanonicalQLClass() { result = "ClassTemplateSpecialization" }
912928
}
913929

914930
/**
@@ -926,6 +942,8 @@ class FullClassTemplateSpecialization extends ClassTemplateSpecialization {
926942
// This class is not an instantiation of a class template.
927943
and not this instanceof ClassTemplateInstantiation
928944
}
945+
946+
override string getCanonicalQLClass() { result = "FullClassTemplateSpecialization" }
929947
}
930948

931949
/**
@@ -950,6 +968,8 @@ class PartialClassTemplateSpecialization extends ClassTemplateSpecialization {
950968
and count(TemplateParameter tp | tp = getATemplateArgument()) !=
951969
count(int i | exists(getTemplateArgument(i)))
952970
}
971+
972+
override string getCanonicalQLClass() { result = "PartialClassTemplateSpecialization" }
953973
}
954974

955975
/**
@@ -960,6 +980,8 @@ class Interface extends Class {
960980
Interface() {
961981
forex(Declaration m | m.getDeclaringType() = this.getABaseClass*() and not compgenerated(unresolveElement(m)) | m instanceof PureVirtualFunction)
962982
}
983+
984+
override string getCanonicalQLClass() { result = "Interface" }
963985
}
964986

965987
/**
@@ -970,6 +992,8 @@ class VirtualClassDerivation extends ClassDerivation {
970992
VirtualClassDerivation() {
971993
hasSpecifier("virtual")
972994
}
995+
996+
override string getCanonicalQLClass() { result = "VirtualClassDerivation" }
973997
}
974998

975999
/**
@@ -980,6 +1004,8 @@ class VirtualBaseClass extends Class {
9801004
exists(VirtualClassDerivation cd | cd.getBaseClass() = this)
9811005
}
9821006

1007+
override string getCanonicalQLClass() { result = "VirtualBaseClass" }
1008+
9831009
/** A virtual class derivation of which this class is the base. */
9841010
VirtualClassDerivation getAVirtualDerivation() {
9851011
result.getBaseClass() = this
@@ -1004,6 +1030,8 @@ class ProxyClass extends UserType {
10041030
usertypes(underlyingElement(this),_,9)
10051031
}
10061032

1033+
override string getCanonicalQLClass() { result = "ProxyClass" }
1034+
10071035
/** Gets the location of the proxy class. */
10081036
override Location getLocation() {
10091037
result = getTemplateParameter().getDefinitionLocation()

cpp/ql/src/semmle/code/cpp/Element.qll

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,13 @@ pragma[inline]
5252
class ElementBase extends @element {
5353
/** Gets a textual representation of this element. */
5454
string toString() { none() }
55+
56+
/**
57+
* Canonical QL class corresponding to this element.
58+
*
59+
* ElementBase is the root class for this predicate.
60+
*/
61+
string getCanonicalQLClass() { result = "???" }
5562
}
5663

5764
/**

cpp/ql/src/semmle/code/cpp/Enum.qll

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@ class Enum extends UserType, IntegralOrEnumType {
99
EnumConstant getAnEnumConstant() { result.getDeclaringEnum() = this }
1010
EnumConstant getEnumConstant(int index) { enumconstants(unresolveElement(result),underlyingElement(this),index,_,_,_) }
1111

12+
override string getCanonicalQLClass() { result = "Enum" }
13+
1214
/**
1315
* Gets a descriptive string for the enum. This method is only intended to
1416
* be used for debugging purposes. For more information, see the comment
@@ -50,6 +52,8 @@ class LocalEnum extends Enum {
5052
LocalEnum() {
5153
isLocal()
5254
}
55+
56+
override string getCanonicalQLClass() { result = "LocalEnum" }
5357
}
5458

5559
/**
@@ -61,6 +65,8 @@ class NestedEnum extends Enum {
6165
this.isMember()
6266
}
6367

68+
override string getCanonicalQLClass() { result = "NestedEnum" }
69+
6470
/** Holds if this member is private. */
6571
predicate isPrivate() { this.hasSpecifier("private") }
6672

@@ -81,6 +87,8 @@ class ScopedEnum extends Enum {
8187
ScopedEnum() {
8288
usertypes(underlyingElement(this),_,13)
8389
}
90+
91+
override string getCanonicalQLClass() { result = "ScopedEnum" }
8492
}
8593

8694
/**
@@ -96,6 +104,8 @@ class EnumConstant extends Declaration, @enumconstant {
96104
*/
97105
Enum getDeclaringEnum() { enumconstants(underlyingElement(this),unresolveElement(result),_,_,_,_) }
98106

107+
override string getCanonicalQLClass() { result = "EnumConstant" }
108+
99109
override Class getDeclaringType() {
100110
result = this.getDeclaringEnum().getDeclaringType()
101111
}

cpp/ql/src/semmle/code/cpp/Function.qll

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -503,6 +503,8 @@ class FunctionDeclarationEntry extends DeclarationEntry, @fun_decl {
503503
/** Gets the function which is being declared or defined. */
504504
override Function getDeclaration() { result = getFunction() }
505505

506+
override string getCanonicalQLClass() { result = "FunctionDeclarationEntry" }
507+
506508
/** Gets the function which is being declared or defined. */
507509
Function getFunction() { fun_decls(underlyingElement(this),unresolveElement(result),_,_,_) }
508510

@@ -707,6 +709,8 @@ class TopLevelFunction extends Function {
707709
TopLevelFunction() {
708710
not this.isMember()
709711
}
712+
713+
override string getCanonicalQLClass() { result = "TopLevelFunction" }
710714
}
711715

712716
/**
@@ -718,6 +722,11 @@ class MemberFunction extends Function {
718722
this.isMember()
719723
}
720724

725+
override string getCanonicalQLClass()
726+
{ not this instanceof CopyAssignmentOperator and
727+
not this instanceof MoveAssignmentOperator and
728+
result = "MemberFunction" }
729+
721730
/**
722731
* Gets the number of parameters of this function, including any implicit
723732
* `this` parameter.
@@ -769,6 +778,8 @@ class VirtualFunction extends MemberFunction {
769778
this.hasSpecifier("virtual") or purefunctions(underlyingElement(this))
770779
}
771780

781+
override string getCanonicalQLClass() { result = "VirtualFunction" }
782+
772783
/** Holds if this virtual function is pure. */
773784
predicate isPure() { this instanceof PureVirtualFunction }
774785

@@ -786,6 +797,7 @@ class PureVirtualFunction extends VirtualFunction {
786797

787798
PureVirtualFunction() { purefunctions(underlyingElement(this)) }
788799

800+
override string getCanonicalQLClass() { result = "PureVirtualFunction" }
789801
}
790802

791803
/**
@@ -797,6 +809,7 @@ class ConstMemberFunction extends MemberFunction {
797809

798810
ConstMemberFunction() { this.hasSpecifier("const") }
799811

812+
override string getCanonicalQLClass() { result = "ConstMemberFunction" }
800813
}
801814

802815
/**
@@ -806,6 +819,8 @@ class Constructor extends MemberFunction {
806819

807820
Constructor() { functions(underlyingElement(this),_,2) }
808821

822+
override string getCanonicalQLClass() { result = "Constructor" }
823+
809824
/**
810825
* Holds if this constructor serves as a default constructor.
811826
*
@@ -851,6 +866,9 @@ class ConversionConstructor extends Constructor, ImplicitConversionFunction {
851866
and not(this instanceof CopyConstructor)
852867
}
853868

869+
override string getCanonicalQLClass()
870+
{ not this instanceof MoveConstructor and result = "ConversionConstructor" }
871+
854872
/** Gets the type this `ConversionConstructor` takes as input. */
855873
override Type getSourceType() { result = this.getParameter(0).getType() }
856874

@@ -906,6 +924,8 @@ class CopyConstructor extends Constructor {
906924
not exists(getATemplateArgument())
907925
}
908926

927+
override string getCanonicalQLClass() { result = "CopyConstructor" }
928+
909929
/**
910930
* Holds if we cannot determine that this constructor will become a copy
911931
* constructor in all instantiations. Depending on template parameters of the
@@ -954,6 +974,8 @@ class MoveConstructor extends Constructor {
954974
not exists(getATemplateArgument())
955975
}
956976

977+
override string getCanonicalQLClass() { result = "MoveConstructor" }
978+
957979
/**
958980
* Holds if we cannot determine that this constructor will become a move
959981
* constructor in all instantiations. Depending on template parameters of the
@@ -986,6 +1008,8 @@ class NoArgConstructor extends Constructor {
9861008
class Destructor extends MemberFunction {
9871009
Destructor() { functions(underlyingElement(this),_,3) }
9881010

1011+
override string getCanonicalQLClass() { result = "Destructor" }
1012+
9891013
/**
9901014
* Gets a compiler-generated action which destructs a base class or member
9911015
* variable.
@@ -1011,6 +1035,8 @@ class ConversionOperator extends MemberFunction, ImplicitConversionFunction {
10111035

10121036
ConversionOperator() { functions(underlyingElement(this),_,4) }
10131037

1038+
override string getCanonicalQLClass() { result = "ConversionOperator" }
1039+
10141040
override Type getSourceType() { result = this.getDeclaringType() }
10151041
override Type getDestType() { result = this.getType() }
10161042

@@ -1023,6 +1049,8 @@ class Operator extends Function {
10231049

10241050
Operator() { functions(underlyingElement(this),_,5) }
10251051

1052+
override string getCanonicalQLClass()
1053+
{ not this instanceof MemberFunction and result = "Operator" }
10261054
}
10271055

10281056
/**
@@ -1045,6 +1073,8 @@ class CopyAssignmentOperator extends Operator {
10451073
not exists(this.getParameter(1)) and
10461074
not exists(getATemplateArgument())
10471075
}
1076+
1077+
override string getCanonicalQLClass() { result = "CopyAssignmentOperator" }
10481078
}
10491079

10501080

@@ -1064,6 +1094,8 @@ class MoveAssignmentOperator extends Operator {
10641094
not exists(this.getParameter(1)) and
10651095
not exists(getATemplateArgument())
10661096
}
1097+
1098+
override string getCanonicalQLClass() { result = "MoveAssignmentOperator" }
10671099
}
10681100

10691101

@@ -1084,6 +1116,7 @@ class MoveAssignmentOperator extends Operator {
10841116
class TemplateFunction extends Function {
10851117
TemplateFunction() { is_function_template(underlyingElement(this)) and exists(getATemplateArgument()) }
10861118

1119+
override string getCanonicalQLClass() { result = "TemplateFunction" }
10871120
/**
10881121
* Gets a compiler-generated instantiation of this function template.
10891122
*/
@@ -1115,6 +1148,8 @@ class FunctionTemplateInstantiation extends Function {
11151148
tf.getAnInstantiation() = this
11161149
}
11171150

1151+
override string getCanonicalQLClass() { result = "FunctionTemplateInstantiation" }
1152+
11181153
/**
11191154
* Gets the function template from which this instantiation was instantiated.
11201155
*
@@ -1151,6 +1186,8 @@ class FunctionTemplateSpecialization extends Function {
11511186
this.isSpecialization()
11521187
}
11531188

1189+
override string getCanonicalQLClass() { result = "FunctionTemplateSpecialization" }
1190+
11541191
/**
11551192
* Gets the primary template for the specialization (the function template
11561193
* this specializes).

cpp/ql/src/semmle/code/cpp/Initializer.qll

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@ import semmle.code.cpp.controlflow.ControlFlowGraph
66
class Initializer extends ControlFlowNode, @initialiser {
77
override Location getLocation() { initialisers(underlyingElement(this),_,_,result) }
88

9+
override string getCanonicalQLClass() { result = "Initializer" }
10+
911
/** Holds if this initializer is explicit in the source. */
1012
override predicate fromSource() {
1113
not (this.getLocation() instanceof UnknownLocation)

cpp/ql/src/semmle/code/cpp/Macro.qll

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@ class Macro extends PreprocessorDirective, @ppd_define {
1111
*/
1212
override string getHead() { preproctext(underlyingElement(this),result,_) }
1313

14+
override string getCanonicalQLClass() { result = "Macro" }
15+
1416
/**
1517
* Gets the body of this macro. For example, `(((x)>(y))?(x):(y))` in
1618
* `#define MAX(x,y) (((x)>(y))?(x):(y))`.

cpp/ql/src/semmle/code/cpp/Parameter.qll

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,8 @@ class Parameter extends LocalScopeVariable, @parameter {
3333
result = "p#" + this.getIndex().toString())
3434
}
3535

36+
override string getCanonicalQLClass() { result = "Parameter" }
37+
3638
/**
3739
* Gets the name of this parameter, including it's type.
3840
*

0 commit comments

Comments
 (0)