@@ -535,7 +535,7 @@ and exp =
535535 | Question of exp * exp * exp * typ
536536 (* * (a ? b : c) operation. Includes
537537 the type of the result *)
538- | CastE of typ * exp (* * Use {!mkCast} to make casts *)
538+ | CastE of castkind * typ * exp (* * Use {!mkCast} to make casts *)
539539
540540 | AddrOf of lval (* * Always use {!mkAddrOf} to
541541 construct one of these. Apply to an
@@ -615,8 +615,15 @@ and binop =
615615 | LAnd (* * logical and *)
616616 | LOr (* * logical or *)
617617
618-
619-
618+ and castkind =
619+ | Explicit (* * Explicit conversion. @see C11 6.3.1. *)
620+ | IntegerPromotion (* * Integer promotion. @see C11 6.3.1.1.2. *)
621+ | DefaultArgumentPromotion (* * Default argument promotion. @see C11 6.5.2.2.6. *)
622+ | ArithmeticConversion (* * Usual arithmetic conversion. @see C11 6.3.1.8. *)
623+ | ConditionalConversion (* * Conditional conversion (non-standard terminology). @see C11 6.5.15.5 and 6.5.15.6. *)
624+ | PointerConversion (* * Pointer conversion (non-standard). @see C11 6.5.6.8, 6.5.8.5 and 6.5.9.5. *)
625+ | Implicit (* * Implicit conversion. @see C11 6.3.1, 6.5.2.2.7, 6.5.2.4.2, 6.5.16.1.2, 6.5.16.2.3, 6.7.9.11, 6.8.4.2.5 and 6.8.6.4.3. *)
626+ | Internal (* * CIL-internal conversion (non-standard). *)
620627
621628(* * An lvalue denotes the contents of a range of memory addresses. This range
622629 is denoted as a host object along with an offset within the object. The
@@ -1729,7 +1736,7 @@ let mkForIncr ~(iter : varinfo) ~(first: exp) ~stopat:(past: exp) ~(incr: exp)
17291736
17301737
17311738let rec stripCasts (e : exp ) =
1732- match e with CastE (_ , e' ) -> stripCasts e' | _ -> e
1739+ match e with CastE (_ , _ , e' ) -> stripCasts e' | _ -> e
17331740
17341741
17351742
@@ -1909,7 +1916,7 @@ let getParenthLevel (e: exp) =
19091916 (* Unary *)
19101917 | Real _ -> 30
19111918 | Imag _ -> 30
1912- | CastE (_ ,_ ) -> 30
1919+ | CastE (_ ,_ , _ ) -> 30
19131920 | AddrOf (_ ) -> 30
19141921 | AddrOfLabel (_ ) -> 30
19151922 | StartOf (_ ) -> 30
@@ -1991,7 +1998,7 @@ let rec typeOf (e: exp) : typ =
19911998 | UnOp (_, _, t)
19921999 | BinOp (_, _, _, t)
19932000 | Question (_, _, _, t)
1994- | CastE (t , _ ) -> t
2001+ | CastE (_ , t , _ ) -> t
19952002 | AddrOf (lv ) -> TPtr (typeOfLval lv, [] )
19962003 | AddrOfLabel (lv ) -> voidPtrType
19972004 | StartOf (lv ) -> begin
@@ -2215,7 +2222,7 @@ let rec getInteger (e:exp) : cilint option =
22152222 | Const (CInt (n , ik , _ )) -> Some (mkCilintIk ik n)
22162223 | Const (CChr c ) -> getInteger (Const (charConstToInt c))
22172224 | Const (CEnum(v , _ , _ )) -> getInteger v
2218- | CastE (t , e ) -> begin
2225+ | CastE (_ , t , e ) -> begin
22192226 (* Handle any truncation due to cast. We optimistically ignore
22202227 loss-of-precision due to floating-point casts. *)
22212228 let mkInt ik n = Some (fst (truncateCilint ik n)) in
@@ -2622,19 +2629,19 @@ and constFold (machdep: bool) (e: exp) : exp =
26222629 | _ -> constFold machdep (AlignOf (typeOf e))
26232630 end
26242631
2625- | CastE ( it,
2626- AddrOf (Mem (CastE (TPtr (bt, _), z)), off))
2632+ | CastE (k, it,
2633+ AddrOf (Mem (CastE (_, TPtr (bt, _), z)), off))
26272634 when machdep && isZero z -> begin
26282635 try
26292636 let start, width = bitsOffset bt off in
26302637 if start mod 8 <> 0 then
26312638 E. s (error " Using offset of bitfield" );
2632- constFold machdep (CastE (it, (kinteger ! kindOfSizeOf (start / 8 ))))
2639+ constFold machdep (CastE (k, it, (kinteger ! kindOfSizeOf (start / 8 ))))
26332640 with SizeOfError _ -> e
26342641 end
26352642
26362643
2637- | CastE (t , e ) -> begin
2644+ | CastE (k , t , e ) -> begin
26382645 match constFold machdep e, unrollType t with
26392646 (* Might truncate silently *)
26402647 | Const (CInt (i,k,_)), TInt (nk,a)
@@ -2643,7 +2650,7 @@ and constFold (machdep: bool) (e: exp) : exp =
26432650 when (dropAttributes [" const" ; " pconst" ] a) = [] ->
26442651 let i', _ = truncateCilint nk (mkCilintIk k i) in
26452652 Const (CInt (i', nk, None ))
2646- | e' , _ -> CastE (t, e')
2653+ | e' , _ -> CastE (k, t, e')
26472654 end
26482655 | Lval lv -> Lval (constFoldLval machdep lv)
26492656 | AddrOf lv -> AddrOf (constFoldLval machdep lv)
@@ -2765,7 +2772,7 @@ let isArrayType t =
27652772 An integer constant expr with value 0, or such an expr cast to void *, is called a null pointer constant. *)
27662773let isNullPtrConstant e =
27672774 let rec isNullPtrConstant = function
2768- | CastE (TPtr (TVoid [] , [] ), e ) -> isNullPtrConstant e (* no qualifiers allowed on void or ptr *)
2775+ | CastE (_ , TPtr (TVoid [] , [] ), e ) -> isNullPtrConstant e (* no qualifiers allowed on void or ptr *)
27692776 | e -> isZero e
27702777 in
27712778 isNullPtrConstant (constFold true e)
@@ -2781,7 +2788,7 @@ let rec isConstant = function
27812788 | Real e -> isConstant e
27822789 | Imag e -> isConstant e
27832790 | SizeOf _ | SizeOfE _ | SizeOfStr _ | AlignOf _ | AlignOfE _ -> true
2784- | CastE (_ , e ) -> isConstant e
2791+ | CastE (_ , _ , e ) -> isConstant e
27852792 | AddrOf (Var vi, off) | StartOf (Var vi, off)
27862793 -> vi.vglob && isConstantOffset off
27872794 | AddrOf (Mem e, off) | StartOf (Mem e, off)
@@ -2875,6 +2882,17 @@ let d_binop () b =
28752882 | LAnd -> text " &&"
28762883 | LOr -> text " ||"
28772884
2885+ let d_castkind () k =
2886+ match k with
2887+ | Explicit -> text " Explicit"
2888+ | IntegerPromotion -> text " IntegerPromotion"
2889+ | DefaultArgumentPromotion -> text " DefaultArgumentPromotion"
2890+ | ArithmeticConversion -> text " ArithmeticConversion"
2891+ | ConditionalConversion -> text " ConditionalConversion"
2892+ | PointerConversion -> text " PointerConversion"
2893+ | Implicit -> text " Implicit"
2894+ | Internal -> text " Internal"
2895+
28782896let invalidStmt = mkStmt (Instr [] )
28792897
28802898(* * Construct a hash with the builtins *)
@@ -3405,9 +3423,12 @@ class defaultCilPrinterClass : cilPrinter = object (self)
34053423 ++ text " : "
34063424 ++ (self#pExpPrec level () e3)
34073425
3408- | CastE (t ,e ) ->
3426+ | CastE (k , t ,e ) ->
34093427 text " ("
3410- ++ self#pType None () t
3428+ ++ self#pType None () t (* TODO: option to not print implicit casts? *)
3429+ (* ++ text "/*"
3430+ ++ d_castkind () k (* convenient for debugging castkinds *)
3431+ ++ text "*/" *)
34113432 ++ text " )"
34123433 ++ self#pExpPrec level () e
34133434
@@ -3698,7 +3719,7 @@ class defaultCilPrinterClass : cilPrinter = object (self)
36983719 in
36993720 let patchArgNotUseVLACast exp =
37003721 match exp with
3701- | CastE (t , e ) -> CastE (patchTypeNotVLA t, e)
3722+ | CastE (k , t , e ) -> CastE (k, patchTypeNotVLA t, e)
37023723 | e -> e
37033724 in
37043725 self#pLineDirective l
@@ -4698,7 +4719,7 @@ class plainCilPrinterClass =
46984719 ++ unalign)
46994720 ++ text " )"
47004721
4701- | CastE (t ,e ) -> dprintf " CastE(@[%a,@?%a@ ])" self#pOnlyType t self#pExp e
4722+ | CastE (k , t ,e ) -> dprintf " CastE(@[%a,@?%a,@?%a@ ])" d_castkind k self#pOnlyType t self#pExp e
47024723
47034724 | UnOp (u ,e1 ,_ ) ->
47044725 dprintf " UnOp(@[%a,@?%a@])"
@@ -5242,9 +5263,9 @@ and childrenExp (vis: cilVisitor) (e: exp) : exp =
52425263 | Question (e1 , e2 , e3 , t ) ->
52435264 let e1' = vExp e1 in let e2' = vExp e2 in let e3' = vExp e3 in let t' = vTyp t in
52445265 if e1' != e1 || e2' != e2 || e3' != e3 || t' != t then Question (e1',e2',e3',t') else e
5245- | CastE (t , e1 ) ->
5266+ | CastE (k , t , e1 ) ->
52465267 let t' = vTyp t in let e1' = vExp e1 in
5247- if t' != t || e1' != e1 then CastE (t', e1') else e
5268+ if t' != t || e1' != e1 then CastE (k, t', e1') else e
52485269 | AddrOf lv ->
52495270 let lv' = vLval lv in
52505271 if lv' != lv then AddrOf lv' else e
@@ -6097,7 +6118,7 @@ let getCompField (cinfo:compinfo) (fieldName:string) : fieldinfo =
60976118 (List. find (fun fi -> fi.fname = fieldName) cinfo.cfields)
60986119
60996120
6100- let mkCastT ~(e : exp ) ~(oldt : typ ) ~(newt : typ ) =
6121+ let mkCastT ~(kind : castkind ) ~( e : exp ) ~(oldt : typ ) ~(newt : typ ) =
61016122 (* Do not remove old casts because they are conversions !!! *)
61026123 if Util. equals (typeSig oldt) (typeSig newt) then begin
61036124 e
@@ -6109,11 +6130,11 @@ let mkCastT ~(e: exp) ~(oldt: typ) ~(newt: typ) =
61096130 let v = if compare i zero_cilint = 0 then zero_cilint else one_cilint in
61106131 Const (CInt (v, IBool , None ))
61116132 | TInt (newik , [] ), Const (CInt(i , _ , _ )) -> kintegerCilint newik i
6112- | _ -> CastE (newt,e)
6133+ | _ -> CastE (kind, newt,e)
61136134 end
61146135
6115- let mkCast ~(e : exp ) ~(newt : typ ) =
6116- mkCastT ~e: e ~oldt: (typeOf e) ~newt: newt
6136+ let mkCast ~kind ~ (e : exp ) ~(newt : typ ) =
6137+ mkCastT ~kind ~ e: e ~oldt: (typeOf e) ~newt: newt
61176138
61186139type existsAction =
61196140 ExistsTrue (* We have found it *)
@@ -6230,7 +6251,7 @@ let rec makeZeroInit (t: typ) : init =
62306251 CompoundInit (t', [] )
62316252
62326253 | TPtr _ as t ->
6233- SingleInit (if ! insertImplicitCasts then mkCast ~e: zero ~newt: t else zero)
6254+ SingleInit (if ! insertImplicitCasts then mkCast ~kind: Internal ~ e: zero ~newt: t else zero)
62346255 | x -> E. s (unimp " Cannot initialize type: %a" d_type x)
62356256
62366257
0 commit comments