From 0bbdf639573a04f921b0a09c98bc02e62a1e7940 Mon Sep 17 00:00:00 2001 From: Jules Villard Date: Tue, 1 May 2018 11:43:58 -0700 Subject: [PATCH] [clang] do not attempt to translate pointer to member constructs Summary: C++... seemsalittlecrazy Reviewed By: sblackshear Differential Revision: D7815648 fbshipit-source-id: f36ac4f --- infer/src/clang/cArithmetic_trans.ml | 9 ++-- infer/src/clang/cTrans.ml | 41 +++++++++------ .../cpp/shared/reference/ptr_mem.cpp | 4 +- .../cpp/shared/reference/ptr_mem.cpp.dot | 52 ++++--------------- 4 files changed, 41 insertions(+), 65 deletions(-) diff --git a/infer/src/clang/cArithmetic_trans.ml b/infer/src/clang/cArithmetic_trans.ml index 45cfc7bf2..29cbdb0ef 100644 --- a/infer/src/clang/cArithmetic_trans.ml +++ b/infer/src/clang/cArithmetic_trans.ml @@ -70,11 +70,12 @@ let binary_operation_instruction source_range boi ((e1, t1) as e1_with_typ) typ an integer offset, which is itself semantically ok though too low-level, but the translation of the argument expressions does not compute such offsets and instead passes the member pointer at type 'void'. *) - | `PtrMemD -> - (binop_exp Binop.PlusPI, []) + | `PtrMemD | `PtrMemI -> - let id = Ident.create_fresh Ident.knormal in - (Exp.BinOp (PlusPI, Exp.Var id, e2), [Sil.Load (id, e1, typ, loc)]) + CFrontend_config.unimplemented __POS__ source_range + "Pointer-to-member constructs are unsupported. Got '%a'." + (Pp.to_string ~f:Clang_ast_j.string_of_binary_operator_info) + boi | `Add -> if Typ.is_pointer t1 then (binop_exp Binop.PlusPI, []) else if Typ.is_pointer t2 then (binop_exp ~change_order:true Binop.PlusPI, []) diff --git a/infer/src/clang/cTrans.ml b/infer/src/clang/cTrans.ml index 5554fd9df..29219caff 100644 --- a/infer/src/clang/cTrans.ml +++ b/infer/src/clang/cTrans.ml @@ -774,21 +774,30 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s res_trans - and decl_ref_trans trans_state pre_trans_result stmt_info decl_ref ~is_constructor_init = + and decl_ref_trans ?(is_constructor_init= false) ~source trans_state stmt_info decl_ref = L.(debug Capture Verbose) " priority node free = '%s'@\n@." (string_of_bool (PriorityNode.is_priority_free trans_state)) ; let decl_kind = decl_ref.Clang_ast_t.dr_kind in - match decl_kind with - | `EnumConstant -> + match (decl_kind, source) with + | `EnumConstant, _ -> enum_constant_trans trans_state decl_ref - | `Function -> + | `Function, _ -> function_deref_trans trans_state decl_ref - | `Var | `ImplicitParam | `ParmVar -> + | (`Var | `ImplicitParam | `ParmVar), _ -> var_deref_trans trans_state stmt_info decl_ref - | `Field | `ObjCIvar -> + | (`Field | `ObjCIvar), `MemberOrIvar pre_trans_result -> + (* a field outside of constructor initialization is probably a pointer to member, which we + do not support *) field_deref_trans trans_state stmt_info pre_trans_result decl_ref ~is_constructor_init - | `CXXMethod | `CXXConversion | `CXXConstructor | `CXXDestructor -> + | (`CXXMethod | `CXXConversion | `CXXConstructor | `CXXDestructor), _ -> + let pre_trans_result = + match source with + | `MemberOrIvar pre_trans_result -> + pre_trans_result + | `DeclRefExpr -> + empty_res_trans + in method_deref_trans trans_state pre_trans_result decl_ref stmt_info decl_kind | _ -> CFrontend_config.unimplemented __POS__ stmt_info.Clang_ast_t.si_source_range @@ -808,7 +817,7 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s | None -> assert false in - decl_ref_trans trans_state empty_res_trans stmt_info decl_ref ~is_constructor_init:false + decl_ref_trans ~source:`DeclRefExpr trans_state stmt_info decl_ref (** evaluates an enum constant *) @@ -899,10 +908,10 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s and binaryOperator_trans trans_state binary_operator_info stmt_info expr_info stmt_list = - let bok = - Clang_ast_j.string_of_binary_operator_kind binary_operator_info.Clang_ast_t.boi_kind - in - L.(debug Capture Verbose) " BinaryOperator '%s' " bok ; + L.(debug Capture Verbose) + " BinaryOperator '%a' " + (Pp.to_string ~f:Clang_ast_j.string_of_binary_operator_kind) + binary_operator_info.Clang_ast_t.boi_kind ; L.(debug Capture Verbose) " priority node free = '%s'@\n@." (string_of_bool (PriorityNode.is_priority_free trans_state)) ; @@ -1157,7 +1166,7 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s else tmp_res_trans in let res_trans_callee = - decl_ref_trans trans_state this_res_trans si decl_ref ~is_constructor_init:false + decl_ref_trans ~source:(`MemberOrIvar this_res_trans) trans_state si decl_ref in let res_trans = cxx_method_construct_call_trans trans_state_pri res_trans_callee params_stmt si @@ -2385,7 +2394,7 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s (* int p = X(1).field; *) let trans_state' = {trans_state with var_exp_typ= None} in let result_trans_exp_stmt = exec_with_glvalue_as_reference instruction trans_state' exp_stmt in - decl_ref_trans trans_state result_trans_exp_stmt stmt_info decl_ref ~is_constructor_init:false + decl_ref_trans ~source:(`MemberOrIvar result_trans_exp_stmt) trans_state stmt_info decl_ref and objCIvarRefExpr_trans trans_state stmt_info stmt_list obj_c_ivar_ref_expr_info = @@ -3447,8 +3456,8 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s let class_typ = match this_typ.Typ.desc with Tptr (t, _) -> t | _ -> assert false in {this_res_trans with exps= [(this_exp, class_typ)]} | `Member decl_ref -> - decl_ref_trans trans_state' this_res_trans child_stmt_info decl_ref - ~is_constructor_init:true + decl_ref_trans ~is_constructor_init:true ~source:(`MemberOrIvar this_res_trans) + trans_state' child_stmt_info decl_ref in let var_exp_typ = extract_exp_from_list var_res_trans.exps diff --git a/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp b/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp index f6fafad2a..9d7ee3fb6 100644 --- a/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp +++ b/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp @@ -29,9 +29,9 @@ struct List { E* E::*next_ptr; }; -int main() { - List l(&item::next); +void skip() { List l(&item::next); } +void noskip(List l) { item i; l.add(&i); l.add_byref(i); diff --git a/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp.dot b/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp.dot index 95b130414..79c8d24d6 100644 --- a/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp.dot +++ b/infer/tests/codetoanalyze/cpp/shared/reference/ptr_mem.cpp.dot @@ -1,28 +1,24 @@ /* @generated */ digraph cfg { -"main.fad58de7366495db4650cfefac2fcd61_1" [label="1: Start main\nFormals: \nLocals: i:item l:List \n DECLARE_LOCALS(&return,&i,&l); [line 32, column 1]\n " color=yellow style=filled] +"noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_1" [label="1: Start noskip\nFormals: l:List&(byval)\nLocals: i:item \n DECLARE_LOCALS(&return,&i); [line 34, column 1]\n " color=yellow style=filled] - "main.fad58de7366495db4650cfefac2fcd61_1" -> "main.fad58de7366495db4650cfefac2fcd61_6" ; -"main.fad58de7366495db4650cfefac2fcd61_2" [label="2: Exit main \n " color=yellow style=filled] + "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_1" -> "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_5" ; +"noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_2" [label="2: Exit noskip \n " color=yellow style=filled] -"main.fad58de7366495db4650cfefac2fcd61_3" [label="3: Call _fun_List_add_byref \n _=*&l:List [line 37, column 3]\n _fun_List_add_byref(&l:List&,&i:item&) [line 37, column 3]\n " shape="box"] +"noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_3" [label="3: Call _fun_List_add_byref \n n$0=*&l:List& [line 37, column 3]\n _=*n$0:List [line 37, column 3]\n _fun_List_add_byref(n$0:List&,&i:item&) [line 37, column 3]\n " shape="box"] - "main.fad58de7366495db4650cfefac2fcd61_3" -> "main.fad58de7366495db4650cfefac2fcd61_2" ; -"main.fad58de7366495db4650cfefac2fcd61_4" [label="4: Call _fun_List_add \n _=*&l:List [line 36, column 3]\n _fun_List_add(&l:List&,&i:item*) [line 36, column 3]\n " shape="box"] + "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_3" -> "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_2" ; +"noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_4" [label="4: Call _fun_List_add \n n$2=*&l:List& [line 36, column 3]\n _=*n$2:List [line 36, column 3]\n _fun_List_add(n$2:List&,&i:item*) [line 36, column 3]\n " shape="box"] - "main.fad58de7366495db4650cfefac2fcd61_4" -> "main.fad58de7366495db4650cfefac2fcd61_3" ; -"main.fad58de7366495db4650cfefac2fcd61_5" [label="5: DeclStmt \n _fun_item_item(&i:item*) [line 35, column 8]\n " shape="box"] + "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_4" -> "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_3" ; +"noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_5" [label="5: DeclStmt \n _fun_item_item(&i:item*) [line 35, column 8]\n " shape="box"] - "main.fad58de7366495db4650cfefac2fcd61_5" -> "main.fad58de7366495db4650cfefac2fcd61_4" ; -"main.fad58de7366495db4650cfefac2fcd61_6" [label="6: DeclStmt \n n$2=*-1.next:item* [line 33, column 17]\n _fun_List_List(&l:List*,n$2:void) [line 33, column 14]\n " shape="box"] - - - "main.fad58de7366495db4650cfefac2fcd61_6" -> "main.fad58de7366495db4650cfefac2fcd61_5" ; + "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_5" -> "noskip#6149941428299352091.c0e56085ae3c9567084b0f9e4211cfc0_4" ; "List#List#{15914538297308632075}.3434f5c53e6f70f530bf6d3beb27430e_1" [label="1: Start List_List\nFormals: this:List* next_ptr:void\nLocals: \n DECLARE_LOCALS(&return); [line 16, column 3]\n " color=yellow style=filled] @@ -38,36 +34,6 @@ digraph cfg { "List#List#{15914538297308632075}.3434f5c53e6f70f530bf6d3beb27430e_4" -> "List#List#{15914538297308632075}.3434f5c53e6f70f530bf6d3beb27430e_3" ; -"add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_1" [label="1: Start List_add\nFormals: this:List* e:item*\nLocals: \n DECLARE_LOCALS(&return); [line 18, column 3]\n " color=yellow style=filled] - - - "add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_1" -> "add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_4" ; -"add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_2" [label="2: Exit List_add \n " color=yellow style=filled] - - -"add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_3" [label="3: BinaryOperatorStmt: Assign \n n$0=*&this:List* [line 20, column 5]\n n$1=*&e:item* [line 20, column 12]\n *n$0.head:item*=n$1 [line 20, column 5]\n " shape="box"] - - - "add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_3" -> "add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_2" ; -"add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_4" [label="4: BinaryOperatorStmt: Assign \n n$2=*&e:item* [line 19, column 5]\n n$3=*&this:List* [line 19, column 9]\n n$4=*n$3.next_ptr:void [line 19, column 9]\n n$5=*n$2:item* [line 19, column 5]\n n$6=*&this:List* [line 19, column 20]\n n$7=*n$6.head:item* [line 19, column 20]\n *(n$5 + n$4):item*=n$7 [line 19, column 5]\n " shape="box"] - - - "add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_4" -> "add#List#(8886422348332570962).d7124ab68ff2274165f87f96f8efb745_3" ; -"add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_1" [label="1: Start List_add_byref\nFormals: this:List* e:item&\nLocals: \n DECLARE_LOCALS(&return); [line 23, column 3]\n " color=yellow style=filled] - - - "add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_1" -> "add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_4" ; -"add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_2" [label="2: Exit List_add_byref \n " color=yellow style=filled] - - -"add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_3" [label="3: BinaryOperatorStmt: Assign \n n$0=*&this:List* [line 25, column 5]\n n$1=*&e:item& [line 25, column 13]\n *n$0.head:item*=n$1 [line 25, column 5]\n " shape="box"] - - - "add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_3" -> "add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_2" ; -"add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_4" [label="4: BinaryOperatorStmt: Assign \n n$2=*&e:item& [line 24, column 5]\n n$3=*&this:List* [line 24, column 8]\n n$4=*n$3.next_ptr:void [line 24, column 8]\n n$5=*&this:List* [line 24, column 19]\n n$6=*n$5.head:item* [line 24, column 19]\n *(n$2 + n$4):item*=n$6 [line 24, column 5]\n " shape="box"] - - - "add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_4" -> "add_byref#List#(435356425820132485).163c5ed0bcef8861fe1a46383d99ea83_3" ; "item#item#{8704603758565933158}.444c1f007931991a5b2dfd25b7b090f5_1" [label="1: Start item_item\nFormals: this:item*\nLocals: \n DECLARE_LOCALS(&return); [line 9, column 8]\n " color=yellow style=filled]