mirror of
https://github.com/github/codeql.git
synced 2026-05-24 08:07:07 +02:00
C++: Add support for alias templates
Add other missing cases to `isFromTemplateInstantiationRec` and `isFromUninstantiatedTemplateRec` while here.
This commit is contained in:
@@ -278,6 +278,8 @@ class Declaration extends Locatable, @declaration {
|
||||
or
|
||||
variable_template_argument(underlyingElement(this), index, unresolveElement(result))
|
||||
or
|
||||
alias_template_argument(underlyingElement(this), index, unresolveElement(result))
|
||||
or
|
||||
template_template_argument(underlyingElement(this), index, unresolveElement(result))
|
||||
or
|
||||
concept_template_argument(underlyingElement(this), index, unresolveElement(result))
|
||||
@@ -290,6 +292,8 @@ class Declaration extends Locatable, @declaration {
|
||||
or
|
||||
variable_template_argument_value(underlyingElement(this), index, unresolveElement(result))
|
||||
or
|
||||
alias_template_argument_value(underlyingElement(this), index, unresolveElement(result))
|
||||
or
|
||||
template_template_argument_value(underlyingElement(this), index, unresolveElement(result))
|
||||
or
|
||||
concept_template_argument_value(underlyingElement(this), index, unresolveElement(result))
|
||||
|
||||
@@ -278,6 +278,15 @@ private predicate isFromTemplateInstantiationRec(Element e, Element instantiatio
|
||||
instantiation.(Variable).isConstructedFrom(_) and
|
||||
e = instantiation
|
||||
or
|
||||
instantiation.(UsingAliasTypedefType).isConstructedFrom(_) and
|
||||
e = instantiation
|
||||
or
|
||||
instantiation.(TemplateTemplateParameterInstantiation).isConstructedFrom(_) and
|
||||
e = instantiation
|
||||
or
|
||||
exists(instantiation.(ConceptIdExpr).getConcept()) and
|
||||
e = instantiation
|
||||
or
|
||||
isFromTemplateInstantiationRec(e.getEnclosingElement(), instantiation)
|
||||
}
|
||||
|
||||
@@ -291,6 +300,15 @@ private predicate isFromUninstantiatedTemplateRec(Element e, Element template) {
|
||||
is_variable_template(unresolveElement(template)) and
|
||||
e = template
|
||||
or
|
||||
is_alias_template(unresolveElement(template)) and
|
||||
e = template
|
||||
or
|
||||
usertypes(unresolveElement(template), _, 8) and // template template parameter
|
||||
e = template
|
||||
or
|
||||
template instanceof @concept_template and
|
||||
e = template
|
||||
or
|
||||
isFromUninstantiatedTemplateRec(e.getEnclosingElement(), template)
|
||||
}
|
||||
|
||||
|
||||
@@ -64,7 +64,8 @@ class CTypedefType extends TypedefType {
|
||||
}
|
||||
|
||||
/**
|
||||
* A using alias C++ typedef type. For example the type declared in the following code:
|
||||
* A C++ type alias or alias template. For example the type declared in the following
|
||||
* code:
|
||||
* ```
|
||||
* using my_int2 = int;
|
||||
* ```
|
||||
@@ -77,6 +78,66 @@ class UsingAliasTypedefType extends TypedefType {
|
||||
override string explain() {
|
||||
result = "using {" + this.getBaseType().explain() + "} as \"" + this.getName() + "\""
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if this alias is constructed from another alias as a result of
|
||||
* template instantiation.
|
||||
*/
|
||||
predicate isConstructedFrom(UsingAliasTypedefType t) {
|
||||
alias_instantiation(underlyingElement(this), unresolveElement(t))
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* A C++ alias template. For example the type declared in the following code:
|
||||
* ```
|
||||
* template <typename T>
|
||||
* using my_type = T;
|
||||
* ```
|
||||
*/
|
||||
class AliasTemplateTypedefType extends TypedefType {
|
||||
AliasTemplateTypedefType() { is_alias_template(underlyingElement(this)) }
|
||||
|
||||
override string getAPrimaryQlClass() { result = "AliasTemplateTypedefType" }
|
||||
|
||||
/**
|
||||
* Gets a alias instantiated from this template.
|
||||
*
|
||||
* For example for `MyAliasTemplate<T>` in the following code, the results are
|
||||
* `MyAliasTemplate<int>` and `MyAliasTemplate<long>`:
|
||||
* ```
|
||||
* template<typename T>
|
||||
* using MyAliasTemplate = ;
|
||||
*
|
||||
* MyAliasTemplate<int> instance1;
|
||||
*
|
||||
* MyAliasTemplate<long> instance2;
|
||||
* ```
|
||||
*/
|
||||
UsingAliasTypedefType getAnInstantiation() { result.isConstructedFrom(this) }
|
||||
}
|
||||
|
||||
/**
|
||||
* A C++ alias template instantiation. For example the `my_int_type` type declared in
|
||||
* the following code:
|
||||
* ```
|
||||
* template <typename T>
|
||||
* using my_type = T;
|
||||
*
|
||||
* using my_int_type = my_type<int>;
|
||||
* ```
|
||||
*/
|
||||
class AliasTemplateInstantiationTypedefType extends UsingAliasTypedefType {
|
||||
AliasTemplateTypedefType ta;
|
||||
|
||||
AliasTemplateInstantiationTypedefType() { ta.getAnInstantiation() = this }
|
||||
|
||||
override string getAPrimaryQlClass() { result = "AliasTemplateInstantiationTypedefType" }
|
||||
|
||||
/**
|
||||
* Gets the alias template from which this instantiation was instantiated.
|
||||
*/
|
||||
AliasTemplateTypedefType getTemplate() { result = ta }
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -960,6 +960,22 @@ variable_template_argument_value(
|
||||
int arg_value: @expr ref
|
||||
);
|
||||
|
||||
is_alias_template(unique int id: @usertype ref);
|
||||
alias_instantiation(
|
||||
unique int to: @usertype ref,
|
||||
int from: @usertype ref
|
||||
);
|
||||
alias_template_argument(
|
||||
int variable_id: @usertype ref,
|
||||
int index: int ref,
|
||||
int arg_type: @type ref
|
||||
);
|
||||
alias_template_argument_value(
|
||||
int variable_id: @usertype ref,
|
||||
int index: int ref,
|
||||
int arg_value: @expr ref
|
||||
);
|
||||
|
||||
template_template_instantiation(
|
||||
int to: @usertype ref,
|
||||
int from: @usertype ref
|
||||
|
||||
Reference in New Issue
Block a user