A typedef defined with extern "C" prevents CodeQL from finding the TypdefType of a C++ member function's FunctionDeclarationEntry
- Lenguaje dominante
- CodeQL
- Estrellas
- 10.1k
- Forks
- 2.1k
- Merge medio
- 2 d 15 h
- PR fusionados (30 d)
- 141
Descripción
**Description of the issue**
If a C++ class member function is declared with a typedef that was defined with "extern "C" ", CodeQL will not return any result for the TypedefType of the FunctionDeclarationEntry for that function when using [getTypedefType()](https://codeql.github.com/codeql-standard-libraries/cpp/semmle/code/cpp/Function.qll/predicate.Function$FunctionDeclarationEntry$getTypedefType.0.html)
**Example**
Query:
```
import cpp
from FunctionDeclarationEntry fde, Class c
where fde.getFunction() = c.getAMemberFunction()
select fde,
"class $@, FDE $@, TypdefType $@ ",c, c.toString(), fde, fde.toString(), fde.getTypedefType(), fde.getTypedefType().toString()
```
Code:
test.h
```
#pragma once
//
// extern
extern "C"
{
typedef VOID
TYPEDEF_TEST1(
_In_ int i);
typedef TYPEDEF_TEST1 *ITEM1;
}
// global namespace
typedef VOID TYPEDEF_TEST2(
_In_ int i);
typedef TYPEDEF_TEST2 *ITEM2;
// some other namespace
namespace SomeOtherNamespace
{
typedef VOID TYPEDEF_TEST3(
_In_ int i);
typedef TYPEDEF_TEST3 *ITEM3;
}
class SomeClass
{
public:
NTSTATUS Init();
//=====================================================================
// Default CUnknown
static TYPEDEF_TEST1 typedefFunction; // This typedef is NOT found
static TYPEDEF_TEST2 typedefFunction2; // This typedef is found
};
namespace SomeOtherNamespace
{
class SomeClassSomeOtherNamespace
{
public:
NTSTATUS Init();
//=====================================================================
// Default CUnknown
static TYPEDEF_TEST1 typedefFunction3; // This typedef is NOT found
static TYPEDEF_TEST2 typedefFunction4; // This typedef is found
static TYPEDEF_TEST3 typedefFunction5; // This typedef is found
};
}
#pragma code_seg()
VOID SomeClass::typedefFunction(
_In_ int i)
{
i = NULL;
}
#pragma code_seg()
VOID SomeClass::typedefFunction2(
_In_ int i)
{
i = NULL;
}
namespace SomeOtherNamespace
{
#pragma code_seg()
VOID SomeClassSomeOtherNamespace::typedefFunction3(
_In_ int i)
{
i = NULL;
}
#pragma code_seg()
VOID SomeClassSomeOtherNamespace::typedefFunction4(
_In_ int i)
{
i = NULL;
}
#pragma code_seg()
VOID SomeClassSomeOtherNamespace::typedefFunction5(
_In_ int i)
{
i = NULL;
}
} // namespace SomeOtherNamespace
```
CodeQL can find just the TypedefTypes. The following query has results for each of the three typedefs:
```
import cpp
from TypedefType t
where
t.getName().matches("TYPEDEF_TEST1") or
t.getName().matches("TYPEDEF_TEST2") or
t.getName().matches("TYPEDEF_TEST3")
select t,
t.toString()
```
And can find just the FunctionDeclarationEntry. The following query has results for each of the functions:
```
import cpp
from FunctionDeclarationEntry fde
where
fde.getName().matches("typedefFunction") or
fde.getName().matches("typedefFunction2") or
fde.getName().matches("typedefFunction3") or
fde.getName().matches("typedefFunction4") or
fde.getName().matches("typedefFunction5")
select fde,
fde.toString()
```
However, it fails to find the TypedefType of the FunctionDeclarationEntry of typedefFunction and typedefFunction3 which are declared with TYPEDEF_TEST1. The results for the following query only produces TYPEDEF_TEST2 and TYPEDEF_TEST3
```
import cpp
from FunctionDeclarationEntry fde
where
fde.getName().matches("typedefFunction") or
fde.getName().matches("typedefFunction2") or
fde.getName().matches("typedefFunction3") or
fde.getName().matches("typedefFunction4") or
fde.getName().matches("typedefFunction5")
select fde,
fde.getTypedefType().toString()
```
Guía de contribución
Evaluación
Este issue todavía no se ha evaluado.