diff --git a/cpp/pom.xml b/cpp/pom.xml new file mode 100644 index 00000000..b16687f8 --- /dev/null +++ b/cpp/pom.xml @@ -0,0 +1,149 @@ + + + + 4.0.0 + + + com.ibm + sonar-cryptography + 1.5.1-SNAPSHOT + ../pom.xml + + + sonar-cryptography-cpp + Sonar Cryptography Plugin :: C/C++ + + C and C++ language support for the Sonar Cryptography Plugin, + with detection rules for OpenSSL and other cryptographic libraries. + + + + 17 + 17 + + + + + + + com.ibm + sonar-cryptography-common + ${project.version} + + + + com.ibm + sonar-cryptography-engine + ${project.version} + + + + com.ibm + sonar-cryptography-mapper + ${project.version} + + + + com.ibm + sonar-cryptography-enricher + ${project.version} + + + + com.ibm + sonar-cryptography-output + ${project.version} + + + + + org.sonarsource.api.plugin + sonar-plugin-api + provided + + + + + org.antlr + antlr4-runtime + + + + + com.google.code.findbugs + jsr305 + + + + + org.slf4j + slf4j-api + + + + + org.junit.jupiter + junit-jupiter + test + + + + org.assertj + assertj-core + test + + + + org.mockito + mockito-core + test + + + + org.sonarsource.api.plugin + sonar-plugin-api-test-fixtures + test + + + + + + + + + + com.diffplug.spotless + spotless-maven-plugin + + + + + org.apache.maven.plugins + maven-surefire-plugin + + + + + + diff --git a/engine/src/main/antlr4/com/ibm/engine/language/csharp/antlr/CLexer.g4 b/engine/src/main/antlr4/com/ibm/engine/language/csharp/antlr/CLexer.g4 new file mode 100644 index 00000000..581c03ca --- /dev/null +++ b/engine/src/main/antlr4/com/ibm/engine/language/csharp/antlr/CLexer.g4 @@ -0,0 +1,359 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/* + * C Lexer Grammar for CBOMkit sonar-cryptography plugin. + * Adapted from the ANTLR4 grammars-v4 C grammar: + * https://github.com/antlr/grammars-v4/tree/master/c + * + * Supports C89, C99, C11 constructs sufficient for detecting + * OpenSSL and other cryptographic library API calls. + */ +lexer grammar CLexer; + +// --------------------------------------------------------------------------- +// Keywords +// --------------------------------------------------------------------------- + +Auto : 'auto'; +Break : 'break'; +Case : 'case'; +Char : 'char'; +Const : 'const'; +Continue : 'continue'; +Default : 'default'; +Do : 'do'; +Double : 'double'; +Else : 'else'; +Enum : 'enum'; +Extern : 'extern'; +Float : 'float'; +For : 'for'; +Goto : 'goto'; +If : 'if'; +Inline : 'inline'; +Int : 'int'; +Long : 'long'; +Register : 'register'; +Restrict : 'restrict'; +Return : 'return'; +Short : 'short'; +Signed : 'signed'; +Sizeof : 'sizeof'; +Static : 'static'; +Struct : 'struct'; +Switch : 'switch'; +Typedef : 'typedef'; +Union : 'union'; +Unsigned : 'unsigned'; +Void : 'void'; +Volatile : 'volatile'; +While : 'while'; + +// C11 keywords +Alignas : '_Alignas'; +Alignof : '_Alignof'; +Atomic : '_Atomic'; +Bool : '_Bool'; +Complex : '_Complex'; +Generic : '_Generic'; +Imaginary : '_Imaginary'; +Noreturn : '_Noreturn'; +StaticAssert : '_Static_assert'; +ThreadLocal : '_Thread_local'; + +// GCC extensions (common in OpenSSL code) +BuiltinVaArg : '__builtin_va_arg'; +BuiltinOffsetof : '__builtin_offsetof'; + +// --------------------------------------------------------------------------- +// Punctuators and operators +// --------------------------------------------------------------------------- + +LeftParen : '('; +RightParen : ')'; +LeftBracket : '['; +RightBracket : ']'; +LeftBrace : '{'; +RightBrace : '}'; + +Less : '<'; +LessEqual : '<='; +Greater : '>'; +GreaterEqual : '>='; +LeftShift : '<<'; +RightShift : '>>'; + +Plus : '+'; +PlusPlus : '++'; +Minus : '-'; +MinusMinus : '--'; +Star : '*'; +Div : '/'; +Mod : '%'; + +And : '&'; +Or : '|'; +AndAnd : '&&'; +OrOr : '||'; +Caret : '^'; +Not : '!'; +Tilde : '~'; + +Question : '?'; +Colon : ':'; +Semi : ';'; +Comma : ','; +Assign : '='; + +// Compound assignment operators +StarAssign : '*='; +DivAssign : '/='; +ModAssign : '%='; +PlusAssign : '+='; +MinusAssign : '-='; +LeftShiftAssign : '<<='; +RightShiftAssign: '>>='; +AndAssign : '&='; +XorAssign : '^='; +OrAssign : '|='; + +Equal : '=='; +NotEqual : '!='; + +Arrow : '->'; +Dot : '.'; +Ellipsis : '...'; + +// --------------------------------------------------------------------------- +// Literals +// --------------------------------------------------------------------------- + +IntegerConstant + : DecimalConstant IntegerSuffix? + | OctalConstant IntegerSuffix? + | HexadecimalConstant IntegerSuffix? + | BinaryConstant + ; + +fragment BinaryConstant + : '0' [bB] [0-1]+ + ; + +fragment DecimalConstant + : NonzeroDigit Digit* + ; + +fragment OctalConstant + : '0' OctalDigit* + ; + +fragment HexadecimalConstant + : HexadecimalPrefix HexadecimalDigit+ + ; + +fragment HexadecimalPrefix + : '0' [xX] + ; + +fragment IntegerSuffix + : UnsignedSuffix LongSuffix? + | UnsignedSuffix LongLongSuffix + | LongSuffix UnsignedSuffix? + | LongLongSuffix UnsignedSuffix? + ; + +fragment UnsignedSuffix + : [uU] + ; + +fragment LongSuffix + : [lL] + ; + +fragment LongLongSuffix + : 'll' | 'LL' + ; + +FloatingConstant + : DecimalFloatingConstant + | HexadecimalFloatingConstant + ; + +fragment DecimalFloatingConstant + : FractionalConstant ExponentPart? FloatingSuffix? + | DigitSequence ExponentPart FloatingSuffix? + ; + +fragment HexadecimalFloatingConstant + : HexadecimalPrefix (HexadecimalFractionalConstant | HexadecimalDigitSequence) BinaryExponentPart FloatingSuffix? + ; + +fragment FractionalConstant + : DigitSequence? '.' DigitSequence + | DigitSequence '.' + ; + +fragment ExponentPart + : [eE] Sign? DigitSequence + ; + +fragment Sign + : [+-] + ; + +fragment DigitSequence + : Digit+ + ; + +fragment HexadecimalFractionalConstant + : HexadecimalDigitSequence? '.' HexadecimalDigitSequence + | HexadecimalDigitSequence '.' + ; + +fragment BinaryExponentPart + : [pP] Sign? DigitSequence + ; + +fragment HexadecimalDigitSequence + : HexadecimalDigit+ + ; + +fragment FloatingSuffix + : [flFL] + ; + +CharacterConstant + : '\'' CCharSequence '\'' + | 'L\'' CCharSequence '\'' + | 'u\'' CCharSequence '\'' + | 'U\'' CCharSequence '\'' + ; + +fragment CCharSequence + : CChar+ + ; + +fragment CChar + : ~['\\\r\n] + | EscapeSequence + ; + +StringLiteral + : EncodingPrefix? '"' SCharSequence? '"' + ; + +fragment EncodingPrefix + : 'u8' | 'u' | 'U' | 'L' + ; + +fragment SCharSequence + : SChar+ + ; + +fragment SChar + : ~["\\\r\n] + | EscapeSequence + | '\\\n' // Added line + | '\\\r\n' // Added line + ; + +fragment EscapeSequence + : SimpleEscapeSequence + | OctalEscapeSequence + | HexadecimalEscapeSequence + | UniversalCharacterName + ; + +fragment SimpleEscapeSequence + : '\\' ['"?abfnrtvv\\] + ; + +fragment OctalEscapeSequence + : '\\' OctalDigit OctalDigit? OctalDigit? + ; + +fragment HexadecimalEscapeSequence + : '\\x' HexadecimalDigit+ + ; + +// --------------------------------------------------------------------------- +// Identifiers +// --------------------------------------------------------------------------- + +Identifier + : IdentifierNondigit (IdentifierNondigit | Digit)* + ; + +fragment IdentifierNondigit + : Nondigit + | UniversalCharacterName + ; + +fragment Nondigit + : [a-zA-Z_] + ; + +fragment Digit + : [0-9] + ; + +fragment NonzeroDigit + : [1-9] + ; + +fragment OctalDigit + : [0-7] + ; + +fragment HexadecimalDigit + : [0-9a-fA-F] + ; + +fragment UniversalCharacterName + : '\\u' HexadecimalDigit HexadecimalDigit HexadecimalDigit HexadecimalDigit + | '\\U' HexadecimalDigit HexadecimalDigit HexadecimalDigit HexadecimalDigit + HexadecimalDigit HexadecimalDigit HexadecimalDigit HexadecimalDigit + ; + +// --------------------------------------------------------------------------- +// Preprocessor directives (skip — we do not expand macros) +// --------------------------------------------------------------------------- + +Directive + : '#' ~[\r\n]* -> skip + ; + +// --------------------------------------------------------------------------- +// Whitespace and comments +// --------------------------------------------------------------------------- + +Whitespace + : [ \t]+ -> skip + ; + +Newline + : ( '\r' '\n'? | '\n' ) -> skip + ; + +BlockComment + : '/*' .*? '*/' -> skip + ; + +LineComment + : '//' ~[\r\n]* -> skip + ; diff --git a/engine/src/main/antlr4/com/ibm/engine/language/csharp/antlr/CParser.g4 b/engine/src/main/antlr4/com/ibm/engine/language/csharp/antlr/CParser.g4 new file mode 100644 index 00000000..41866acf --- /dev/null +++ b/engine/src/main/antlr4/com/ibm/engine/language/csharp/antlr/CParser.g4 @@ -0,0 +1,494 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/* + * C Parser Grammar for CBOMkit sonar-cryptography plugin. + * Adapted from the ANTLR4 grammars-v4 C grammar: + * https://github.com/antlr/grammars-v4/tree/master/c + * + * Supports C89, C99, C11 constructs sufficient for detecting + * OpenSSL and other cryptographic library API calls. + * + * Key design goals: + * - Detect function calls: EVP_EncryptInit_ex(ctx, EVP_aes_256_cbc(), ...) + * - Detect string literals used as algorithm identifiers + * - Detect integer constants used as key sizes + * - Handle pointer dereferences and struct member access + */ +parser grammar CParser; + +options { + tokenVocab = CLexer; +} + +// --------------------------------------------------------------------------- +// Top-level rule +// --------------------------------------------------------------------------- + +compilationUnit + : translationUnit? EOF + ; + +translationUnit + : externalDeclaration+ + ; + +externalDeclaration + : functionDefinition + | declaration + | Semi // stray semicolons + ; + +// --------------------------------------------------------------------------- +// Function definitions +// --------------------------------------------------------------------------- + +functionDefinition + : declarationSpecifiers declarator declarationList? compoundStatement + ; + +declarationList + : declaration+ + ; + +// --------------------------------------------------------------------------- +// Declarations +// --------------------------------------------------------------------------- + +declaration + : declarationSpecifiers initDeclaratorList? Semi + | staticAssertDeclaration + ; + +declarationSpecifiers + : declarationSpecifier+ + ; + +declarationSpecifiers2 + : declarationSpecifier+ + ; + +declarationSpecifier + : storageClassSpecifier + | typeSpecifier + | typeQualifier + | functionSpecifier + | alignmentSpecifier + ; + +initDeclaratorList + : initDeclarator ( Comma initDeclarator )* + ; + +initDeclarator + : declarator ( Assign initializer )? + ; + +storageClassSpecifier + : Typedef + | Extern + | Static + | ThreadLocal + | Auto + | Register + ; + +typeSpecifier + : Void + | Char + | Short + | Int + | Long + | Float + | Double + | Signed + | Unsigned + | Bool + | Complex + | atomicTypeSpecifier + | structOrUnionSpecifier + | enumSpecifier + | typedefName + | typeofSpecifier + ; + +// typeof() — GCC extension common in OpenSSL +typeofSpecifier + : '__typeof__' LeftParen (expression | typeName) RightParen + | '__typeof' LeftParen (expression | typeName) RightParen + ; + +structOrUnionSpecifier + : structOrUnion Identifier? LeftBrace structDeclarationList RightBrace + | structOrUnion Identifier + ; + +structOrUnion + : 'struct' + | 'union' + ; + +structDeclarationList + : structDeclaration+ + ; + +structDeclaration + : specifierQualifierList structDeclaratorList? Semi + | staticAssertDeclaration + ; + +specifierQualifierList + : (typeSpecifier | typeQualifier | alignmentSpecifier)+ + ; + +structDeclaratorList + : structDeclarator (Comma structDeclarator)* + ; + +structDeclarator + : declarator + | declarator? Colon constantExpression + ; + +enumSpecifier + : 'enum' Identifier? LeftBrace enumeratorList Comma? RightBrace + | 'enum' Identifier + ; + +enumeratorList + : enumerator (Comma enumerator)* + ; + +enumerator + : enumerationConstant (Assign constantExpression)? + ; + +enumerationConstant + : Identifier + ; + +atomicTypeSpecifier + : Atomic LeftParen typeName RightParen + ; + +typeQualifier + : Const + | Restrict + | Volatile + | Atomic + ; + +functionSpecifier + : Inline + | Noreturn + ; + +alignmentSpecifier + : Alignas LeftParen (typeName | constantExpression) RightParen + ; + +declarator + : pointer? directDeclarator + ; + +directDeclarator + : Identifier + | LeftParen declarator RightParen + | directDeclarator LeftBracket typeQualifierList? assignmentExpression? RightBracket + | directDeclarator LeftBracket Static typeQualifierList? assignmentExpression RightBracket + | directDeclarator LeftBracket typeQualifierList Static assignmentExpression RightBracket + | directDeclarator LeftBracket typeQualifierList? Star RightBracket + | directDeclarator LeftParen parameterTypeList RightParen + | directDeclarator LeftParen identifierList? RightParen + ; + +pointer + : ( Star typeQualifierList? )+ + ; + +typeQualifierList + : typeQualifier+ + ; + +parameterTypeList + : parameterList ( Comma Ellipsis )? + ; + +parameterList + : parameterDeclaration ( Comma parameterDeclaration )* + ; + +parameterDeclaration + : declarationSpecifiers declarator + | declarationSpecifiers2 abstractDeclarator? + ; + +identifierList + : Identifier ( Comma Identifier )* + ; + +typeName + : specifierQualifierList abstractDeclarator? + ; + +abstractDeclarator + : pointer + | pointer? directAbstractDeclarator + ; + +directAbstractDeclarator + : LeftParen abstractDeclarator RightParen + | LeftBracket typeQualifierList? assignmentExpression? RightBracket + | LeftBracket Static typeQualifierList? assignmentExpression RightBracket + | LeftBracket typeQualifierList Static assignmentExpression RightBracket + | LeftBracket Star RightBracket + | LeftParen parameterTypeList? RightParen + | directAbstractDeclarator LeftBracket typeQualifierList? assignmentExpression? RightBracket + | directAbstractDeclarator LeftBracket Static typeQualifierList? assignmentExpression RightBracket + | directAbstractDeclarator LeftBracket typeQualifierList Static assignmentExpression RightBracket + | directAbstractDeclarator LeftBracket Star RightBracket + | directAbstractDeclarator LeftParen parameterTypeList? RightParen + ; + +typedefName + : Identifier + ; + +initializer + : assignmentExpression + | LeftBrace initializerList Comma? RightBrace + ; + +initializerList + : designation? initializer ( Comma designation? initializer )* + ; + +designation + : designatorList Assign + ; + +designatorList + : designator+ + ; + +designator + : LeftBracket constantExpression RightBracket + | Dot Identifier + ; + +staticAssertDeclaration + : StaticAssert LeftParen constantExpression Comma StringLiteral+ RightParen Semi + ; + +// --------------------------------------------------------------------------- +// Statements +// --------------------------------------------------------------------------- + +statement + : labeledStatement + | compoundStatement + | expressionStatement + | selectionStatement + | iterationStatement + | jumpStatement + ; + +labeledStatement + : Identifier Colon statement + | Case constantExpression Colon statement + | Default Colon statement + ; + +compoundStatement + : LeftBrace blockItemList? RightBrace + ; + +blockItemList + : blockItem+ + ; + +blockItem + : statement + | declaration + ; + +expressionStatement + : expression? Semi + ; + +selectionStatement + : If LeftParen expression RightParen statement ( Else statement )? + | Switch LeftParen expression RightParen statement + ; + +iterationStatement + : While LeftParen expression RightParen statement + | Do statement While LeftParen expression RightParen Semi + | For LeftParen forCondition RightParen statement + ; + +forCondition + : ( forDeclaration | expression? ) Semi forExpression? Semi forExpression? + ; + +forDeclaration + : declarationSpecifiers initDeclaratorList? + ; + +forExpression + : assignmentExpression ( Comma assignmentExpression )* + ; + +jumpStatement + : Goto Identifier Semi + | Continue Semi + | Break Semi + | Return expression? Semi + ; + +// --------------------------------------------------------------------------- +// Expressions +// --------------------------------------------------------------------------- + +compilationUnit2 + : expression EOF + ; + +expression + : assignmentExpression ( Comma assignmentExpression )* + ; + +assignmentExpression + : conditionalExpression + | unaryExpression assignmentOperator assignmentExpression + ; + +assignmentOperator + : Assign | StarAssign | DivAssign | ModAssign | PlusAssign | MinusAssign + | LeftShiftAssign | RightShiftAssign | AndAssign | XorAssign | OrAssign + ; + +conditionalExpression + : logicalOrExpression ( Question expression Colon conditionalExpression )? + ; + +logicalOrExpression + : logicalAndExpression ( OrOr logicalAndExpression )* + ; + +logicalAndExpression + : inclusiveOrExpression ( AndAnd inclusiveOrExpression )* + ; + +inclusiveOrExpression + : exclusiveOrExpression ( Or exclusiveOrExpression )* + ; + +exclusiveOrExpression + : andExpression ( Caret andExpression )* + ; + +andExpression + : equalityExpression ( And equalityExpression )* + ; + +equalityExpression + : relationalExpression ( ( Equal | NotEqual ) relationalExpression )* + ; + +relationalExpression + : shiftExpression ( ( Less | Greater | LessEqual | GreaterEqual ) shiftExpression )* + ; + +shiftExpression + : additiveExpression ( ( LeftShift | RightShift ) additiveExpression )* + ; + +additiveExpression + : multiplicativeExpression ( ( Plus | Minus ) multiplicativeExpression )* + ; + +multiplicativeExpression + : castExpression ( ( Star | Div | Mod ) castExpression )* + ; + +castExpression + : LeftParen typeName RightParen castExpression + | unaryExpression + ; + +unaryExpression + : postfixExpression + | PlusPlus unaryExpression + | MinusMinus unaryExpression + | unaryOperator castExpression + | Sizeof ( unaryExpression | LeftParen typeName RightParen ) + | Alignof LeftParen typeName RightParen + | BuiltinVaArg LeftParen unaryExpression Comma typeName RightParen + | BuiltinOffsetof LeftParen typeName Comma unaryExpression RightParen + ; + +unaryOperator + : And | Star | Plus | Minus | Tilde | Not + ; + +// --------------------------------------------------------------------------- +// Postfix expressions — KEY RULE for detecting function calls +// --------------------------------------------------------------------------- + +postfixExpression + : primaryExpression + | postfixExpression LeftBracket expression RightBracket // array index + | postfixExpression LeftParen argumentExpressionList? RightParen // FUNCTION CALL ← detect this + | postfixExpression ( Dot | Arrow ) Identifier // member access + | postfixExpression ( PlusPlus | MinusMinus ) + | LeftParen typeName RightParen LeftBrace initializerList Comma? RightBrace + ; + +argumentExpressionList + : assignmentExpression ( Comma assignmentExpression )* + ; + +primaryExpression + : Identifier + | Constant + | StringLiteral+ + | LeftParen expression RightParen + | genericSelection + ; + +Constant + : IntegerConstant + | FloatingConstant + | CharacterConstant + ; + +genericSelection + : Generic LeftParen assignmentExpression Comma genericAssocList RightParen + ; + +genericAssocList + : genericAssociation ( Comma genericAssociation )* + ; + +genericAssociation + : ( typeName | Default ) Colon assignmentExpression + ; + +constantExpression + : conditionalExpression + ; diff --git a/pom.xml b/pom.xml index a32d3c77..f411054a 100644 --- a/pom.xml +++ b/pom.xml @@ -14,6 +14,7 @@ python go csharp + cpp engine output common diff --git a/sonar-cryptography-plugin/pom.xml b/sonar-cryptography-plugin/pom.xml index 9ac6bfe6..a181f9ee 100644 --- a/sonar-cryptography-plugin/pom.xml +++ b/sonar-cryptography-plugin/pom.xml @@ -47,6 +47,12 @@ 2.0.0-SNAPSHOT compile + + com.ibm + cpp + 2.0.0-SNAPSHOT + compile + @@ -71,7 +77,7 @@ Sonar Crypto Plugin com.ibm.plugin.CryptographyPlugin - java,jsp,py,ipynb,go,cs + java,jsp,py,ipynb,go,cs,c,cpp,h ${sonar.minVersion} true true @@ -104,7 +110,7 @@ NOTICE* - + @@ -174,4 +180,4 @@ - \ No newline at end of file +