note description: "Special optimization on calls where target is a basic type." legal: "See notice at end of class." status: "See notice at end of class." date: "$Date$" revision: "$Revision$" limitation: "We cannot handle `set_item', `copy', `standard_copy' or `deep_copy'% %because when called on attributes whose types are basic types we cannot% %store the result back to the attribute." class SPECIAL_FEATURES inherit BYTE_CONST SHARED_INCLUDE SHARED_TYPES SHARED_WORKBENCH feature -- Access has (feature_name_id: INTEGER; is_c_compilation: BOOLEAN; target_type: BASIC_A): BOOLEAN -- Does Current have `feature_name_id'? require valid_feature_name_id: feature_name_id > 0 do if is_c_compilation then c_type_table.search (feature_name_id) if c_type_table.found then function_type := c_type_table.found_item if target_type.is_character_32 then -- Do not inline "lower", "upper", "is_space" on CHARACTER_32 -- because the code is not generated inline. inspect function_type when lower_type, upper_type, is_space_type then else Result := True end else Result := True end end else byte_type_table.search (feature_name_id) if byte_type_table.found then function_type := byte_type_table.found_item Result := True end end end feature -- Access code function_type: INTEGER -- Is current call based on an operator instead of a function -- call? feature -- Status valid_function_type (type: INTEGER): BOOLEAN -- Is `f' a valid function type supported by Current? do Result := type >= min_type_id and type <= max_type_id ensure valid: Result implies (type >= min_type_id and type <= max_type_id) end feature -- Byte code special generation make_byte_code (ba: BYTE_ARRAY; basic_type: BASIC_A; result_type: TYPE_A) -- Generate byte code sequence that will be used with basic types. require basic_type_not_void: basic_type /= Void valid_function_type: valid_function_type (function_type) do inspect function_type when is_equal_type then ba.append (Bc_eq) when is_less_type then ba.append (bc_lt) when is_less_equal_type then ba.append (bc_le) when is_greater_type then ba.append (bc_gt) when is_greater_equal_type then ba.append (bc_ge) when to_character_8_type then check valid_type: type_of (basic_type) = integer_type_id or type_of (basic_type) = character_type_id end ba.append (bc_cast_char8) when to_character_32_type then check valid_type: type_of (basic_type) = integer_type_id or type_of (basic_type) = character_type_id end ba.append (bc_cast_char32) when as_natural_8_type, to_natural_8_type then ba.append (bc_cast_natural) ba.append_integer (8) when as_natural_16_type, to_natural_16_type then ba.append (bc_cast_natural) ba.append_integer (16) when as_natural_32_type, to_natural_32_type then ba.append (bc_cast_natural) ba.append_integer (32) when as_natural_64_type, to_natural_64_type then ba.append (bc_cast_natural) ba.append_integer (64) when as_integer_8_type, to_integer_8_type then ba.append (Bc_cast_integer) ba.append_integer (8) when as_integer_16_type, to_integer_16_type then ba.append (Bc_cast_integer) ba.append_integer (16) when as_integer_32_type, to_integer_32_type then ba.append (Bc_cast_integer) ba.append_integer (32) when as_integer_64_type, to_integer_64_type then ba.append (Bc_cast_integer) ba.append_integer (64) when to_real_64_type then ba.append (Bc_cast_real64) when to_real_32_type then ba.append (Bc_cast_real32) when floor_real_type then ba.append (bc_cast_real64) ba.append (bc_floor) if basic_type.is_real_32 then ba.append (bc_cast_real32) end when is_nan_type then ba.append (bc_basic_operations) ba.append (bc_is_nan) when is_negative_infinity_type then ba.append (bc_basic_operations) ba.append (bc_is_negative_infinity) when is_positive_infinity_type then ba.append (bc_basic_operations) ba.append (bc_is_positive_infinity) when nan_type then ba.append (bc_basic_operations) ba.append (bc_nan) when negative_infinity_type then ba.append (bc_basic_operations) ba.append (bc_negative_infinity) when positive_infinity_type then ba.append (bc_basic_operations) ba.append (bc_positive_infinity) when ceiling_real_type then ba.append (bc_cast_real64) ba.append (bc_ceil) if basic_type.is_real_32 then ba.append (bc_cast_real32) end when max_type then ba.append (Bc_basic_operations) ba.append (Bc_max) when min_type then ba.append (Bc_basic_operations) ba.append (Bc_min) when generator_type then ba.append (Bc_basic_operations) if attached result_type.actual_type as t and then t.has_associated_class and then attached system.string_32_class as s and then s.is_compiled and then t.base_class.class_id = s.compiled_class.class_id then -- Result is of type STRING_32. ba.append (bc_generator__s4) else -- Result is of type STRING_8. ba.append (bc_generator__s1) end when plus_type then if type_of (basic_type) = pointer_type_id then ba.append (Bc_basic_operations) ba.append (Bc_offset) else ba.append (Bc_plus) end when minus_type then if type_of (basic_type) = pointer_type_id then ba.append (bc_uminus) ba.append (Bc_basic_operations) ba.append (Bc_offset) else ba.append (Bc_minus) end when product_type then ba.append (bc_star) when quotient_type then ba.append (bc_slash) when integer_quotient_type then ba.append (bc_div) when integer_remainder_type then ba.append (bc_mod) when power_type then ba.append (bc_power) when zero_type then ba.append (Bc_basic_operations) ba.append (Bc_zero) when one_type then ba.append (Bc_basic_operations) ba.append (Bc_one) when default_type then -- We do not need target, so let's get rid of -- it for now. ba.append (bc_pop) ba.append_uint32_integer (1) basic_type.c_type.make_default_byte_code (ba) when negated_type then ba.append (bc_not) when opposite_type then ba.append (bc_uminus) when bit_and_type..bit_test_type, set_bit_with_mask_type, set_bit_type then check integer_type: type_of (basic_type) = integer_type_id end make_bit_operation_code (ba, function_type) when three_way_comparison_type then ba.append (bc_basic_operations) ba.append (bc_three_way_comparison) when identity_type, twin_type, as_attached_type then -- Nothing to do, top of the stack has correct value when do_nothing_type then -- We simply pop the top of the stack. ba.append (bc_pop) ba.append_uint32_integer (1) when is_default_pointer_type then -- We have the pointer on the stack, we load the default pointer -- type and then compare them for equality. basic_type.c_type.make_default_byte_code (ba) ba.append (bc_eq) when is_character_8_type then -- Check that the character code value is less than 255. check integer_type: type_of (basic_type) = character_type_id end ba.append (bc_wchar) ba.append_character_32 ({CHARACTER_8}.max_value.to_character_32) ba.append (bc_le) end end feature -- C special code generation generate (basic_type: BASIC_A; target: REGISTRABLE; parameters: BYTE_LIST [PARAMETER_B]; result_type: TYPE_A; buffer: GENERATION_BUFFER) require valid_output_buffer: buffer /= Void valid_target: target /= Void valid_function_type: valid_function_type (function_type) local parameter: PARAMETER_BL do if attached parameters then parameter := {PARAMETER_BL} / parameters.first check paramater_attached: attached parameter end end inspect function_type when lower_type, upper_type then generate_lower_upper (buffer, basic_type, function_type, target) when is_space_type then generate_is_space (buffer, basic_type, target) when is_digit_type then generate_is_digit (buffer, basic_type, target) when is_equal_type, is_less_type, is_less_equal_type, is_greater_type, is_greater_equal_type then generate_comparison (buffer, basic_type, target, parameter) when to_character_8_type then buffer.put_string ("(EIF_CHARACTER_8) ") target.print_register when to_character_32_type then buffer.put_string ("(EIF_CHARACTER_32) ") target.print_register when as_natural_8_type, to_natural_8_type then buffer.put_string ("(EIF_NATURAL_8) ") target.print_register when as_natural_16_type, to_natural_16_type then buffer.put_string ("(EIF_NATURAL_16) ") target.print_register when as_natural_32_type, to_natural_32_type then buffer.put_string ("(EIF_NATURAL_32) ") target.print_register when as_natural_64_type, to_natural_64_type then buffer.put_string ("(EIF_NATURAL_64) ") target.print_register when as_integer_8_type, to_integer_8_type then buffer.put_string ("(EIF_INTEGER_8) ") target.print_register when as_integer_16_type, to_integer_16_type then buffer.put_string ("(EIF_INTEGER_16) ") target.print_register when as_integer_32_type, to_integer_32_type then buffer.put_string ("(EIF_INTEGER_32) ") if basic_type.is_pointer then -- Special code generation for conversion from POINTER to INTEGER without -- raising a warning at the C compilation level on platforms where the pointer -- size is different from the size of an INTEGER_32. buffer.put_string ("(rt_int_ptr) ") end target.print_register when as_integer_64_type, to_integer_64_type then buffer.put_string ("(EIF_INTEGER_64) ") target.print_register when to_real_64_type then -- We are using `c_type' here, but in some descendants of -- REGISTRABLE such as NESTED_BL it is the `c_type' of the -- first nested call, not of the whole. However it seems that -- here we never get a NESTED_BL so it works just fine. target.c_type.generate_conversion_to_real_64 (buffer) target.print_register buffer.put_character (')') when to_real_32_type then -- We are using `c_type' here, but in some descendants of -- REGISTRABLE such as NESTED_BL it is the `c_type' of the -- first nested call, not of the whole. However it seems that -- here we never get a NESTED_BL so it works just fine. target.c_type.generate_conversion_to_real_32 (buffer) target.print_register buffer.put_character (')') when ceiling_real_type then basic_type.c_type.generate_cast (buffer) buffer.put_string ("ceil ((double)") target.print_register buffer.put_character (')') -- Add `<math.h>' for C declaration of `ceil'. shared_include_queue_put ({PREDEFINED_NAMES}.math_header_name_id) when floor_real_type then basic_type.c_type.generate_cast (buffer) buffer.put_string ("floor ((double)") target.print_register buffer.put_character (')') -- Add `<math.h>' for C declaration of `floor'. shared_include_queue_put ({PREDEFINED_NAMES}.math_header_name_id) when is_nan_type, is_negative_infinity_type, is_positive_infinity_type then buffer.put_four_character ('e', 'i', 'f', '_') inspect function_type when is_nan_type then buffer.put_string ("is_nan_") when is_negative_infinity_type then buffer.put_string ("is_negative_infinity_") when is_positive_infinity_type then buffer.put_string ("is_positive_infinity_") end if basic_type.is_real_32 then buffer.put_string ("real_32") else buffer.put_string ("real_64") end buffer.put_two_character (' ', '(') target.print_register buffer.put_character (')') -- Add `eif_helpers.h' for C declaration of `floor'. shared_include_queue_put ({PREDEFINED_NAMES}.eif_helpers_header_name_id) when nan_type, negative_infinity_type, positive_infinity_type then buffer.put_four_character ('e', 'i', 'f', '_') if basic_type.is_real_32 then buffer.put_string ("real_32_") else buffer.put_string ("real_64_") end inspect function_type when nan_type then buffer.put_string ("nan") when negative_infinity_type then buffer.put_string ("negative_infinity") when positive_infinity_type then buffer.put_string ("positive_infinity") end -- Add `eif_helpers.h' for C declaration of `floor'. shared_include_queue_put ({PREDEFINED_NAMES}.eif_helpers_header_name_id) when plus_type then generate_plus (buffer, type_of (basic_type), target, parameter, False) when minus_type then generate_plus (buffer, type_of (basic_type), target, parameter, True) when product_type then buffer.put_character ('(') target.print_register buffer.put_three_character (' ', '*', ' ') parameter.print_immediate_register buffer.put_character (')') when quotient_type then generate_real_division (basic_type, target, parameter, result_type, buffer) when integer_quotient_type then buffer.put_character ('(') target.print_register buffer.put_three_character (' ', '/', ' ') parameter.print_immediate_register buffer.put_character (')') when integer_remainder_type then buffer.put_character ('(') target.print_register buffer.put_three_character (' ', '%%', ' ') parameter.print_immediate_register buffer.put_character (')') when power_type then generate_power (basic_type, target, parameter, result_type, buffer) when out_type then generate_out (buffer, basic_type, target, result_type) when hash_code_type then generate_hashcode (buffer, type_of (basic_type), target) when hash_code_64_type then generate_hashcode_64 (buffer, type_of (basic_type), target) when max_type then generate_max (buffer, type_of (basic_type), target, parameter) when min_type then generate_min (buffer, type_of (basic_type), target, parameter) when three_way_comparison_type then generate_three_way_comparison (buffer, type_of (basic_type), target, parameter) when abs_type then generate_abs (buffer, type_of (basic_type), target) when generator_type then if attached result_type.actual_type as t and then t.has_associated_class and then attached system.string_32_class as s and then s.is_compiled and then t.base_class.class_id = s.compiled_class.class_id then generate_generator__s4 (buffer, type_of (basic_type)) else generate_generator__s1 (buffer, type_of (basic_type)) end when default_type then basic_type.c_type.generate_default_value (buffer) when negated_type then buffer.put_string ("(EIF_BOOLEAN) !") target.print_register when opposite_type then basic_type.c_type.generate_cast (buffer) buffer.put_character ('-') target.print_register when bit_and_type..bit_test_type then check integer_type: type_of (basic_type) = integer_type_id end generate_bit_operation (buffer, function_type, target, parameter) when set_bit_with_mask_type then check integer_type: type_of (basic_type) = integer_type_id parameters_not_void: parameters /= Void end generate_set_bit_with_mask (buffer, target, parameters) when set_bit_type then check integer_type: type_of (basic_type) = integer_type_id parameters_not_void: parameters /= Void end generate_set_bit (buffer, target, parameters) when zero_type then generate_zero (buffer, type_of (basic_type)) when one_type then generate_one (buffer, type_of (basic_type)) when memory_move, memory_copy, memory_set, memory_alloc, memory_free, memory_calloc then check pointer_type: type_of (basic_type) = pointer_type_id end generate_memory_routine (buffer, function_type, target, parameters) when identity_type, twin_type, as_attached_type then -- There is nothing to do, just print the previous value. target.print_register when do_nothing_type then if not target.is_predefined then -- There is something to do when `target' is not a predefined entities. -- See eweasel test#exec191 and test#exec324. buffer.put_string ("eif_do_nothing_value.") basic_type.c_type.generate_typed_field (buffer) buffer.put_three_character (' ', '=', ' ') target.print_register end when is_default_pointer_type then buffer.put_character('!') target.print_register when is_character_8_type then check integer_type: type_of (basic_type) = character_type_id end buffer.put_character ('(') target.print_register buffer.put_four_character (' ', '<', '=', ' ') buffer.put_hex_natural_32 ({CHARACTER_8}.max_value.to_natural_32) buffer.put_character (')') end end feature {NONE} -- C and Byte code corresponding Eiffel function calls c_type_table: HASH_TABLE [INTEGER, INTEGER] once create Result.make (100) Result.put (is_equal_type, {PREDEFINED_NAMES}.is_deep_equal_name_id) Result.put (is_equal_type, {PREDEFINED_NAMES}.is_equal_name_id) Result.put (is_equal_type, {PREDEFINED_NAMES}.standard_is_equal_name_id) Result.put (is_less_type, {PREDEFINED_NAMES}.is_less_name_id) Result.put (is_less_equal_type, {PREDEFINED_NAMES}.is_less_equal_name_id) Result.put (is_greater_type, {PREDEFINED_NAMES}.is_greater_name_id) Result.put (is_greater_equal_type, {PREDEFINED_NAMES}.is_greater_equal_name_id) Result.put (out_type, {PREDEFINED_NAMES}.out_name_id) Result.put (hash_code_64_type, {PREDEFINED_NAMES}.hash_code_64_name_id) Result.put (hash_code_type, {PREDEFINED_NAMES}.hash_code_name_id) Result.put (hash_code_type, {PREDEFINED_NAMES}.code_name_id) Result.put (max_type, {PREDEFINED_NAMES}.max_name_id) Result.put (min_type, {PREDEFINED_NAMES}.min_name_id) Result.put (abs_type, {PREDEFINED_NAMES}.abs_name_id) Result.put (zero_type, {PREDEFINED_NAMES}.zero_name_id) Result.put (one_type, {PREDEFINED_NAMES}.one_name_id) Result.put (generator_type, {PREDEFINED_NAMES}.generator_name_id) Result.put (to_character_8_type, {PREDEFINED_NAMES}.to_character_8_name_id) Result.put (to_character_8_type, {PREDEFINED_NAMES}.to_character_name_id) Result.put (to_character_8_type, {PREDEFINED_NAMES}.ascii_char_name_id) Result.put (to_character_32_type, {PREDEFINED_NAMES}.to_character_32_name_id) Result.put (as_integer_8_type, {PREDEFINED_NAMES}.as_integer_8_name_id) Result.put (as_integer_16_type, {PREDEFINED_NAMES}.as_integer_16_name_id) Result.put (as_integer_32_type, {PREDEFINED_NAMES}.as_integer_32_name_id) Result.put (as_integer_64_type, {PREDEFINED_NAMES}.as_integer_64_name_id) Result.put (to_integer_8_type, {PREDEFINED_NAMES}.to_integer_8_name_id) Result.put (to_integer_16_type, {PREDEFINED_NAMES}.to_integer_16_name_id) Result.put (to_integer_32_type, {PREDEFINED_NAMES}.truncated_to_integer_name_id) Result.put (to_integer_32_type, {PREDEFINED_NAMES}.to_integer_name_id) Result.put (to_integer_32_type, {PREDEFINED_NAMES}.to_integer_32_name_id) Result.put (to_integer_64_type, {PREDEFINED_NAMES}.to_integer_64_name_id) Result.put (to_integer_64_type, {PREDEFINED_NAMES}.truncated_to_integer_64_name_id) Result.put (as_natural_8_type, {PREDEFINED_NAMES}.as_natural_8_name_id) Result.put (as_natural_16_type, {PREDEFINED_NAMES}.as_natural_16_name_id) Result.put (as_natural_32_type, {PREDEFINED_NAMES}.as_natural_32_name_id) Result.put (as_natural_32_type, {PREDEFINED_NAMES}.natural_32_code_name_id) Result.put (as_natural_64_type, {PREDEFINED_NAMES}.as_natural_64_name_id) Result.put (to_natural_8_type, {PREDEFINED_NAMES}.to_natural_8_name_id) Result.put (to_natural_16_type, {PREDEFINED_NAMES}.to_natural_16_name_id) Result.put (to_natural_32_type, {PREDEFINED_NAMES}.to_natural_32_name_id) Result.put (to_natural_64_type, {PREDEFINED_NAMES}.to_natural_64_name_id) Result.put (to_real_64_type, {PREDEFINED_NAMES}.to_real_64_name_id) Result.put (to_real_32_type, {PREDEFINED_NAMES}.to_real_32_name_id) Result.put (to_real_64_type, {PREDEFINED_NAMES}.to_double_name_id) Result.put (to_real_32_type, {PREDEFINED_NAMES}.to_real_name_id) Result.put (to_real_32_type, {PREDEFINED_NAMES}.truncated_to_real_name_id) Result.put (identity_type, {PREDEFINED_NAMES}.identity_name_id) Result.put (opposite_type, {PREDEFINED_NAMES}.opposite_name_id) Result.put (plus_type, {PREDEFINED_NAMES}.plus_name_id) Result.put (plus_type, {PREDEFINED_NAMES}.infix_plus_name_id) Result.put (minus_type, {PREDEFINED_NAMES}.minus_name_id) Result.put (product_type, {PREDEFINED_NAMES}.product_name_id) Result.put (quotient_type, {PREDEFINED_NAMES}.quotient_name_id) Result.put (integer_quotient_type, {PREDEFINED_NAMES}.integer_quotient_name_id) Result.put (integer_remainder_type, {PREDEFINED_NAMES}.integer_remainder_name_id) Result.put (power_type, {PREDEFINED_NAMES}.power_name_id) Result.put (negated_type, {PREDEFINED_NAMES}.negated_name_id) -- Result.put (conjuncted_type, {PREDEFINED_NAMES}.conjuncted_name_id) -- Result.put (conjuncted_semistrict_type, {PREDEFINED_NAMES}.conjuncted_semistrict_name_id) -- Result.put (disjuncted_type, {PREDEFINED_NAMES}.disjuncted_name_id) -- Result.put (disjuncted_semistrict_type, {PREDEFINED_NAMES}.disjuncted_semistrict_name_id) -- Result.put (disjuncted_exclusive_type, {PREDEFINED_NAMES}.disjuncted_exclusive_name_id) -- Result.put (implication_type, {PREDEFINED_NAMES}.implication_name_id) Result.put (default_type, {PREDEFINED_NAMES}.default_name_id) Result.put (bit_and_type, {PREDEFINED_NAMES}.bit_and_name_id) Result.put (bit_and_type, {PREDEFINED_NAMES}.infix_bit_and_name_id) Result.put (bit_or_type, {PREDEFINED_NAMES}.bit_or_name_id) Result.put (bit_or_type, {PREDEFINED_NAMES}.infix_bit_or_name_id) Result.put (bit_xor_type, {PREDEFINED_NAMES}.bit_xor_name_id) Result.put (bit_not_type, {PREDEFINED_NAMES}.bit_not_name_id) Result.put (bit_shift_left_type, {PREDEFINED_NAMES}.bit_shift_left_name_id) Result.put (bit_shift_left_type, {PREDEFINED_NAMES}.infix_shift_left_name_id) Result.put (bit_shift_right_type, {PREDEFINED_NAMES}.bit_shift_right_name_id) Result.put (bit_shift_right_type, {PREDEFINED_NAMES}.infix_shift_right_name_id) Result.put (bit_test_type, {PREDEFINED_NAMES}.bit_test_name_id) Result.put (set_bit_type, {PREDEFINED_NAMES}.set_bit_name_id) Result.put (set_bit_with_mask_type, {PREDEFINED_NAMES}.set_bit_with_mask_name_id) Result.put (memory_copy, {PREDEFINED_NAMES}.memory_copy_name_id) Result.put (memory_move, {PREDEFINED_NAMES}.memory_move_name_id) Result.put (memory_set, {PREDEFINED_NAMES}.memory_set_name_id) Result.put (memory_calloc, {PREDEFINED_NAMES}.memory_calloc_name_id) Result.put (memory_alloc, {PREDEFINED_NAMES}.memory_alloc_name_id) Result.put (memory_free, {PREDEFINED_NAMES}.memory_free_name_id) Result.put (lower_type, {PREDEFINED_NAMES}.lower_name_id) Result.put (lower_type, {PREDEFINED_NAMES}.as_lower_name_id) Result.put (upper_type, {PREDEFINED_NAMES}.upper_name_id) Result.put (upper_type, {PREDEFINED_NAMES}.as_upper_name_id) Result.put (is_digit_type, {PREDEFINED_NAMES}.is_digit_name_id) Result.put (is_space_type, {PREDEFINED_NAMES}.is_space_name_id) Result.put (three_way_comparison_type, {PREDEFINED_NAMES}.three_way_comparison_name_id) Result.put (twin_type, {PREDEFINED_NAMES}.standard_twin_name_id) Result.put (twin_type, {PREDEFINED_NAMES}.twin_name_id) Result.put (twin_type, {PREDEFINED_NAMES}.deep_twin_name_id) Result.put (as_attached_type, {PREDEFINED_NAMES}.as_attached_name_id) Result.put (ceiling_real_type, {PREDEFINED_NAMES}.ceiling_real_32_name_id) Result.put (ceiling_real_type, {PREDEFINED_NAMES}.ceiling_real_64_name_id) Result.put (floor_real_type, {PREDEFINED_NAMES}.floor_real_32_name_id) Result.put (floor_real_type, {PREDEFINED_NAMES}.floor_real_64_name_id) Result.put (is_nan_type, {PREDEFINED_NAMES}.is_nan_name_id) Result.put (is_negative_infinity_type, {PREDEFINED_NAMES}.is_negative_infinity_name_id) Result.put (is_positive_infinity_type, {PREDEFINED_NAMES}.is_positive_infinity_name_id) Result.put (nan_type, {PREDEFINED_NAMES}.nan_name_id) Result.put (negative_infinity_type, {PREDEFINED_NAMES}.negative_infinity_name_id) Result.put (positive_infinity_type, {PREDEFINED_NAMES}.positive_infinity_name_id) Result.put (do_nothing_type, {PREDEFINED_NAMES}.do_nothing_name_id) Result.put (is_default_pointer_type, {PREDEFINED_NAMES}.is_default_pointer_name_id) Result.put (is_character_8_type, {PREDEFINED_NAMES}.is_character_8_name_id) -- Result.put (set_item_type, feature {PREDEFINED_NAMES}.set_item_name_id) -- Result.put (set_item_type, feature {PREDEFINED_NAMES}.copy_name_id) -- Result.put (set_item_type, feature {PREDEFINED_NAMES}.deep_copy_name_id) -- Result.put (set_item_type, feature {PREDEFINED_NAMES}.standard_copy_name_id) end byte_type_table: HASH_TABLE [INTEGER, INTEGER] once create Result.make (100) Result.put (is_equal_type, {PREDEFINED_NAMES}.is_deep_equal_name_id) Result.put (is_equal_type, {PREDEFINED_NAMES}.is_equal_name_id) Result.put (is_equal_type, {PREDEFINED_NAMES}.standard_is_equal_name_id) Result.put (is_less_type, {PREDEFINED_NAMES}.is_less_name_id) Result.put (is_less_equal_type, {PREDEFINED_NAMES}.is_less_equal_name_id) Result.put (is_greater_type, {PREDEFINED_NAMES}.is_greater_name_id) Result.put (is_greater_equal_type, {PREDEFINED_NAMES}.is_greater_equal_name_id) Result.put (max_type, {PREDEFINED_NAMES}.max_name_id) Result.put (min_type, {PREDEFINED_NAMES}.min_name_id) Result.put (generator_type, {PREDEFINED_NAMES}.generator_name_id) Result.put (identity_type, {PREDEFINED_NAMES}.identity_name_id) Result.put (opposite_type, {PREDEFINED_NAMES}.opposite_name_id) Result.put (plus_type, {PREDEFINED_NAMES}.plus_name_id) Result.put (plus_type, {PREDEFINED_NAMES}.infix_plus_name_id) Result.put (minus_type, {PREDEFINED_NAMES}.minus_name_id) Result.put (product_type, {PREDEFINED_NAMES}.product_name_id) Result.put (quotient_type, {PREDEFINED_NAMES}.quotient_name_id) Result.put (integer_quotient_type, {PREDEFINED_NAMES}.integer_quotient_name_id) Result.put (integer_remainder_type, {PREDEFINED_NAMES}.integer_remainder_name_id) Result.put (power_type, {PREDEFINED_NAMES}.power_name_id) Result.put (negated_type, {PREDEFINED_NAMES}.negated_name_id) -- Result.put (conjuncted_type, {PREDEFINED_NAMES}.conjuncted_name_id) -- Result.put (conjuncted_semistrict_type, {PREDEFINED_NAMES}.conjuncted_semistrict_name_id) -- Result.put (disjuncted_type, {PREDEFINED_NAMES}.disjuncted_name_id) -- Result.put (disjuncted_semistrict_type, {PREDEFINED_NAMES}.disjuncted_semistrict_name_id) -- Result.put (disjuncted_exclusive_type, {PREDEFINED_NAMES}.disjuncted_exclusive_name_id) -- Result.put (implication_type, {PREDEFINED_NAMES}.implication_name_id) Result.put (default_type, {PREDEFINED_NAMES}.default_name_id) Result.put (zero_type, {PREDEFINED_NAMES}.zero_name_id) Result.put (one_type, {PREDEFINED_NAMES}.one_name_id) Result.put (bit_and_type, {PREDEFINED_NAMES}.bit_and_name_id) Result.put (bit_and_type, {PREDEFINED_NAMES}.infix_bit_and_name_id) Result.put (bit_or_type, {PREDEFINED_NAMES}.bit_or_name_id) Result.put (bit_or_type, {PREDEFINED_NAMES}.infix_bit_or_name_id) Result.put (bit_xor_type, {PREDEFINED_NAMES}.bit_xor_name_id) Result.put (bit_not_type, {PREDEFINED_NAMES}.bit_not_name_id) Result.put (bit_shift_left_type, {PREDEFINED_NAMES}.bit_shift_left_name_id) Result.put (bit_shift_left_type, {PREDEFINED_NAMES}.infix_shift_left_name_id) Result.put (bit_shift_right_type, {PREDEFINED_NAMES}.bit_shift_right_name_id) Result.put (bit_shift_right_type, {PREDEFINED_NAMES}.infix_shift_right_name_id) Result.put (bit_test_type, {PREDEFINED_NAMES}.bit_test_name_id) Result.put (set_bit_type, {PREDEFINED_NAMES}.set_bit_name_id) Result.put (set_bit_with_mask_type, {PREDEFINED_NAMES}.set_bit_with_mask_name_id) Result.put (to_character_8_type, {PREDEFINED_NAMES}.to_character_8_name_id) Result.put (to_character_8_type, {PREDEFINED_NAMES}.to_character_name_id) Result.put (to_character_8_type, {PREDEFINED_NAMES}.ascii_char_name_id) Result.put (to_character_32_type, {PREDEFINED_NAMES}.to_character_32_name_id) Result.put (as_integer_8_type, {PREDEFINED_NAMES}.as_integer_8_name_id) Result.put (as_integer_16_type, {PREDEFINED_NAMES}.as_integer_16_name_id) Result.put (as_integer_32_type, {PREDEFINED_NAMES}.as_integer_32_name_id) Result.put (as_integer_64_type, {PREDEFINED_NAMES}.as_integer_64_name_id) Result.put (to_integer_32_type, {PREDEFINED_NAMES}.truncated_to_integer_name_id) Result.put (to_integer_8_type, {PREDEFINED_NAMES}.to_integer_8_name_id) Result.put (to_integer_16_type, {PREDEFINED_NAMES}.to_integer_16_name_id) Result.put (to_integer_32_type, {PREDEFINED_NAMES}.to_integer_name_id) Result.put (to_integer_32_type, {PREDEFINED_NAMES}.to_integer_32_name_id) Result.put (to_integer_64_type, {PREDEFINED_NAMES}.to_integer_64_name_id) Result.put (to_integer_64_type, {PREDEFINED_NAMES}.truncated_to_integer_64_name_id) Result.put (as_natural_8_type, {PREDEFINED_NAMES}.as_natural_8_name_id) Result.put (as_natural_16_type, {PREDEFINED_NAMES}.as_natural_16_name_id) Result.put (as_natural_32_type, {PREDEFINED_NAMES}.as_natural_32_name_id) Result.put (as_natural_32_type, {PREDEFINED_NAMES}.natural_32_code_name_id) Result.put (as_natural_64_type, {PREDEFINED_NAMES}.as_natural_64_name_id) Result.put (to_natural_8_type, {PREDEFINED_NAMES}.to_natural_8_name_id) Result.put (to_natural_16_type, {PREDEFINED_NAMES}.to_natural_16_name_id) Result.put (to_natural_32_type, {PREDEFINED_NAMES}.to_natural_32_name_id) Result.put (to_natural_64_type, {PREDEFINED_NAMES}.to_natural_64_name_id) Result.put (to_real_64_type, {PREDEFINED_NAMES}.to_real_64_name_id) Result.put (to_real_32_type, {PREDEFINED_NAMES}.to_real_32_name_id) Result.put (to_real_32_type, {PREDEFINED_NAMES}.truncated_to_real_name_id) Result.put (to_real_64_type, {PREDEFINED_NAMES}.to_double_name_id) Result.put (to_real_32_type, {PREDEFINED_NAMES}.to_real_name_id) Result.put (three_way_comparison_type, {PREDEFINED_NAMES}.three_way_comparison_name_id) Result.put (twin_type, {PREDEFINED_NAMES}.standard_twin_name_id) Result.put (twin_type, {PREDEFINED_NAMES}.twin_name_id) Result.put (twin_type, {PREDEFINED_NAMES}.deep_twin_name_id) Result.put (as_attached_type, {PREDEFINED_NAMES}.as_attached_name_id) Result.put (ceiling_real_type, {PREDEFINED_NAMES}.ceiling_real_32_name_id) Result.put (ceiling_real_type, {PREDEFINED_NAMES}.ceiling_real_64_name_id) Result.put (floor_real_type, {PREDEFINED_NAMES}.floor_real_32_name_id) Result.put (floor_real_type, {PREDEFINED_NAMES}.floor_real_64_name_id) Result.put (is_nan_type, {PREDEFINED_NAMES}.is_nan_name_id) Result.put (is_negative_infinity_type, {PREDEFINED_NAMES}.is_negative_infinity_name_id) Result.put (is_positive_infinity_type, {PREDEFINED_NAMES}.is_positive_infinity_name_id) Result.put (nan_type, {PREDEFINED_NAMES}.nan_name_id) Result.put (negative_infinity_type, {PREDEFINED_NAMES}.negative_infinity_name_id) Result.put (positive_infinity_type, {PREDEFINED_NAMES}.positive_infinity_name_id) Result.put (do_nothing_type, {PREDEFINED_NAMES}.do_nothing_name_id) Result.put (is_default_pointer_type, {PREDEFINED_NAMES}.is_default_pointer_name_id) Result.put (is_character_8_type, {PREDEFINED_NAMES}.is_character_8_name_id) -- Result.put (set_item_type, feature {PREDEFINED_NAMES}.set_item_name_id) end feature {NONE} -- Fast access to feature name min_type_id: INTEGER = 1 is_equal_type: INTEGER = 1 set_item_type: INTEGER = 2 out_type: INTEGER = 3 hash_code_type: INTEGER = 4 max_type: INTEGER = 5 min_type: INTEGER = 6 abs_type: INTEGER = 7 generator_type: INTEGER = 8 to_integer_32_type: INTEGER = 9 plus_type: INTEGER = 10 default_type: INTEGER = 11 bit_and_type: INTEGER = 12 bit_or_type: INTEGER = 13 bit_xor_type: INTEGER = 14 bit_not_type: INTEGER = 15 bit_shift_left_type: INTEGER = 16 bit_shift_right_type: INTEGER = 17 bit_test_type: INTEGER = 18 zero_type: INTEGER = 19 one_type: INTEGER = 20 memory_move: INTEGER = 21 memory_copy: INTEGER = 22 memory_set: INTEGER = 23 to_integer_8_type: INTEGER = 24 to_integer_16_type: INTEGER = 25 to_integer_64_type: INTEGER = 26 set_bit_with_mask_type: INTEGER = 27 memory_alloc: INTEGER = 28 memory_free: INTEGER = 29 to_character_8_type: INTEGER = 30 upper_type: INTEGER = 31 lower_type: INTEGER = 32 is_digit_type: INTEGER = 33 memory_calloc: INTEGER = 34 to_real_64_type: INTEGER = 35 to_real_32_type: INTEGER = 36 three_way_comparison_type: INTEGER = 37 to_natural_8_type: INTEGER = 38 to_natural_16_type: INTEGER = 39 to_natural_32_type: INTEGER = 40 to_natural_64_type: INTEGER = 41 twin_type: INTEGER = 42 as_integer_8_type: INTEGER = 43 as_integer_16_type: INTEGER = 44 as_integer_32_type: INTEGER = 45 as_integer_64_type: INTEGER = 46 as_natural_8_type: INTEGER = 47 as_natural_16_type: INTEGER = 48 as_natural_32_type: INTEGER = 49 as_natural_64_type: INTEGER = 50 set_bit_type: INTEGER = 51 is_space_type: INTEGER = 52 to_character_32_type: INTEGER = 53 ceiling_real_type: INTEGER = 54 floor_real_type: INTEGER = 55 as_attached_type: INTEGER = 56 is_nan_type: INTEGER = 57 is_negative_infinity_type: INTEGER = 58 is_positive_infinity_type: INTEGER = 59 nan_type: INTEGER = 60 negative_infinity_type: INTEGER = 61 positive_infinity_type: INTEGER = 62 do_nothing_type: INTEGER = 63 is_default_pointer_type: INTEGER = 64 is_character_8_type: INTEGER = 65 hash_code_64_type: INTEGER = 66 identity_type: INTEGER = 67 opposite_type: INTEGER = 68 minus_type: INTEGER = 69 product_type: INTEGER = 70 quotient_type: INTEGER = 71 integer_quotient_type: INTEGER = 72 integer_remainder_type: INTEGER = 73 power_type: INTEGER = 74 is_less_type: INTEGER = 75 is_less_equal_type: INTEGER = 76 is_greater_type: INTEGER = 77 is_greater_equal_type: INTEGER = 78 negated_type: INTEGER = 79 conjuncted_type: INTEGER = 80 conjuncted_semistrict_type: INTEGER = 81 disjuncted_type: INTEGER = 82 disjuncted_semistrict_type: INTEGER = 83 disjuncted_exclusive_type: INTEGER = 84 implication_type: INTEGER = 85 max_type_id: INTEGER = 85 feature {NONE} -- Byte code generation make_bit_operation_code (ba: BYTE_ARRAY; op: INTEGER) -- Make byte code for call on bit operations from INTEGER. require ba_not_void: ba /= Void do ba.append (Bc_int_bit_op) inspect op when bit_and_type then ba.append (Bc_int_bit_and) when bit_or_type then ba.append (Bc_int_bit_or) when bit_xor_type then ba.append (Bc_int_bit_xor) when bit_not_type then ba.append (Bc_int_bit_not) when bit_shift_left_type then ba.append (Bc_int_bit_shift_left) when bit_shift_right_type then ba.append (Bc_int_bit_shift_right) when bit_test_type then ba.append (Bc_int_bit_test) when set_bit_type then ba.append (Bc_int_set_bit) when set_bit_with_mask_type then ba.append (Bc_int_set_bit_with_mask) end end feature {NONE} -- C code generation generate_lower_upper (buffer: GENERATION_BUFFER; basic_type: BASIC_A; f_type: INTEGER; target: REGISTRABLE) -- Generate fast wrapper for call on `upper' and `lower' of CHARACTER. require buffer_not_void: buffer /= Void target_not_void: target /= Void character_type: type_of (basic_type) = character_type_id valid_function_type: f_type = lower_type or f_type = upper_type do buffer.put_string (if function_type = lower_type then "eif_builtin_CHARACTER_8_as_lower__" else "eif_builtin_CHARACTER_8_as_upper__" end) {BUILT_IN_EXTENSION_I}.append_type_name (basic_type, system.byte_context.context_class_type, buffer) buffer.put_character ('_') {BUILT_IN_EXTENSION_I}.append_type_name (basic_type, system.byte_context.context_class_type, buffer) buffer.put_character ('(') target.print_register buffer.put_character (')') -- Add "eif_built_in.h" for C compilation where all output functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_built_in_header_name_id) end generate_is_digit (buffer: GENERATION_BUFFER; basic_type: BASIC_A; target: REGISTRABLE) -- Generate fast wrapper for call on `is_digit'. require buffer_not_void: buffer /= Void target_not_void: target /= Void character_type: type_of (basic_type) = character_type_id do buffer.put_string ("EIF_TEST(isdigit(") target.print_register buffer.put_character (')') buffer.put_character (')') -- Add `ctype.h' for C compilation where `isdigit' is declared. shared_include_queue_put ({PREDEFINED_NAMES}.ctype_header_name_id) end generate_is_space (buffer: GENERATION_BUFFER; basic_type: BASIC_A; target: REGISTRABLE) -- Generate fast wrapper for call on `is_space' of CHARACTER. require buffer_not_void: buffer /= Void target_not_void: target /= Void character_type: type_of (basic_type) = character_type_id do buffer.put_string ("eif_builtin_CHARACTER_8_is_space__") {BUILT_IN_EXTENSION_I}.append_type_name (basic_type, system.byte_context.context_class_type, buffer) buffer.put_character ('_') {BUILT_IN_EXTENSION_I}.append_type_name (boolean_type, system.byte_context.context_class_type, buffer) buffer.put_character ('(') target.print_register buffer.put_character (')') -- Add "eif_built_in.h" for C compilation where all output functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_built_in_header_name_id) end generate_comparison (buffer: GENERATION_BUFFER; basic_type: BASIC_A; target: REGISTRABLE; parameter: PARAMETER_BL) -- Generate a call to "is_equal", "<", "<=", ">", ">=" where target and parameter -- are both basic types. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameter_not_void: parameter /= Void valid_function_type: (<<is_equal_type, is_less_type, is_less_equal_type, is_greater_type, is_greater_equal_type>>).has (function_type) do if (basic_type.is_real_32 or else basic_type.is_real_64) and then system.total_order_on_reals then shared_include_queue_put ({PREDEFINED_NAMES}.eif_helpers_header_name_id) buffer.put_string (inspect function_type when is_equal_type then "eif_is_equal_real_" when is_less_type then "eif_is_less_real_" when is_less_equal_type then "eif_is_less_equal_real_" when is_greater_type then "eif_is_greater_real_" when is_greater_equal_type then "eif_is_greater_equal_real_" end) if basic_type.is_real_32 then buffer.put_two_character ('3', '2') else buffer.put_two_character ('6', '4') end buffer.put_two_character (' ', '(') target.print_register buffer.put_two_character (',', ' ') parameter.print_immediate_register buffer.put_character (')') else target.print_register buffer.put_character (' ') inspect function_type when is_equal_type then buffer.put_character ('=') buffer.put_character ('=') when is_less_type then buffer.put_character ('<') when is_less_equal_type then buffer.put_character ('<') buffer.put_character ('=') when is_greater_type then buffer.put_character ('>') when is_greater_equal_type then buffer.put_character ('>') buffer.put_character ('=') end buffer.put_character (' ') parameter.print_immediate_register end end generate_plus (buffer: GENERATION_BUFFER; type_of_basic: INTEGER; target: REGISTRABLE; parameter: PARAMETER_BL; is_minus: BOOLEAN) -- Generate fast wrapper for call on `+' where target and parameter -- are both basic types. Only `POINTER' and `CHARACTER' are handled, the -- other basic types have their own handling by the compiler. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameter_not_void: parameter /= Void do inspect type_of_basic when pointer_type_id then buffer.put_string ("RTPOF(") target.print_register buffer.put_character (',') if is_minus then buffer.put_three_character (' ', '-', '(') end when character_type_id then if is_wide then buffer.put_string ("(EIF_CHARACTER_32) (((EIF_NATURAL_32) ") else buffer.put_string ("(EIF_CHARACTER_8) (((EIF_INTEGER_32) ") end target.print_register buffer.put_four_character (')', ' ', if is_minus then '-' else '+' end,' ') else buffer.put_character ('(') target.print_register buffer.put_three_character (' ', if is_minus then '-' else '+' end,' ') end parameter.print_immediate_register if is_minus and then type_of_basic = pointer_type_id then buffer.put_character (')') end buffer.put_character (')') end generate_real_division (basic_type: BASIC_A; target: REGISTRABLE; parameter: PARAMETER_BL; result_type: TYPE_A; buffer: GENERATION_BUFFER) -- Generate real division (quotient), usually for operator "/" for `target` and ` `basic_type`, in buffer `buffer` do workbench.system.byte_context.real_type (result_type).c_type.generate_cast (buffer) buffer.put_character ('(') basic_type.c_type.generate_conversion_to_real_64 (buffer) target.print_register buffer.put_four_character (')', ' ', '/', ' ') basic_type.c_type.generate_conversion_to_real_64 (buffer) parameter.print_immediate_register buffer.put_character (')') buffer.put_character (')') end generate_power (basic_type: BASIC_A; target: REGISTRABLE; parameter: PARAMETER_BL; result_type: TYPE_A; buffer: GENERATION_BUFFER) local power_value: REAL_64 done: BOOLEAN do if attached {REAL_CONST_B} parameter.expression as power_nb then power_value := power_nb.value.to_real_64 if power_value = 0.0 then done := True buffer.put_string ("(EIF_REAL_64) 1") elseif power_value = 1.0 then done := True basic_type.c_type.generate_conversion_to_real_64 (buffer) target.print_register buffer.put_character (')') elseif power_value = 2.0 or power_value = 3.0 then done := True buffer.put_string ("(EIF_REAL_64) (") basic_type.c_type.generate_conversion_to_real_64 (buffer) target.print_register buffer.put_string (") * ") basic_type.c_type.generate_conversion_to_real_64 (buffer) target.print_register if power_value = 3.0 then buffer.put_string (") * ") basic_type.c_type.generate_conversion_to_real_64 (buffer) target.print_register end buffer.put_two_character (')', ')') end end if not done then -- No optimization could have been done, so we generate the -- call to `pow'. shared_include_queue_put ({PREDEFINED_NAMES}.math_header_name_id) buffer.put_string ("(EIF_REAL_64) pow (") basic_type.c_type.generate_conversion_to_real_64 (buffer) target.print_register buffer.put_string ("), ") workbench.system.byte_context.real_type (parameter.type).c_type.generate_conversion_to_real_64 (buffer) parameter.print_immediate_register buffer.put_two_character (')', ')') end end generate_out (buffer: GENERATION_BUFFER; basic_type: BASIC_A; target: REGISTRABLE; result_type: TYPE_A) -- Generate fast wrapper for call on `out' where target -- is a basic type. require buffer_not_void: buffer /= Void target_not_void: target /= Void local is_string_32: BOOLEAN do if attached result_type.actual_type as t and then t.has_associated_class and then attached system.string_32_class as s and then s.is_compiled and then t.base_class.class_id = s.compiled_class.class_id then is_string_32 := True end if basic_type.is_boolean then buffer.put_character ('(') target.print_register if is_string_32 then buffer.put_three_character (' ', '?', ' ') buffer.generate_manifest_string_32 ("True", False) buffer.put_three_character (' ', ':', ' ') buffer.generate_manifest_string_32 ("False", False) buffer.put_character (')') else buffer.put_string (" ? makestr (%"True%", 4) : makestr (%"False%", 5))") -- Add `eif_plug.h' for C compilation where `makestr' is -- declared shared_include_queue_put ({PREDEFINED_NAMES}.eif_plug_header_name_id) end else buffer.put_string ("eif_out__") {BUILT_IN_EXTENSION_I}.append_type_name (basic_type, system.byte_context.context_class_type, buffer) buffer.put_character ('_') {BUILT_IN_EXTENSION_I}.append_type_name (result_type, system.byte_context.context_class_type, buffer) buffer.put_character ('(') target.print_register buffer.put_character (')') -- Add "eif_out.h" for C compilation where all output functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_out_header_name_id) end end generate_hashcode (buffer: GENERATION_BUFFER; type_of_basic: INTEGER; target: REGISTRABLE) -- Generate fast wrapper for call on `hash_code' where target -- is a basic type. require buffer_not_void: buffer /= Void target_not_void: target /= Void do inspect type_of_basic when boolean_type_id then buffer.put_character ('(') target.print_register buffer.put_string (" ? 1L : 0L)") when character_type_id then buffer.put_string ("(EIF_INTEGER_32) (") target.print_register buffer.put_character(')') else buffer.put_string ("(EIF_INTEGER_32) (0x7FFFFFFF & (EIF_INTEGER_32) ((rt_int_ptr) (") target.print_register buffer.put_three_character (')', ')', ')') end end generate_hashcode_64 (buffer: GENERATION_BUFFER; type_of_basic: INTEGER; target: REGISTRABLE) -- Generate fast wrapper for call on `hash_code' where target -- is a basic type. require buffer_not_void: buffer /= Void target_not_void: target /= Void do inspect type_of_basic when boolean_type_id then buffer.put_character ('(') target.print_register buffer.put_string (" ? 1L : 0L)") when character_type_id then buffer.put_string ("(EIF_NATURAL_64) (") target.print_register buffer.put_character(')') else buffer.put_string ("(EIF_NATURAL_64) (rt_int_ptr) (") target.print_register buffer.put_character (')') end end generate_generator__s1 (buffer: GENERATION_BUFFER; type_of_basic: INTEGER) -- Generate fast wrapper for call on `generator' where target -- is a basic type. require buffer_not_void: buffer /= Void do inspect type_of_basic when boolean_type_id then buffer.put_string (" RTMS_EX(%"BOOLEAN%", 7)") when character_type_id then if is_wide then buffer.put_string (" RTMS_EX(%"CHARACTER_32%", 12)") else buffer.put_string (" RTMS_EX(%"CHARACTER_8%", 11)") end when integer_type_id then if is_signed_integer then buffer.put_string (" RTMS_EX(%"INTEGER") inspect integer_size when 8 then buffer.put_string ("_8%", 9)") when 16 then buffer.put_string ("_16%", 10)") when 32 then buffer.put_string ("_32%", 10)") when 64 then buffer.put_string ("_64%", 10)") end else buffer.put_string (" RTMS_EX(%"NATURAL_") inspect integer_size when 8 then buffer.put_string ("8%", 9)") when 16 then buffer.put_string ("16%", 10)") when 32 then buffer.put_string ("32%", 10)") when 64 then buffer.put_string ("64%", 10)") end end when pointer_type_id then buffer.put_string (" RTMS_EX(%"POINTER%", 7)") when real_32_type_id then buffer.put_string (" RTMS_EX(%"REAL_32%", 7)") when real_64_type_id then buffer.put_string (" RTMS_EX(%"REAL_64%", 7)") end end generate_generator__s4 (buffer: GENERATION_BUFFER; type_of_basic: INTEGER) -- Generate fast wrapper for call on `generator' where target -- is a basic type. require buffer_not_void: buffer /= Void do buffer.generate_manifest_string_32 (inspect type_of_basic when boolean_type_id then {STRING_32} "BOOLEAN" when character_type_id then if is_wide then {STRING_32} "CHARACTER_32" else {STRING_32} "CHARACTER_8" end when integer_type_id then if is_signed_integer then inspect integer_size when 8 then {STRING_32} "INTEGER_8" when 16 then {STRING_32} "INTEGER_16" when 32 then {STRING_32} "INTEGER_32" when 64 then {STRING_32} "INTEGER_64" end else inspect integer_size when 8 then {STRING_32} "NATURAL_8" when 16 then {STRING_32} "NATURAL_16" when 32 then {STRING_32} "NATURAL_32" when 64 then {STRING_32} "NATURAL_64" end end when pointer_type_id then {STRING_32} "POINTER" when real_32_type_id then {STRING_32} "REAL_32" when real_64_type_id then {STRING_32} "REAL_64" end, False) end generate_max (buffer: GENERATION_BUFFER; type_of_basic: INTEGER; target: REGISTRABLE; parameter: PARAMETER_BL) -- Generate fast wrapper for call on `max' where target and parameter -- are both basic types. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameter_not_void: parameter /= Void do inspect type_of_basic when character_type_id then if is_wide then buffer.put_string ("eif_max_wide_char (") else buffer.put_string ("eif_max_char (") end when integer_type_id then if is_signed_integer then buffer.put_string ("eif_max_") else buffer.put_string ("eif_max_u") end inspect integer_size when 8 then buffer.put_string ("int8 (") when 16 then buffer.put_string ("int16 (") when 32 then buffer.put_string ("int32 (") when 64 then buffer.put_string ("int64 (") end when real_32_type_id then buffer.put_string ("eif_max_real32 (") when real_64_type_id then buffer.put_string ("eif_max_real64 (") end target.print_register buffer.put_character (',') parameter.print_immediate_register buffer.put_character (')') -- Add `eif_helpers.h' for C compilation where all bit functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_helpers_header_name_id) end generate_min (buffer: GENERATION_BUFFER; type_of_basic: INTEGER; target: REGISTRABLE; parameter: PARAMETER_BL) -- Generate fast wrapper for call on `min' where target and parameter -- are both basic types. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameter_not_void: parameter /= Void do inspect type_of_basic when character_type_id then if is_wide then buffer.put_string ("eif_min_wide_char (") else buffer.put_string ("eif_min_char (") end when integer_type_id then if is_signed_integer then buffer.put_string ("eif_min_") else buffer.put_string ("eif_min_u") end inspect integer_size when 8 then buffer.put_string ("int8 (") when 16 then buffer.put_string ("int16 (") when 32 then buffer.put_string ("int32 (") when 64 then buffer.put_string ("int64 (") end when real_32_type_id then buffer.put_string ("eif_min_real32 (") when real_64_type_id then buffer.put_string ("eif_min_real64 (") end target.print_register buffer.put_character (',') parameter.print_immediate_register buffer.put_character (')') -- Add `eif_helpers.h' for C compilation where all bit functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_helpers_header_name_id) end generate_three_way_comparison (buffer: GENERATION_BUFFER; type_of_basic: INTEGER; target: REGISTRABLE; parameter: PARAMETER_BL) -- Generate fast wrapper for call on `three_way_comparison' where target and parameter -- are both basic types. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameter_not_void: parameter /= Void do inspect type_of_basic when character_type_id then if is_wide then buffer.put_string ("eif_twc_wide_char (") else buffer.put_string ("eif_twc_char (") end when integer_type_id then if is_signed_integer then buffer.put_string ("eif_twc_") else buffer.put_string ("eif_twc_u") end inspect integer_size when 8 then buffer.put_string ("int8 (") when 16 then buffer.put_string ("int16 (") when 32 then buffer.put_string ("int32 (") when 64 then buffer.put_string ("int64 (") end when real_32_type_id then buffer.put_string ("eif_twc_real32 (") when real_64_type_id then buffer.put_string ("eif_twc_real64 (") end target.print_register buffer.put_character (',') parameter.print_immediate_register buffer.put_character (')') -- Add `eif_helpers.h' for C compilation where all bit functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_helpers_header_name_id) end generate_abs (buffer: GENERATION_BUFFER; type_of_basic: INTEGER; target: REGISTRABLE) -- Generate fast wrapper for call on `abs' where target -- is a basic type. require buffer_not_void: buffer /= Void target_not_void: target /= Void do inspect type_of_basic when integer_type_id then if is_signed_integer then buffer.put_string ("eif_abs_") else buffer.put_string ("eif_abs_u") end inspect integer_size when 8 then buffer.put_string ("int8 (") when 16 then buffer.put_string ("int16 (") when 32 then buffer.put_string ("int32 (") when 64 then buffer.put_string ("int64 (") end when real_32_type_id then buffer.put_string ("eif_abs_real32 (") when real_64_type_id then buffer.put_string ("eif_abs_real64 (") end target.print_register buffer.put_character (')') -- Add `eif_helpers.h' for C compilation where all bit functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_helpers_header_name_id) end generate_memory_routine (buffer: GENERATION_BUFFER; f_type: INTEGER; target: REGISTRABLE; parameters: BYTE_LIST [PARAMETER_B]) -- Generate fast wrapper for call on `memory_copy', -- `memory_move', `memory_set' and `memory_calloc' from POINTER. require buffer_not_void: buffer /= Void target_not_void: target /= Void valid_paramaters: f_type /= memory_free implies parameters /= Void valid_function_type: f_type = memory_move or f_type = memory_copy or f_type = memory_set or f_type = memory_free or f_type = memory_alloc or f_type = memory_calloc do shared_include_queue_put ({PREDEFINED_NAMES}.string_header_name_id) inspect f_type when memory_move then buffer.put_string ("memmove((void *)") when memory_copy then buffer.put_string ("memcpy((void *)") when memory_set then buffer.put_string ("memset((void *)") when memory_alloc then buffer.put_string ("malloc((size_t)") when memory_calloc then buffer.put_string ("calloc((size_t)") when memory_free then buffer.put_string ("free(") end if f_type /= memory_alloc and f_type /= memory_calloc then target.print_register end inspect f_type when memory_free, memory_alloc, memory_calloc then when memory_set then buffer.put_string (", (int) ") else buffer.put_string (", (const void *) ") end inspect f_type when memory_move, memory_set, memory_copy, memory_calloc then check valid_parameters: parameters.count = 2 end if attached {PARAMETER_BL} parameters [1] as parameter then parameter.print_immediate_register end buffer.put_string (", (size_t) ") if attached {PARAMETER_BL} parameters [2] as parameter then parameter.print_immediate_register end when memory_alloc then check valid_paramters: parameters.count = 1 end if attached {PARAMETER_BL} parameters [1] as parameter then parameter.print_immediate_register end else end buffer.put_string (")") end generate_bit_operation (buffer: GENERATION_BUFFER; op: INTEGER; target: REGISTRABLE; parameter: PARAMETER_BL) -- Generate fast wrapper for call on `bit_xxx' where target and parameter -- are both basic types of type INTEGER. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameter_not_void: (op /= bit_not_type) implies parameter /= Void do if op = bit_not_type then buffer.put_string ("eif_bit_not(") target.print_register else inspect op when bit_and_type then buffer.put_string ("eif_bit_and(") when bit_or_type then buffer.put_string ("eif_bit_or(") when bit_xor_type then buffer.put_string ("eif_bit_xor(") when bit_shift_left_type then buffer.put_string ("eif_bit_shift_left(") when bit_shift_right_type then buffer.put_string ("eif_bit_shift_right(") when bit_test_type then buffer.put_string ("eif_bit_test(") target.c_type.generate (buffer) buffer.put_character (',') end target.print_register buffer.put_character (',') parameter.print_immediate_register end buffer.put_character (')') -- Add `eif_misc.h' for C compilation where all bit functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_misc_header_name_id) end generate_set_bit (buffer: GENERATION_BUFFER; target: REGISTRABLE; parameters: BYTE_LIST [PARAMETER_B]) -- Generate fast wrapper for call on `set_bit' where target and parameter -- are both basic types of type INTEGER. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameters_not_void: parameters /= Void valid_parameters: parameters.count = 2 do buffer.put_string ("eif_set_bit(") target.c_type.generate (buffer) buffer.put_character (',') target.print_register buffer.put_character (',') if attached {PARAMETER_BL} parameters [1] as parameter then parameter.print_immediate_register end buffer.put_character (',') if attached {PARAMETER_BL} parameters [2] as parameter then parameter.print_immediate_register end buffer.put_character (')') -- Add `eif_misc.h' for C compilation where all bit functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_misc_header_name_id) end generate_set_bit_with_mask (buffer: GENERATION_BUFFER; target: REGISTRABLE; parameters: BYTE_LIST [PARAMETER_B]) -- Generate fast wrapper for call on `set_bit_with_mask' where target and parameter -- are both basic types of type INTEGER. require buffer_not_void: buffer /= Void target_not_void: target /= Void parameters_not_void: parameters /= Void valid_parameters: parameters.count = 2 do buffer.put_string ("eif_set_bit_with_mask(") target.print_register buffer.put_character (',') if attached {PARAMETER_BL} parameters [1] as parameter then parameter.print_immediate_register end buffer.put_character (',') if attached {PARAMETER_BL} parameters [2] as parameter then parameter.print_immediate_register end buffer.put_character (')') -- Add `eif_misc.h' for C compilation where all bit functions are declared. shared_include_queue_put ({PREDEFINED_NAMES}.eif_misc_header_name_id) end generate_zero (buffer: GENERATION_BUFFER; type_of_basic: INTEGER) -- Generate fast wrapper for call on `zero' for INTEGER, -- REAL and DOUBLE. require buffer_not_void: buffer /= Void valid_type_of_basic: type_of_basic = integer_type_id or else type_of_basic = real_32_type_id or else type_of_basic = real_64_type_id do inspect type_of_basic when integer_type_id then buffer.put_string ("0") when real_32_type_id, real_64_type_id then buffer.put_string ("0.0") end end generate_one (buffer: GENERATION_BUFFER; type_of_basic: INTEGER) -- Generate fast wrapper for call on `one' for INTEGER, -- REAL and DOUBLE. require buffer_not_void: buffer /= Void valid_type_of_basic: type_of_basic = integer_type_id or else type_of_basic = real_32_type_id or else type_of_basic = real_64_type_id do inspect type_of_basic when integer_type_id then buffer.put_string ("1") when real_32_type_id, real_64_type_id then buffer.put_string ("1.0") end end feature {NONE} -- Type information boolean_type_id: INTEGER = 1 character_type_id: INTEGER = 2 integer_type_id: INTEGER = 3 pointer_type_id: INTEGER = 4 real_32_type_id: INTEGER = 5 real_64_type_id: INTEGER = 6 -- Constant defining type integer_size: like {NATURAL_A}.size -- Size of datatype when `type_of' returns `integer_type_id'. is_signed_integer: BOOLEAN -- Is `integer_type_id' a INTEGER_XX type? -- False for NATURAL_XX type. is_wide: BOOLEAN -- Is `character_type_id' returned by `type_of' a WIDE_CHARACTER? type_of (b: BASIC_A): INTEGER -- Returns corresponding type constants to `b'. require b_not_void: b /= Void do inspect b.sk_value (Void) when {SK_CONST}.sk_bool then Result := boolean_type_id when {SK_CONST}.sk_char8 then Result := character_type_id is_wide := False when {SK_CONST}.sk_char32 then Result := character_type_id is_wide := True when {SK_CONST}.sk_uint8, {SK_CONST}.sk_uint16, {SK_CONST}.sk_uint32, {SK_CONST}.sk_uint64 then Result := integer_type_id is_signed_integer := False integer_size := if attached {NATURAL_A} b as t then t.size else integer_size.zero end when {SK_CONST}.sk_int8, {SK_CONST}.sk_int16, {SK_CONST}.sk_int32, {SK_CONST}.sk_int64 then Result := integer_type_id is_signed_integer := True integer_size := if attached {INTEGER_A} b as t then t.size else integer_size.zero end when {SK_CONST}.sk_pointer then Result := pointer_type_id when {SK_CONST}.sk_real32 then Result := real_32_type_id when {SK_CONST}.sk_real64 then Result := real_64_type_id else if attached {TYPED_POINTER_A} b as t then Result := pointer_type_id end end ensure valid_type_id: Result = boolean_type_id or else Result = character_type_id or else Result = integer_type_id or else Result = pointer_type_id or else Result = real_32_type_id or else Result = real_64_type_id end note copyright: "Copyright (c) 1984-2021, Eiffel Software" license: "GPL version 2 (see http://www.eiffel.com/licensing/gpl.txt)" licensing_options: "http://www.eiffel.com/licensing" copying: "[ This file is part of Eiffel Software's Eiffel Development Environment. Eiffel Software's Eiffel Development Environment is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2 of the License (available at the URL listed under "license" above). Eiffel Software's Eiffel Development Environment is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Eiffel Software's Eiffel Development Environment; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA ]" source: "[ Eiffel Software 5949 Hollister Ave., Goleta, CA 93117 USA Telephone 805-685-1006, Fax 805-685-6869 Website http://www.eiffel.com Customer support http://support.eiffel.com ]" end