@@ -359,29 +359,7 @@ std::string expr2ct::convert_rec(
359359 }
360360 else if (src.id ()==ID_struct)
361361 {
362- const struct_typet &struct_type=to_struct_type (src);
363-
364- std::string dest=q+" struct" ;
365-
366- const irep_idt &tag=struct_type.get_tag ();
367- if (tag!=" " ) dest+=" " +id2string (tag);
368- dest+=" {" ;
369-
370- for (struct_typet::componentst::const_iterator
371- it=struct_type.components ().begin ();
372- it!=struct_type.components ().end ();
373- it++)
374- {
375- dest+=' ' ;
376- dest+=convert_rec (it->type (), c_qualifierst (), id2string (it->get_name ()));
377- dest+=' ;' ;
378- }
379-
380- dest+=" }" ;
381-
382- dest+=d;
383-
384- return dest;
362+ return convert_struct_type (src, q, d);
385363 }
386364 else if (src.id ()==ID_incomplete_struct)
387365 {
@@ -517,18 +495,7 @@ std::string expr2ct::convert_rec(
517495 }
518496 else if (src.id ()==ID_array)
519497 {
520- // The [...] gets attached to the declarator.
521- std::string array_suffix;
522-
523- if (to_array_type (src).size ().is_nil ())
524- array_suffix=" []" ;
525- else
526- array_suffix=" [" +convert (to_array_type (src).size ())+" ]" ;
527-
528- // This won't really parse without declarator.
529- // Note that qualifiers are passed down.
530- return convert_rec (
531- src.subtype (), qualifiers, declarator+array_suffix);
498+ return convert_array_type (src, qualifiers, declarator);
532499 }
533500 else if (src.id ()==ID_incomplete_array)
534501 {
@@ -708,6 +675,160 @@ std::string expr2ct::convert_rec(
708675
709676/* ******************************************************************\
710677
678+ Function: expr2ct::convert_struct_type
679+
680+ Inputs:
681+ src - the struct type being converted
682+ qualifiers - any qualifiers on the type
683+ declarator - the declarator on the type
684+
685+ Outputs: Returns a type declaration for a struct, containing the
686+ body of the struct and in that body the padding parameters.
687+
688+ Purpose: To generate C-like string for defining the given struct
689+
690+ \*******************************************************************/
691+ std::string expr2ct::convert_struct_type (
692+ const typet &src,
693+ const std::string &qualifiers_str,
694+ const std::string &declarator_str)
695+ {
696+ return convert_struct_type (src, qualifiers_str, declarator_str, true , true );
697+ }
698+
699+ /* ******************************************************************\
700+
701+ Function: expr2ct::convert_struct_type
702+
703+ Inputs:
704+ src - the struct type being converted
705+ qualifiers - any qualifiers on the type
706+ declarator - the declarator on the type
707+ inc_struct_body - when generating the code, should we include
708+ a complete definition of the struct
709+ inc_padding_components - should the padding parameters be included
710+ Note this only makes sense if inc_struct_body
711+
712+ Outputs: Returns a type declaration for a struct, optionally containing the
713+ body of the struct (and in that body, optionally the padding
714+ parameters).
715+
716+ Purpose: To generate C-like string for declaring (or defining) the given struct
717+
718+ \*******************************************************************/
719+ std::string expr2ct::convert_struct_type (
720+ const typet &src,
721+ const std::string &qualifiers,
722+ const std::string &declarator,
723+ bool inc_struct_body,
724+ bool inc_padding_components)
725+ {
726+ // Either we are including the body (in which case it makes sense to include
727+ // or exclude the parameters) or there is no body so therefore we definitely
728+ // shouldn't be including the parameters
729+ assert (inc_struct_body || !inc_padding_components);
730+
731+ const struct_typet &struct_type=to_struct_type (src);
732+
733+ std::string dest=qualifiers+" struct" ;
734+
735+ const irep_idt &tag=struct_type.get_tag ();
736+ if (tag!=" " )
737+ dest+=" " +id2string (tag);
738+
739+ if (inc_struct_body)
740+ {
741+ dest+=" {" ;
742+
743+ for (const struct_union_typet::componentt &component :
744+ struct_type.components ())
745+ {
746+ // Skip padding parameters unless we including them
747+ if (component.get_is_padding () && !inc_padding_components)
748+ {
749+ continue ;
750+ }
751+
752+ dest+=' ' ;
753+ dest+=convert_rec (
754+ component.type (),
755+ c_qualifierst (),
756+ id2string (component.get_name ()));
757+ dest+=' ;' ;
758+ }
759+
760+ dest+=" }" ;
761+ }
762+
763+ dest+=declarator;
764+
765+ return dest;
766+ }
767+
768+ /* ******************************************************************\
769+
770+ Function: expr2ct::convert_array_type
771+
772+ Inputs:
773+ src - The array type to convert
774+ qualifier
775+ declarator_str
776+
777+ Outputs: A C-like type declaration of an array
778+
779+ Purpose: To generate a C-like type declaration of an array. Includes
780+ the size of the array in the []
781+
782+ \*******************************************************************/
783+
784+ std::string expr2ct::convert_array_type (
785+ const typet &src,
786+ const c_qualifierst &qualifiers,
787+ const std::string &declarator_str)
788+ {
789+ return convert_array_type (src, qualifiers, declarator_str, true );
790+ }
791+
792+ /* ******************************************************************\
793+
794+ Function: expr2ct::convert_array_type
795+
796+ Inputs:
797+ src - The array type to convert
798+ qualifier
799+ declarator_str
800+ inc_size_if_possible - Should the generated string include
801+ the size of the array (if it is known).
802+
803+ Outputs: A C-like type declaration of an array
804+
805+ Purpose: To generate a C-like type declaration of an array. Optionally
806+ can include or exclude the size of the array in the []
807+
808+ \*******************************************************************/
809+
810+ std::string expr2ct::convert_array_type (
811+ const typet &src,
812+ const c_qualifierst &qualifiers,
813+ const std::string &declarator_str,
814+ bool inc_size_if_possible)
815+ {
816+ // The [...] gets attached to the declarator.
817+ std::string array_suffix;
818+
819+ if (to_array_type (src).size ().is_nil () || !inc_size_if_possible)
820+ array_suffix=" []" ;
821+ else
822+ array_suffix=" [" +convert (to_array_type (src).size ())+" ]" ;
823+
824+ // This won't really parse without declarator.
825+ // Note that qualifiers are passed down.
826+ return convert_rec (
827+ src.subtype (), qualifiers, declarator_str+array_suffix);
828+ }
829+
830+ /* ******************************************************************\
831+
711832Function: expr2ct::convert_typecast
712833
713834 Inputs:
@@ -2147,11 +2268,7 @@ std::string expr2ct::convert_constant(
21472268 }
21482269 else if (type.id ()==ID_bool)
21492270 {
2150- // C doesn't really have these
2151- if (src.is_true ())
2152- dest=" TRUE" ;
2153- else
2154- dest=" FALSE" ;
2271+ dest=convert_constant_bool (src.is_true ());
21552272 }
21562273 else if (type.id ()==ID_unsignedbv ||
21572274 type.id ()==ID_signedbv ||
@@ -2167,11 +2284,7 @@ std::string expr2ct::convert_constant(
21672284
21682285 if (type.id ()==ID_c_bool)
21692286 {
2170- // C doesn't really have these
2171- if (int_value!=0 )
2172- dest=" TRUE" ;
2173- else
2174- dest=" FALSE" ;
2287+ dest=convert_constant_bool (int_value!=0 );
21752288 }
21762289 else if (type==char_type () && type!=signed_int_type () && type!=unsigned_int_type ())
21772290 {
@@ -2324,6 +2437,28 @@ std::string expr2ct::convert_constant(
23242437
23252438/* ******************************************************************\
23262439
2440+ Function: expr2ct::convert_constant_bool
2441+
2442+ Inputs:
2443+ boolean_value - The value of the constant bool expression
2444+
2445+ Outputs: Returns a C-like representation of the boolean value,
2446+ e.g. TRUE or FALSE.
2447+
2448+ Purpose: To get the C-like representation of a given boolean value.
2449+
2450+ \*******************************************************************/
2451+ std::string expr2ct::convert_constant_bool (bool boolean_value)
2452+ {
2453+ // C doesn't really have these
2454+ if (boolean_value)
2455+ return " TRUE" ;
2456+ else
2457+ return " FALSE" ;
2458+ }
2459+
2460+ /* ******************************************************************\
2461+
23272462Function: expr2ct::convert_struct
23282463
23292464 Inputs:
@@ -2337,6 +2472,31 @@ Function: expr2ct::convert_struct
23372472std::string expr2ct::convert_struct (
23382473 const exprt &src,
23392474 unsigned &precedence)
2475+ {
2476+ return convert_struct (src, precedence, true );
2477+ }
2478+
2479+ /* ******************************************************************\
2480+
2481+ Function: expr2ct::convert_struct
2482+
2483+ Inputs:
2484+ src - The struct declaration expression
2485+ precedence
2486+ include_padding_components - Should the generated C code
2487+ include the padding members added
2488+ to structs for GOTOs benifit
2489+
2490+ Outputs: A string representation of the struct expression
2491+
2492+ Purpose: To generate a C-like string representing a struct. Can optionally
2493+ include the padding parameters.
2494+
2495+ \*******************************************************************/
2496+ std::string expr2ct::convert_struct (
2497+ const exprt &src,
2498+ unsigned &precedence,
2499+ bool include_padding_components)
23402500{
23412501 const typet full_type=ns.follow (src.type ());
23422502
@@ -2360,14 +2520,18 @@ std::string expr2ct::convert_struct(
23602520 bool newline=false ;
23612521 size_t last_size=0 ;
23622522
2363- for (struct_typet::componentst::const_iterator
2364- c_it=components.begin ();
2365- c_it!=components.end ();
2366- c_it++)
2523+ for (const struct_union_typet::componentt &component :
2524+ struct_type.components ())
23672525 {
23682526 if (o_it->type ().id ()==ID_code)
23692527 continue ;
23702528
2529+ if (component.get_is_padding () && !include_padding_components)
2530+ {
2531+ ++o_it;
2532+ continue ;
2533+ }
2534+
23712535 if (first)
23722536 first=false ;
23732537 else
@@ -2391,7 +2555,7 @@ std::string expr2ct::convert_struct(
23912555 newline=false ;
23922556
23932557 dest+=' .' ;
2394- dest+=c_it-> get_string (ID_name);
2558+ dest+=component. get_string (ID_name);
23952559 dest+=' =' ;
23962560 dest+=tmp;
23972561
0 commit comments