From 3bacba762aad0e5759fd0bd9bbf345d82da7a711 Mon Sep 17 00:00:00 2001 From: Jia Chen Date: Tue, 18 Jul 2017 15:59:29 -0700 Subject: [PATCH] Whitelist the constructors+conversion operators+destructors for classes listed on whitelisted_cpp_classes Reviewed By: akotulski Differential Revision: D5435639 fbshipit-source-id: 4d6782d --- infer/src/clang/cFrontend_decl.ml | 6 +++ .../tests/codetoanalyze/cpp/errors/issues.exp | 2 +- .../codetoanalyze/cpp/quandary/issues.exp | 43 +++++++++--------- .../codetoanalyze/cpp/quandary/strings.cpp | 44 +++++++++---------- 4 files changed, 50 insertions(+), 45 deletions(-) diff --git a/infer/src/clang/cFrontend_decl.ml b/infer/src/clang/cFrontend_decl.ml index e2a777490..963365c38 100644 --- a/infer/src/clang/cFrontend_decl.ml +++ b/infer/src/clang/cFrontend_decl.ml @@ -172,6 +172,9 @@ module CFrontend_decl_funct (T : CModule_type.CTranslation) : CModule_type.CFron match dec with | Clang_ast_t.FunctionDecl (_, name_info, _, _) | Clang_ast_t.CXXMethodDecl (_, name_info, _, _, _) + | Clang_ast_t.CXXConstructorDecl (_, name_info, _, _, _) + | Clang_ast_t.CXXConversionDecl (_, name_info, _, _, _) + | Clang_ast_t.CXXDestructorDecl (_, name_info, _, _, _) -> is_whitelisted_cpp_method (CAst_utils.get_qualified_name name_info) | _ -> false @@ -184,6 +187,9 @@ module CFrontend_decl_funct (T : CModule_type.CTranslation) : CModule_type.CFron match dec with | Clang_ast_t.FunctionDecl (_, name_info, _, _) | Clang_ast_t.CXXMethodDecl (_, name_info, _, _, _) + | Clang_ast_t.CXXConstructorDecl (_, name_info, _, _, _) + | Clang_ast_t.CXXConversionDecl (_, name_info, _, _, _) + | Clang_ast_t.CXXDestructorDecl (_, name_info, _, _, _) -> let fun_name = name_info.Clang_ast_t.ni_name in Str.string_match (Str.regexp "__infer_skip__") fun_name 0 | _ diff --git a/infer/tests/codetoanalyze/cpp/errors/issues.exp b/infer/tests/codetoanalyze/cpp/errors/issues.exp index ff5c11ec2..a8e52272c 100644 --- a/infer/tests/codetoanalyze/cpp/errors/issues.exp +++ b/infer/tests/codetoanalyze/cpp/errors/issues.exp @@ -164,7 +164,7 @@ codetoanalyze/cpp/errors/vector/empty_access.cpp, size_check0_empty, 2, EMPTY_VE codetoanalyze/cpp/errors/vector/empty_access.cpp, vector_as_param_by_value_empty, 2, EMPTY_VECTOR_ACCESS, [start of procedure vector_as_param_by_value_empty(),start of procedure vector_param_by_value_access(),return from a call to vector_param_by_value_access] codetoanalyze/cpp/errors/vector/empty_access.cpp, vector_as_param_clear, 3, EMPTY_VECTOR_ACCESS, [start of procedure vector_as_param_clear(),start of procedure vector_param_clear(),return from a call to vector_param_clear] codetoanalyze/cpp/errors/vector/empty_access.cpp, vector_as_param_empty, 2, EMPTY_VECTOR_ACCESS, [start of procedure vector_as_param_empty(),start of procedure vector_param_access(),return from a call to vector_param_access] -codetoanalyze/cpp/errors/vector/iterator_access.cpp, iterator_access::possible_npe, 4, NULL_DEREFERENCE, [start of procedure iterator_access::possible_npe(),Skipped call: function or method not found,Condition is true,Condition is true,Condition is true] +codetoanalyze/cpp/errors/vector/iterator_access.cpp, iterator_access::possible_npe, 4, NULL_DEREFERENCE, [start of procedure iterator_access::possible_npe(),Condition is true,Condition is true,Condition is true] codetoanalyze/cpp/shared/attributes/annotate.cpp, derefFirstArg2_null_deref, 2, NULL_DEREFERENCE, [start of procedure derefFirstArg2_null_deref()] codetoanalyze/cpp/shared/attributes/annotate.cpp, derefFirstArg3_null_deref, 2, NULL_DEREFERENCE, [start of procedure derefFirstArg3_null_deref(),start of procedure derefFirstArg3()] codetoanalyze/cpp/shared/attributes/annotate.cpp, derefFirstArg_null_deref, 2, NULL_DEREFERENCE, [start of procedure derefFirstArg_null_deref()] diff --git a/infer/tests/codetoanalyze/cpp/quandary/issues.exp b/infer/tests/codetoanalyze/cpp/quandary/issues.exp index a9c8d1eb5..c4936a44c 100644 --- a/infer/tests/codetoanalyze/cpp/quandary/issues.exp +++ b/infer/tests/codetoanalyze/cpp/quandary/issues.exp @@ -51,32 +51,31 @@ codetoanalyze/cpp/quandary/pointers.cpp, pointers::assign_pointer_pass_to_sink_b codetoanalyze/cpp/quandary/pointers.cpp, pointers::assign_source_by_reference_bad1, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source with tainted data @val$0,Return from pointers::assign_source_by_reference,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/pointers.cpp, pointers::assign_source_by_reference_bad2, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source with tainted data @val$0,Return from pointers::assign_source_by_reference,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/pointers.cpp, pointers::assign_source_by_reference_bad3, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source with tainted data @val$0,Return from pointers::assign_source_by_reference with tainted data @val$0,Return from pointers::call_assign_source_by_reference,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::append_bad1, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::append_bad2, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::assign_bad1, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::assign_bad2, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::concat_bad1, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::concat_bad2, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::concat_bad3, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::constructor_bad1, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::constructor_bad2, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::constructor_bad3, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::format_bad1, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::format_bad2, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::format_bad3, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::format_bad4, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::append1_bad, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::append2_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::assign1_bad, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::assign2_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::concat1_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::concat2_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::concat3_bad, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::constructor1_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::constructor2_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::format1_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::format2_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::format3_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::format4_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/strings.cpp, strings::format_varargs_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::insert_bad1, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::insert_bad2, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::insert1_bad, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::insert2_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/strings.cpp, strings::memchr_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/strings.cpp, strings::memcpy_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/strings.cpp, strings::memmove_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::replace_bad1, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::replace_bad2, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::sprintf_bad1, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::sprintf_bad2, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::strcpy_bad1, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] -codetoanalyze/cpp/quandary/strings.cpp, strings::strcpy_bad2, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::replace1_bad, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::replace2_bad, 3, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::sprintf1_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::sprintf2_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::strcpy1_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] +codetoanalyze/cpp/quandary/strings.cpp, strings::strcpy2_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/strings.cpp, strings::strncpy_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/strings.cpp, strings::swap_bad, 4, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] codetoanalyze/cpp/quandary/unknown_code.cpp, unknown_code::direct_bad, 2, QUANDARY_TAINT_ERROR, [Return from __infer_taint_source,Call to __infer_taint_sink] diff --git a/infer/tests/codetoanalyze/cpp/quandary/strings.cpp b/infer/tests/codetoanalyze/cpp/quandary/strings.cpp index 0d871477e..568857bc8 100644 --- a/infer/tests/codetoanalyze/cpp/quandary/strings.cpp +++ b/infer/tests/codetoanalyze/cpp/quandary/strings.cpp @@ -16,28 +16,28 @@ extern void __infer_taint_sink(std::string); // tests related to string manipulation, format strings, etc. namespace strings { -void sprintf_bad1() { +void sprintf1_bad() { char laundered_source[50]; auto source = __infer_taint_source().c_str(); sprintf(laundered_source, "%s", source); __infer_taint_sink(laundered_source); } -void sprintf_bad2() { +void sprintf2_bad() { char laundered_source[50]; auto source = __infer_taint_source().c_str(); sprintf(laundered_source, "%s%s%d", "a", source, 1); __infer_taint_sink(laundered_source); } -void strcpy_bad1() { +void strcpy1_bad() { char laundered_source[50]; auto source = __infer_taint_source().c_str(); auto copy = strcpy(laundered_source, source); __infer_taint_sink(copy); } -void strcpy_bad2() { +void strcpy2_bad() { char laundered_source[50]; auto source = __infer_taint_source().c_str(); strcpy(laundered_source, source); @@ -71,81 +71,81 @@ void memchr_bad() { __infer_taint_sink(laundered_source); } -void constructor_bad1() { +void constructor1_bad() { auto source = __infer_taint_source(); auto laundered_source = std::string(source); __infer_taint_sink(laundered_source); } -void constructor_bad2() { +void constructor2_bad() { auto source = __infer_taint_source(); auto laundered_source = std::string(source, 0, 5); __infer_taint_sink(laundered_source); } -void constructor_bad3() { +void FN_constructor3_bad() { auto source = __infer_taint_source(); auto laundered_source = std::string(source.begin(), source.begin() + 5); __infer_taint_sink(laundered_source); } -void concat_bad1() { +void concat1_bad() { auto source = __infer_taint_source(); source += "other string"; __infer_taint_sink(source); } -void concat_bad2() { +void concat2_bad() { auto source = __infer_taint_source(); auto laundered_source = std::string("string"); laundered_source += source; __infer_taint_sink(laundered_source); } -void concat_bad3() { +void concat3_bad() { auto source = __infer_taint_source(); __infer_taint_sink(source += "string"); } -void append_bad1() { +void append1_bad() { auto source = __infer_taint_source(); __infer_taint_sink(std::string("string").append(source)); } -void append_bad2() { +void append2_bad() { auto source = __infer_taint_source(); source.append("string"); __infer_taint_sink(source); } -void assign_bad1() { +void assign1_bad() { auto source = __infer_taint_source(); __infer_taint_sink(std::string("string").assign(source)); } -void assign_bad2() { +void assign2_bad() { auto source = __infer_taint_source(); source.assign("string"); __infer_taint_sink(source); } -void insert_bad1() { +void insert1_bad() { auto source = __infer_taint_source(); __infer_taint_sink(std::string("string").assign(source)); } -void insert_bad2() { +void insert2_bad() { auto source = __infer_taint_source(); source.insert(0, "string"); __infer_taint_sink(source); } -void replace_bad1() { +void replace1_bad() { auto source = __infer_taint_source(); __infer_taint_sink(std::string("string").replace(0, 5, source)); } -void replace_bad2() { +void replace2_bad() { auto source = __infer_taint_source(); source.replace(0, 5, "string"); __infer_taint_sink(source); @@ -182,25 +182,25 @@ Formatter format3(std::string fmt, Args&&... args); template Formatter* format4(std::string fmt, Args&&... args); -void format_bad1() { +void format1_bad() { auto source = __infer_taint_source(); auto laundered_source = format1("%s", source).str(); __infer_taint_sink(laundered_source); } -void format_bad2() { +void format2_bad() { auto source = __infer_taint_source(); auto laundered_source = format2("%s", source)->str(); __infer_taint_sink(laundered_source); } -void format_bad3() { +void format3_bad() { auto source = __infer_taint_source(); auto laundered_source = format3("%s", source).str(); __infer_taint_sink(laundered_source); } -void format_bad4() { +void format4_bad() { auto source = __infer_taint_source(); auto laundered_source = format4("%s", source)->str(); __infer_taint_sink(laundered_source);