Revert "[frontend][clang][RFC] fix translation of enum constant"

Reviewed By: ezgicicek

Differential Revision: D21662044

fbshipit-source-id: ecaf0c36a
master
Dulma Churchill 5 years ago committed by Facebook GitHub Bot
parent b394ed0400
commit 61869b8edb

@ -867,47 +867,47 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s
decl_ref_trans ~context:DeclRefExpr trans_state stmt_info decl_ref decl_ref_trans ~context:DeclRefExpr trans_state stmt_info decl_ref
and enum_constant_trans trans_state decl_ref = (** evaluates an enum constant *)
let typ = and enum_const_eval context enum_constant_pointer prev_enum_constant_opt zero =
let {CContext.tenv} = trans_state.context in match CAst_utils.get_decl enum_constant_pointer with
let _, _, qual_type = CAst_utils.get_info_from_decl_ref decl_ref in | Some (Clang_ast_t.EnumConstantDecl (_, _, _, enum_constant_decl_info)) -> (
CType_decl.qual_type_to_sil_type tenv qual_type match enum_constant_decl_info.Clang_ast_t.ecdi_init_expr with
in | Some stmt ->
let zero () = mk_trans_result (Exp.Const (Const.Cint IntLit.zero), typ) empty_control in expression_trans context stmt
(* translate enum declaration statements *) | None -> (
let rec trans_enum_decl ~prev_decl_pointer_opt decl_pointer = match prev_enum_constant_opt with
match CAst_utils.get_decl decl_pointer with | Some prev_constant_pointer ->
| Some (Clang_ast_t.EnumConstantDecl (_, _, _, enum_constant_decl_info)) -> ( let previous_exp = get_enum_constant_expr context prev_constant_pointer in
match enum_constant_decl_info.Clang_ast_t.ecdi_init_expr with CArithmetic_trans.sil_const_plus_one previous_exp
| Some stmt ->
instruction trans_state stmt
| None -> (
match prev_decl_pointer_opt with
| Some prev_decl_pointer ->
let ({return= exp, typ} as trans_result) = trans_with_cache prev_decl_pointer in
{trans_result with return= (CArithmetic_trans.sil_const_plus_one exp, typ)}
| None ->
zero () ) )
| _ ->
zero ()
(* try looking up from cache before calling [trans_enum_decl] *)
and trans_with_cache decl_pointer =
try
let prev_decl_pointer_opt, cached_exp = CAst_utils.get_enum_constant_exp_exn decl_pointer in
match cached_exp with
| Some exp ->
mk_trans_result (exp, typ) empty_control
| None -> | None ->
let trans_result = trans_enum_decl ~prev_decl_pointer_opt decl_pointer in zero ) )
( match fst trans_result.return with | _ ->
| Exp.Const _ as exp -> zero
CAst_utils.update_enum_map_exn decl_pointer exp
| _ ->
() ) ; (** get the sil value of the enum constant from the map or by evaluating it *)
trans_result and get_enum_constant_expr context enum_constant_pointer =
with Not_found_s _ | Caml.Not_found -> zero () let zero = Exp.Const (Const.Cint IntLit.zero) in
in try
trans_with_cache decl_ref.Clang_ast_t.dr_decl_pointer let prev_enum_constant_opt, sil_exp_opt =
CAst_utils.get_enum_constant_exp_exn enum_constant_pointer
in
match sil_exp_opt with
| Some exp ->
exp
| None ->
let exp = enum_const_eval context enum_constant_pointer prev_enum_constant_opt zero in
CAst_utils.update_enum_map_exn enum_constant_pointer exp ;
exp
with Not_found_s _ | Caml.Not_found -> zero
and enum_constant_trans trans_state decl_ref =
let context = trans_state.context in
let _, _, qual_type = CAst_utils.get_info_from_decl_ref decl_ref in
let typ = CType_decl.qual_type_to_sil_type context.CContext.tenv qual_type in
let const_exp = get_enum_constant_expr context decl_ref.Clang_ast_t.dr_decl_pointer in
mk_trans_result (const_exp, typ) empty_control
and arraySubscriptExpr_trans trans_state expr_info stmt_list = and arraySubscriptExpr_trans trans_state expr_info stmt_list =
@ -3898,6 +3898,12 @@ module CTrans_funct (F : CModule_type.CFrontend) : CModule_type.CTranslation = s
exec_trans_instrs trans_state stmt_trans_fun exec_trans_instrs trans_state stmt_trans_fun
and expression_trans context stmt =
let trans_state = CTrans_utils.default_trans_state context in
let res_trans_stmt = instruction trans_state stmt in
fst res_trans_stmt.return
let instructions_trans context body extra_instrs exit_node ~is_destructor_wrapper = let instructions_trans context body extra_instrs exit_node ~is_destructor_wrapper =
let default_trans_state = CTrans_utils.default_trans_state context in let default_trans_state = CTrans_utils.default_trans_state context in
let trans_state = {default_trans_state with succ_nodes= [exit_node]} in let trans_state = {default_trans_state with succ_nodes= [exit_node]} in

@ -22,7 +22,7 @@ void compare_global_const_enum_Bad() {
arr[10] = 1; arr[10] = 1;
} }
void compare_global_const_enum_Good() { void compare_global_const_enum_Good_FP() {
char arr[10]; char arr[10];
if (global_const > 10) if (global_const > 10)
arr[10] = 1; arr[10] = 1;

@ -127,9 +127,8 @@ codetoanalyze/c/bufferoverrun/get_field.c, call_get_v2_Bad, 8, BUFFER_OVERRUN_L5
codetoanalyze/c/bufferoverrun/get_field.c, call_get_v2_Good_FP, 8, BUFFER_OVERRUN_L5, no_bucket, ERROR, [<Offset trace>,Call,Assignment,<Length trace>,Array declaration,Array access: Offset: [-oo, +oo] Size: 10] codetoanalyze/c/bufferoverrun/get_field.c, call_get_v2_Good_FP, 8, BUFFER_OVERRUN_L5, no_bucket, ERROR, [<Offset trace>,Call,Assignment,<Length trace>,Array declaration,Array access: Offset: [-oo, +oo] Size: 10]
codetoanalyze/c/bufferoverrun/get_field.c, call_get_v_Bad, 8, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Offset trace>,Assignment,Call,Parameter `l->next->prev->v`,Assignment,<Length trace>,Array declaration,Array access: Offset: 10 Size: 10] codetoanalyze/c/bufferoverrun/get_field.c, call_get_v_Bad, 8, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Offset trace>,Assignment,Call,Parameter `l->next->prev->v`,Assignment,<Length trace>,Array declaration,Array access: Offset: 10 Size: 10]
codetoanalyze/c/bufferoverrun/get_field.c, make_many_locations, 1, CONDITION_ALWAYS_TRUE, no_bucket, WARNING, [Here] codetoanalyze/c/bufferoverrun/get_field.c, make_many_locations, 1, CONDITION_ALWAYS_TRUE, no_bucket, WARNING, [Here]
codetoanalyze/c/bufferoverrun/global.c, compare_global_const_enum_Bad, 2, CONDITION_ALWAYS_TRUE, no_bucket, WARNING, [Here]
codetoanalyze/c/bufferoverrun/global.c, compare_global_const_enum_Bad, 3, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Length trace>,Array declaration,Array access: Offset: 10 Size: 10] codetoanalyze/c/bufferoverrun/global.c, compare_global_const_enum_Bad, 3, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Length trace>,Array declaration,Array access: Offset: 10 Size: 10]
codetoanalyze/c/bufferoverrun/global.c, compare_global_const_enum_Good, 2, CONDITION_ALWAYS_FALSE, no_bucket, WARNING, [Here] codetoanalyze/c/bufferoverrun/global.c, compare_global_const_enum_Good_FP, 3, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Length trace>,Array declaration,Array access: Offset: 10 Size: 10]
codetoanalyze/c/bufferoverrun/global.c, compare_global_variable_bad, 3, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Length trace>,Array declaration,Array access: Offset: 10 Size: 10] codetoanalyze/c/bufferoverrun/global.c, compare_global_variable_bad, 3, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Length trace>,Array declaration,Array access: Offset: 10 Size: 10]
codetoanalyze/c/bufferoverrun/global.c, copyfilter_Good_FP, 3, INTEGER_OVERFLOW_L5, no_bucket, ERROR, [<LHS trace>,Assignment,Binary operation: ([0, +oo] + 1):signed32] codetoanalyze/c/bufferoverrun/global.c, copyfilter_Good_FP, 3, INTEGER_OVERFLOW_L5, no_bucket, ERROR, [<LHS trace>,Assignment,Binary operation: ([0, +oo] + 1):signed32]
codetoanalyze/c/bufferoverrun/global.c, use_global_const_ten_Bad, 2, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Offset trace>,Assignment,<Length trace>,Array declaration,Array access: Offset: 10 Size: 5] codetoanalyze/c/bufferoverrun/global.c, use_global_const_ten_Bad, 2, BUFFER_OVERRUN_L1, no_bucket, ERROR, [<Offset trace>,Assignment,<Length trace>,Array declaration,Array access: Offset: 10 Size: 5]

Loading…
Cancel
Save