Repository: joernio/joern (scala)

Issue:
(C/C++) Joern recognizes "LOCAL" node of a struct statement as a "TYPE_DECL" node
```C++
struct R
{
    int a;
} r;

struct R s;
```

The node "r" and "s" should be of "LOCAL" type, but in fact, "s" is while "r" isn't.

Here is the AST dot file:
```dot
digraph "&lt;global&gt;" {  
"5" [label = <(METHOD,&lt;global&gt;)<SUB>30</SUB>> ]
"6" [label = <(BLOCK,&lt;empty&gt;,&lt;empty&gt;)> ]
"7" [label = <> ]
"8" [label = <<SUB>32</SUB>> ]
"9" [label = <<SUB>33</SUB>> ]
"10" [label = <> ]
"11" [label = <(LOCAL,struct R s: R)<SUB>35</SUB>> ]
"12" [label = <(METHOD,main)<SUB>37</SUB>> ]
"13" [label = <(BLOCK,&lt;empty&gt;,&lt;empty&gt;)<SUB>38</SUB>> ]
"14" [label = <(RETURN,return 0;,return 0;)<SUB>39</SUB>> ]
"15" [label = <(LITERAL,0,return 0;)<SUB>39</SUB>> ]
"16" [label = <(METHOD_RETURN,int)<SUB>37</SUB>> ]
"18" [label = <(METHOD_RETURN,ANY)> ]
  "5" -> "6" 
  "5" -> "18" 
  "6" -> "7" 
  "6" -> "9" 
  "6" -> "10" 
  "6" -> "11" 
  "6" -> "12" 
  "7" -> "8" 
  "12" -> "13" 
  "12" -> "16" 
  "13" -> "14" 
  "14" -> "15" 
}
```

The two nodes are:
```json
  "9": {
    "inheritsFromTypeFullName": [],
    "name": "r",
    "astParentFullName": "",
    "fullName": "r",
    "astParentType": "",
    "columnNumber": 3,
    "_label": "TYPE_DECL",
    "aliasTypeFullName": "R",
    "code": "struct R\n{\n    int a;\n} r;",
    "isExternal": false,
    "lineNumber": 33,
    "id": 9,
    "order": 2,
    "filename": "/root/workspace/slice/testcase1/tmpdir/a.c"
  },
  "11": {
    "dynamicTypeHintFullName": [],
    "name": "s",
    "typeFullName": "R",
    "columnNumber": 10,
    "order": 4,
    "_label": "LOCAL",
    "code": "struct R s",
    "lineNumber": 35,
    "id": 11
  },
```

Pull request:
Fixes: https://github.com/joernio/joern/issues/1357

Patch:
diff --git a/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstCreatorHelper.scala b/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstCreatorHelper.scala
index 21b77a9af1aa..353064522e09 100644
--- a/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstCreatorHelper.scala
+++ b/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstCreatorHelper.scala
@@ -131,8 +131,23 @@ trait AstCreatorHelper {
   }
 
   // Sadly, there is no predefined List / Enum of this within Eclipse CDT:
-  private val reservedTypeKeywords =
-    List("const", "static", "volatile", "restrict", "extern", "typedef", "inline", "constexpr", "auto", "virtual")
+  private val reservedTypeKeywords: List[String] =
+    List(
+      "const",
+      "static",
+      "volatile",
+      "restrict",
+      "extern",
+      "typedef",
+      "inline",
+      "constexpr",
+      "auto",
+      "virtual",
+      "enum",
+      "struct",
+      "interface",
+      "class"
+    )
 
   protected def cleanType(rawType: String, stripKeywords: Boolean = true): String = {
     val tpe =
@@ -170,8 +185,8 @@ trait AstCreatorHelper {
         val nodeType = ASTTypeUtil.getNodeType(node)
         val arr      = nodeType.substring(nodeType.indexOf("["), nodeType.indexOf("]") + 1)
         s"$tpe$arr"
-      case _: IASTIdExpression | _: IASTName | _: IASTArrayDeclarator =>
-        cleanType(ASTTypeUtil.getNodeType(node))
+      case _: IASTIdExpression | _: IASTName | _: IASTDeclarator =>
+        cleanType(ASTTypeUtil.getNodeType(node), stripKeywords)
       case s: IASTNamedTypeSpecifier =>
         cleanType(ASTStringUtil.getReturnTypeString(s, null), stripKeywords)
       case s: IASTCompositeTypeSpecifier =>
@@ -459,9 +474,15 @@ trait AstCreatorHelper {
       case s: IASTNamedTypeSpecifier if s.getParent.isInstanceOf[IASTSimpleDeclaration] =>
         val parentDecl = s.getParent.asInstanceOf[IASTSimpleDeclaration].getDeclarators.toList(index)
         pointersAsString(s, parentDecl, stripKeywords)
-      case s: IASTNamedTypeSpecifier     => ASTStringUtil.getSimpleName(s.getName)
+      case s: IASTNamedTypeSpecifier => ASTStringUtil.getSimpleName(s.getName)
+      case s: IASTCompositeTypeSpecifier if s.getParent.isInstanceOf[IASTSimpleDeclaration] =>
+        val parentDecl = s.getParent.asInstanceOf[IASTSimpleDeclaration].getDeclarators.toList(index)
+        pointersAsString(s, parentDecl, stripKeywords)
       case s: IASTCompositeTypeSpecifier => ASTStringUtil.getSimpleName(s.getName)
-      case s: IASTEnumerationSpecifier   => ASTStringUtil.getSimpleName(s.getName)
+      case s: IASTEnumerationSpecifier if s.getParent.isInstanceOf[IASTSimpleDeclaration] =>
+        val parentDecl = s.getParent.asInstanceOf[IASTSimpleDeclaration].getDeclarators.toList(index)
+        pointersAsString(s, parentDecl, stripKeywords)
+      case s: IASTEnumerationSpecifier => ASTStringUtil.getSimpleName(s.getName)
       case s: IASTElaboratedTypeSpecifier if s.getParent.isInstanceOf[IASTParameterDeclaration] =>
         val parentDecl = s.getParent.asInstanceOf[IASTParameterDeclaration].getDeclarator
         pointersAsString(s, parentDecl, stripKeywords)
diff --git a/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForFunctionsCreator.scala b/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForFunctionsCreator.scala
index e02fb9b8d888..4f80e069ffeb 100644
--- a/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForFunctionsCreator.scala
+++ b/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForFunctionsCreator.scala
@@ -227,14 +227,14 @@ trait AstForFunctionsCreator {
         (
           ASTStringUtil.getSimpleName(p.getDeclarator.getName),
           nodeSignature(p),
-          typeForDeclSpecifier(p.getDeclSpecifier),
+          cleanType(typeForDeclSpecifier(p.getDeclSpecifier)),
           false
         )
       case p: CPPASTParameterDeclaration =>
         (
           ASTStringUtil.getSimpleName(p.getDeclarator.getName),
           nodeSignature(p),
-          typeForDeclSpecifier(p.getDeclSpecifier),
+          cleanType(typeForDeclSpecifier(p.getDeclSpecifier)),
           p.getDeclarator.declaresParameterPack()
         )
       case s: IASTSimpleDeclaration =>
@@ -243,11 +243,11 @@ trait AstForFunctionsCreator {
             .map(n => ASTStringUtil.getSimpleName(n.getName))
             .getOrElse(uniqueName("parameter", "", "")._1),
           nodeSignature(s),
-          typeForDeclSpecifier(s),
+          cleanType(typeForDeclSpecifier(s)),
           false
         )
       case other =>
-        (nodeSignature(other), nodeSignature(other), typeForDeclSpecifier(other), false)
+        (nodeSignature(other), nodeSignature(other), cleanType(typeForDeclSpecifier(other)), false)
     }
 
     val parameterNode = NewMethodParameterIn()
diff --git a/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForTypesCreator.scala b/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForTypesCreator.scala
index 1e6e091ef5c1..d9051e392eba 100644
--- a/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForTypesCreator.scala
+++ b/joern-cli/frontends/c2cpg/src/main/scala/io/joern/c2cpg/astcreation/AstForTypesCreator.scala
@@ -20,9 +20,7 @@ trait AstForTypesCreator {
   }
 
   private def isTypeDef(decl: IASTSimpleDeclaration): Boolean =
-    nodeSignature(decl).startsWith("typedef") ||
-      decl.getDeclSpecifier.isInstanceOf[IASTCompositeTypeSpecifier] ||
-      decl.getDeclSpecifier.isInstanceOf[IASTEnumerationSpecifier]
+    nodeSignature(decl).startsWith("typedef")
 
   protected def templateParameters(e: IASTNode): Option[String] = {
     val templateDeclaration = e match {
@@ -91,50 +89,54 @@ trait AstForTypesCreator {
   }
 
   protected def astForDeclarator(declaration: IASTSimpleDeclaration, declarator: IASTDeclarator, index: Int): Ast = {
-    val declTypeName = registerType(typeForDeclSpecifier(declaration.getDeclSpecifier))
-    val tpe          = typeFor(declarator)
     val name         = ASTStringUtil.getSimpleName(declarator.getName)
     val lineNumber   = line(declarator)
     val columnNumber = column(declarator)
     declaration match {
       case d if isTypeDef(d) =>
         val filename = fileName(declaration)
+        val tpe      = registerType(typeFor(declarator))
         Ast(
           newTypeDecl(
             name,
             registerType(name),
             filename,
             nodeSignature(d),
-            alias = Some(declTypeName),
+            alias = Some(tpe),
             line = lineNumber,
             column = columnNumber
           )
         )
       case d if parentIsClassDef(d) =>
+        val tpe = registerType(typeFor(declaration.getDeclSpecifier))
         Ast(
           NewMember()
             .code(nodeSignature(declarator))
             .name(name)
-            .typeFullName(declTypeName)
+            .typeFullName(tpe)
             .lineNumber(lineNumber)
             .columnNumber(columnNumber)
         )
       case _ if declarator.isInstanceOf[IASTArrayDeclarator] =>
+        val tpe     = registerType(typeFor(declarator))
         val codeTpe = typeFor(declarator, stripKeywords = false)
         val l = NewLocal()
           .code(s"$codeTpe $name")
           .name(name)
-          .typeFullName(registerType(tpe))
+          .typeFullName(tpe)
           .lineNumber(lineNumber)
           .columnNumber(columnNumber)
         scope.addToScope(name, (l, tpe))
         Ast(l)
       case _ =>
+        val tpe = registerType(
+          cleanType(typeForDeclSpecifier(declaration.getDeclSpecifier, stripKeywords = true, index))
+        )
         val codeTpe = typeForDeclSpecifier(declaration.getDeclSpecifier, stripKeywords = false, index)
         val l = NewLocal()
           .code(s"$codeTpe $name")
           .name(name)
-          .typeFullName(registerType(tpe))
+          .typeFullName(tpe)
           .lineNumber(lineNumber)
           .columnNumber(columnNumber)
         scope.addToScope(name, (l, tpe))
@@ -191,7 +193,7 @@ trait AstForTypesCreator {
         name,
         registerType(name),
         filename,
-        mappedName,
+        nodeSignature(aliasDeclaration),
         alias = Some(mappedName),
         line = linenumber,
         column = columnnumber
@@ -234,7 +236,7 @@ trait AstForTypesCreator {
           case spec: IASTNamedTypeSpecifier if declaration.getDeclarators.isEmpty =>
             val filename = fileName(spec)
             val name     = ASTStringUtil.getSimpleName(spec.getName)
-            Seq(Ast(newTypeDecl(name, registerType(name), filename, name, alias = Some(name))))
+            Seq(Ast(newTypeDecl(name, registerType(name), filename, nodeSignature(spec), alias = Some(name))))
           case _ if declaration.getDeclarators.nonEmpty =>
             declaration.getDeclarators.toIndexedSeq.zipWithIndex.map {
               case (d: IASTFunctionDeclarator, _) =>
@@ -290,7 +292,7 @@ trait AstForTypesCreator {
 
     val name                   = ASTStringUtil.getSimpleName(typeSpecifier.getName)
     val fullname               = registerType(cleanType(fullName(typeSpecifier)))
-    val code                   = typeFor(typeSpecifier)
+    val code                   = nodeSignature(typeSpecifier)
     val nameWithTemplateParams = templateParameters(typeSpecifier).map(t => registerType(fullname + t))
 
     val typeDecl = typeSpecifier match {
@@ -335,7 +337,7 @@ trait AstForTypesCreator {
     val nameWithTemplateParams = templateParameters(typeSpecifier).map(t => registerType(fullname + t))
 
     val typeDecl =
-      newTypeDecl(name, fullname, filename, typeFor(typeSpecifier), alias = nameWithTemplateParams)
+      newTypeDecl(name, fullname, filename, nodeSignature(typeSpecifier), alias = nameWithTemplateParams)
 
     Ast(typeDecl) +: declAsts
   }
@@ -372,7 +374,7 @@ trait AstForTypesCreator {
 
     val (name, fullname) =
       uniqueName("enum", ASTStringUtil.getSimpleName(typeSpecifier.getName), fullName(typeSpecifier))
-    val typeDecl = newTypeDecl(name, registerType(fullname), filename, typeFor(typeSpecifier))
+    val typeDecl = newTypeDecl(name, registerType(fullname), filename, nodeSignature(typeSpecifier))
 
     methodAstParentStack.push(typeDecl)
     scope.pushNewScope(typeDecl)
diff --git a/querydb/src/main/scala/io/joern/scanners/c/UseAfterFree.scala b/querydb/src/main/scala/io/joern/scanners/c/UseAfterFree.scala
index 5ac804c35e4c..eaf4b5789a45 100644
--- a/querydb/src/main/scala/io/joern/scanners/c/UseAfterFree.scala
+++ b/querydb/src/main/scala/io/joern/scanners/c/UseAfterFree.scala
@@ -89,7 +89,7 @@ object UseAfterFree extends QueryBundle {
           |The function sets a field of a function parameter to a value of a local
           |variable.
           |This variable is then freed in some paths. Unless the value set in the
-          |function |parameter is overridden later on, the caller has access to the
+          |function parameter is overridden later on, the caller has access to the
           |free'd memory, which is undefined behavior.
           |
           |Finds bugs like CVE-2019-18902.
@@ -98,7 +98,7 @@ object UseAfterFree extends QueryBundle {
       withStrRep({ cpg =>
         def outParams =
           cpg.parameter
-            .typeFullName(".+\\*")
+            .code(".+\\*.+")
             .whereNot(
               _.referencingIdentifiers
                 .argumentIndex(1)


Test patch:
diff --git a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/EnumTests.scala b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/EnumTests.scala
index 1070c6f09f47..0f52554f72cd 100644
--- a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/EnumTests.scala
+++ b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/EnumTests.scala
@@ -22,7 +22,7 @@ class EnumTests extends AnyWordSpec with Matchers with Inside with CompleteCpgFi
         |};""".stripMargin) { cpg =>
       inside(cpg.typeDecl.nameNot("<global>").internal.l) { case List(color) =>
         color.name shouldBe "color"
-        color.code shouldBe "enum color"
+        color.code should startWith("enum color")
         inside(color.member.l) { case List(red, yellow, green, blue) =>
           red.name shouldBe "red"
           yellow.name shouldBe "yellow"
@@ -50,7 +50,7 @@ class EnumTests extends AnyWordSpec with Matchers with Inside with CompleteCpgFi
         |} C;""".stripMargin) { cpg =>
       inside(cpg.typeDecl.nameNot("<global>").filter(x => !x.isExternal).l) { case List(color, c) =>
         color.name shouldBe "color"
-        color.code shouldBe "enum color"
+        color.code should startWith("typedef enum color")
         color.aliasTypeFullName shouldBe None
         c.name shouldBe "C"
         c.aliasTypeFullName shouldBe Some("color")
@@ -79,7 +79,7 @@ class EnumTests extends AnyWordSpec with Matchers with Inside with CompleteCpgFi
         |}; """.stripMargin) { cpg =>
       inside(cpg.typeDecl.nameNot("<global>").internal.l) { case List(altitude) =>
         altitude.name shouldBe "altitude"
-        altitude.code shouldBe "enum altitude"
+        altitude.code should startWith("enum class altitude")
         inside(altitude.member.l) { case List(high, low) =>
           high.name shouldBe "high"
           high.typeFullName shouldBe "char"
@@ -99,7 +99,7 @@ class EnumTests extends AnyWordSpec with Matchers with Inside with CompleteCpgFi
     }
 
     "be correct for simple enum with type" in CompleteCpgFixture("""
-        enum smallenum: int
+        |enum smallenum: int
         |{
         |    a,
         |    b,
@@ -107,7 +107,7 @@ class EnumTests extends AnyWordSpec with Matchers with Inside with CompleteCpgFi
         |};""".stripMargin) { cpg =>
       inside(cpg.typeDecl.nameNot("<global>").internal.l) { case List(smallenum) =>
         smallenum.name shouldBe "smallenum"
-        smallenum.code shouldBe "enum smallenum"
+        smallenum.code should startWith("enum smallenum")
         inside(smallenum.member.l) { case List(a, b, c) =>
           a.name shouldBe "a"
           a.typeFullName shouldBe "int"
@@ -129,7 +129,7 @@ class EnumTests extends AnyWordSpec with Matchers with Inside with CompleteCpgFi
          |};""".stripMargin) { cpg =>
       inside(cpg.typeDecl.nameNot("<global>").internal.l) { case List(anon) =>
         anon.name shouldBe "anonymous_enum_0"
-        anon.code shouldBe "enum"
+        anon.code should startWith("enum")
         inside(anon.member.l) { case List(d, e, f) =>
           d.name shouldBe "d"
           e.name shouldBe "e"
@@ -149,7 +149,7 @@ class EnumTests extends AnyWordSpec with Matchers with Inside with CompleteCpgFi
        |""".stripMargin) { cpg =>
       inside(cpg.typeDecl.nameNot("<global>").internal.l) { case List(x) =>
         x.name shouldBe "X"
-        x.code shouldBe "enum X"
+        x.code should startWith("enum X")
         inside(x.member.l) { case List(a, b) =>
           a.name shouldBe "a"
           a.typeFullName shouldBe "int"
diff --git a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/AstCreationPassTests.scala b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/AstCreationPassTests.scala
index 77fe680d3fca..f07fb7e9f3e2 100644
--- a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/AstCreationPassTests.scala
+++ b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/AstCreationPassTests.scala
@@ -72,7 +72,7 @@ class AstCreationPassTests
           x.order shouldBe 1
           args.name shouldBe "args"
           args.code shouldBe "int*... args"
-          args.typeFullName shouldBe "int*"
+          args.typeFullName shouldBe "int"
           args.isVariadic shouldBe true
           args.order shouldBe 2
         }
@@ -111,11 +111,11 @@ class AstCreationPassTests
         inside(m.parameter.l) { case List(x, y) =>
           x.name shouldBe "x"
           x.code shouldBe "int *x;"
-          x.typeFullName shouldBe "int*"
+          x.typeFullName shouldBe "int"
           x.order shouldBe 1
           y.name shouldBe "y"
           y.code shouldBe "int *y;"
-          y.typeFullName shouldBe "int*"
+          y.typeFullName shouldBe "int"
           y.order shouldBe 2
         }
       }
@@ -370,8 +370,9 @@ class AstCreationPassTests
         |}
         |""".stripMargin) { cpg =>
       inside(cpg.method.name("method").parameter.l) { case List(param: MethodParameterIn) =>
-        param.typeFullName shouldBe "a_struct_type*"
+        param.typeFullName shouldBe "a_struct_type"
         param.name shouldBe "a_struct"
+        param.code shouldBe "a_struct_type *a_struct"
       }
     }
 
@@ -383,7 +384,8 @@ class AstCreationPassTests
        |}
        |""".stripMargin) { cpg =>
       inside(cpg.method.name("method").parameter.l) { case List(param: MethodParameterIn) =>
-        param.typeFullName shouldBe "struct date*"
+        param.code shouldBe "struct date *date"
+        param.typeFullName shouldBe "date"
         param.name shouldBe "date"
       }
     }
@@ -1066,6 +1068,27 @@ class AstCreationPassTests
       cpg.typeDecl.name("abc").aliasTypeFullName("foo").size shouldBe 1
     }
 
+    "be correct for struct with local" in TestAstOnlyFixture("""
+        |struct A {
+        |  int x;
+        |} a;
+        |struct B b;
+      """.stripMargin) { cpg =>
+      inside(cpg.typeDecl("A").member.l) { case List(x) =>
+        x.name shouldBe "x"
+        x.typeFullName shouldBe "int"
+      }
+      cpg.typeDecl.name("B").size shouldBe 1
+      inside(cpg.local.l) { case List(a, b) =>
+        a.name shouldBe "a"
+        a.typeFullName shouldBe "A"
+        a.code shouldBe "struct A a"
+        b.name shouldBe "b"
+        b.typeFullName shouldBe "B"
+        b.code shouldBe "struct B b"
+      }
+    }
+
     "be correct for global struct" in TestAstOnlyFixture("""
         |struct filesystem {
         |	void (*open)(int a);
diff --git a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/TypeNodePassTests.scala b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/TypeNodePassTests.scala
index c81931e356c7..dcbb5ca2f680 100644
--- a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/TypeNodePassTests.scala
+++ b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/passes/TypeNodePassTests.scala
@@ -48,7 +48,7 @@ class TypeNodePassTests extends AnyWordSpec with Matchers with Inside with CpgTy
         inside(arg.typ.referencedTypeDecl.l) { case List(tpe) =>
           tpe.fullName shouldBe "test"
           tpe.name shouldBe "test"
-          tpe.code shouldBe "struct test"
+          tpe.code should startWith("struct test")
         }
         inside(cpg.local.l) { case List(ptr) =>
           ptr.name shouldBe "ptr"
@@ -58,7 +58,7 @@ class TypeNodePassTests extends AnyWordSpec with Matchers with Inside with CpgTy
         inside(cpg.local.typ.referencedTypeDecl.l) { case List(tpe) =>
           tpe.fullName shouldBe "test"
           tpe.name shouldBe "test"
-          tpe.code shouldBe "struct test"
+          tpe.code should startWith("struct test")
         }
       }
     }
diff --git a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/querying/NodeTypeStartersTests.scala b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/querying/NodeTypeStartersTests.scala
index 281d0f29f023..dd476a1f633e 100644
--- a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/querying/NodeTypeStartersTests.scala
+++ b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/querying/NodeTypeStartersTests.scala
@@ -64,7 +64,7 @@ class NodeTypeStartersTests extends CCodeToCpgSuite {
   }
 
   "should allow retrieving (used) types" in {
-    cpg.typ.name.toSetMutable shouldBe Set("int", "void", "char**", "ANY", "foo")
+    cpg.typ.name.toSetMutable shouldBe Set("int", "void", "char", "ANY", "foo")
   }
 
   "should allow retrieving namespaces" in {
diff --git a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/standard/MethodParameterTests.scala b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/standard/MethodParameterTests.scala
index 8715be7c8f69..3afe535ff65c 100644
--- a/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/standard/MethodParameterTests.scala
+++ b/joern-cli/frontends/c2cpg/src/test/scala/io/joern/c2cpg/standard/MethodParameterTests.scala
@@ -22,7 +22,7 @@ class MethodParameterTests extends CCodeToCpgSuite {
 
     val List(y) = cpg.parameter.name("argv").l
     y.code shouldBe "char **argv"
-    y.typeFullName shouldBe "char**"
+    y.typeFullName shouldBe "char"
     y.lineNumber shouldBe Some(2)
     y.columnNumber shouldBe Some(22)
     y.order shouldBe 2