From a5052bcf3f4f93888aa145b6697dd77d1e053433 Mon Sep 17 00:00:00 2001 From: kevstone Date: Mon, 13 Nov 2023 19:40:54 +0000 Subject: [PATCH] More bugfixing --- src/conversion/accessor_input_files | 2 +- .../grib_accessor_class_bit.py | 2 +- .../grib_accessor_class_bits.py | 2 +- .../grib_accessor_class_bytes.py | 2 +- .../grib_accessor_class_codetable.py | 29 +++++ .../grib_accessor_class_count_missing.py | 2 +- ...a_g1second_order_constant_width_packing.py | 2 +- ...ass_data_g1second_order_general_packing.py | 2 +- .../grib_accessor_class_data_raw_packing.py | 2 +- ..._accessor_class_data_run_length_packing.py | 2 +- .../grib_accessor_class_data_sh_packed.py | 2 +- .../grib_accessor_class_data_sh_unpacked.py | 2 +- ...grib_accessor_class_data_simple_packing.py | 2 +- ...ib_accessor_class_g1_half_byte_codeflag.py | 2 +- .../grib_accessor_class_g1bitmap.py | 2 +- .../grib_accessor_class_md5.py | 2 +- .../grib_accessor_class_message_copy.py | 2 +- .../grib_accessor_class_uint64.py | 2 +- ...rib_accessor_class_uint64_little_endian.py | 2 +- .../grib_accessor_class_uint8.py | 2 +- .../grib_accessor_class_unsigned.py | 48 ++++++++ src/conversion/arg.py | 1 + src/conversion/constructor_method_conv.py | 32 ----- src/conversion/convert.py | 22 ++-- src/conversion/destructor_method_conv.py | 10 ++ src/conversion/func_conv.py | 50 ++++---- .../grib_bits_funcsig_conv.py | 8 +- .../all_grib_stub_funcsig_conv.py | 2 - .../grib_bits_any_endian_stub_funcsig_conv.py | 8 +- ..._bits_fast_big_endian_stub_funcsig_conv.py | 10 -- .../grib_buffer_stub_funcsig_conv.py | 6 +- src/conversion/grib_accessor_conv.py | 18 +-- src/conversion/method_conv.py | 112 +++++++++++------- src/cpp/CMakeLists.txt | 3 +- src/cpp/eccodes/accessor/Accessor.cc | 4 +- src/cpp/eccodes/accessor/Accessor.h | 4 +- src/cpp/eccodes/accessor/AccessorBuffer.h | 23 ++-- .../accessor/AccessorData/AccessorData.cc | 4 +- .../accessor/AccessorData/AccessorData.h | 9 +- src/cpp/eccodes/accessor/GribCpp/GribBits.cc | 8 +- src/cpp/eccodes/accessor/GribCpp/GribBits.h | 8 +- .../GribStub/GribBitsAnyEndianStub.cc | 31 +++-- .../accessor/GribStub/GribBitsAnyEndianStub.h | 12 +- .../GribStub/GribBitsFastBigEndianStub.cc | 14 --- .../GribStub/GribBitsFastBigEndianStub.h | 12 -- .../accessor/GribStub/GribBufferStub.cc | 7 +- .../accessor/GribStub/GribBufferStub.h | 7 +- .../accessor/GribStub/GribStubIncludes.h | 2 +- .../accessor/GribStub/GribVirtualValueStub.h | 21 ++++ .../eccodes/accessor/Test/GribFileTests.cc | 2 +- src/grib_accessor_class_unsigned.cc | 2 +- 51 files changed, 328 insertions(+), 239 deletions(-) create mode 100644 src/conversion/accessor_specific/grib_accessor_class_codetable.py create mode 100644 src/conversion/accessor_specific/grib_accessor_class_unsigned.py delete mode 100755 src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_fast_big_endian_stub_funcsig_conv.py delete mode 100644 src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.cc delete mode 100644 src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.h create mode 100644 src/cpp/eccodes/accessor/GribStub/GribVirtualValueStub.h diff --git a/src/conversion/accessor_input_files b/src/conversion/accessor_input_files index b4103af6a..cd9f12f51 100644 --- a/src/conversion/accessor_input_files +++ b/src/conversion/accessor_input_files @@ -24,7 +24,7 @@ grib_accessor_class_change_scanning_direction.cc grib_accessor_class_check_internal_version.cc grib_accessor_class_closest_date.cc grib_accessor_class_codeflag.cc -grib_accessor_class_codetable.cc +#grib_accessor_class_codetable.cc grib_accessor_class_codetable_title.cc grib_accessor_class_codetable_units.cc grib_accessor_class_concept.cc diff --git a/src/conversion/accessor_specific/grib_accessor_class_bit.py b/src/conversion/accessor_specific/grib_accessor_class_bit.py index f161f4769..12307708b 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_bit.py +++ b/src/conversion/accessor_specific/grib_accessor_class_bit.py @@ -6,5 +6,5 @@ class BitDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","mdata") : arg.Arg("DataPointer","mdata"), + arg.Arg("unsigned char*","mdata") : arg.Arg("AccessorDataPointer","mdata"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_bits.py b/src/conversion/accessor_specific/grib_accessor_class_bits.py index 44578c159..1ce070e8e 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_bits.py +++ b/src/conversion/accessor_specific/grib_accessor_class_bits.py @@ -6,7 +6,7 @@ class BitsDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","p") : arg.Arg("DataPointer","p"), + arg.Arg("unsigned char*","p") : arg.Arg("AccessorDataPointer","p"), arg.Arg("int","type") : arg.Arg("GribType","type"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_bytes.py b/src/conversion/accessor_specific/grib_accessor_class_bytes.py index 2d4f7bcc7..81dd33619 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_bytes.py +++ b/src/conversion/accessor_specific/grib_accessor_class_bytes.py @@ -6,6 +6,6 @@ class BytesDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","p") : arg.Arg("DataPointer","p"), + arg.Arg("unsigned char*","p") : arg.Arg("AccessorDataPointer","p"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_codetable.py b/src/conversion/accessor_specific/grib_accessor_class_codetable.py new file mode 100644 index 000000000..b9505473c --- /dev/null +++ b/src/conversion/accessor_specific/grib_accessor_class_codetable.py @@ -0,0 +1,29 @@ +from accessor_specific.default import AccessorSpecific + +from converter_collection import Converter +import static_func_funcsig_conv +from funcsig import FuncSig +from arg_indexes import ArgIndexes +from arg import Arg +import arg +from funcsig_mapping import FuncSigMapping + +class CodetableDataFuncSigConverter(static_func_funcsig_conv.StaticFunctionFuncSigConverter): + func_conversions = [ + FuncSigMapping(FuncSig("int", "grib_inline_strcmp", [Arg("const char*", "a"), Arg("const char*", "b")]), + FuncSig(None, None, [None, None])), + FuncSigMapping(FuncSig("int", "str_eq", [Arg("const char*", "a"), Arg("const char*", "b")]), + FuncSig(None, None, [None, None])), + ] + + def __init__(self, cfuncsig): + super().__init__(cfuncsig) + self._conversions.extend(self.func_conversions) + +class CodetableDataAccessorSpecific(AccessorSpecific): + def __init__(self) -> None: + super().__init__() + + def update_converters(self, converters): + converters[Converter.STATIC_FUNC_FUNCSIG] = CodetableDataFuncSigConverter + return converters diff --git a/src/conversion/accessor_specific/grib_accessor_class_count_missing.py b/src/conversion/accessor_specific/grib_accessor_class_count_missing.py index b576ba4eb..421b2c35e 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_count_missing.py +++ b/src/conversion/accessor_specific/grib_accessor_class_count_missing.py @@ -6,6 +6,6 @@ class CountMissingDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","p") : arg.Arg("DataPointer","p"), + arg.Arg("unsigned char*","p") : arg.Arg("AccessorDataPointer","p"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_constant_width_packing.py b/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_constant_width_packing.py index 998095976..9e289e79d 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_constant_width_packing.py +++ b/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_constant_width_packing.py @@ -6,6 +6,6 @@ class DataG1secondOrderConstantWidthPackingDataAccessorSpecific(AccessorSpecific super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_general_packing.py b/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_general_packing.py index 4a73d8c83..4d2cde02b 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_general_packing.py +++ b/src/conversion/accessor_specific/grib_accessor_class_data_g1second_order_general_packing.py @@ -25,7 +25,7 @@ class DataG1secondOrderGeneralPackingDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } def update_converters(self, converters): diff --git a/src/conversion/accessor_specific/grib_accessor_class_data_raw_packing.py b/src/conversion/accessor_specific/grib_accessor_class_data_raw_packing.py index 3f6d61ac1..4a0b717e7 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_data_raw_packing.py +++ b/src/conversion/accessor_specific/grib_accessor_class_data_raw_packing.py @@ -6,6 +6,6 @@ class DataRawPackingDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_data_run_length_packing.py b/src/conversion/accessor_specific/grib_accessor_class_data_run_length_packing.py index ff445fa41..3f2f4e065 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_data_run_length_packing.py +++ b/src/conversion/accessor_specific/grib_accessor_class_data_run_length_packing.py @@ -6,6 +6,6 @@ class DataRunLengthPackingDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_data_sh_packed.py b/src/conversion/accessor_specific/grib_accessor_class_data_sh_packed.py index b7342ccab..820a6eb66 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_data_sh_packed.py +++ b/src/conversion/accessor_specific/grib_accessor_class_data_sh_packed.py @@ -6,6 +6,6 @@ class DataShPackedDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_data_sh_unpacked.py b/src/conversion/accessor_specific/grib_accessor_class_data_sh_unpacked.py index 29491ec1b..8834fc1fd 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_data_sh_unpacked.py +++ b/src/conversion/accessor_specific/grib_accessor_class_data_sh_unpacked.py @@ -6,6 +6,6 @@ class DataShUnpackedDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_data_simple_packing.py b/src/conversion/accessor_specific/grib_accessor_class_data_simple_packing.py index 1da0172d1..27ba52db6 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_data_simple_packing.py +++ b/src/conversion/accessor_specific/grib_accessor_class_data_simple_packing.py @@ -25,7 +25,7 @@ class DataSimplePackingDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } def update_converters(self, converters): diff --git a/src/conversion/accessor_specific/grib_accessor_class_g1_half_byte_codeflag.py b/src/conversion/accessor_specific/grib_accessor_class_g1_half_byte_codeflag.py index 9a94593ca..e727d8a38 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_g1_half_byte_codeflag.py +++ b/src/conversion/accessor_specific/grib_accessor_class_g1_half_byte_codeflag.py @@ -6,6 +6,6 @@ class G1HalfByteCodeflagDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","dat") : arg.Arg("DataPointer","dat"), + arg.Arg("unsigned char*","dat") : arg.Arg("AccessorDataPointer","dat"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_g1bitmap.py b/src/conversion/accessor_specific/grib_accessor_class_g1bitmap.py index 3ffdbfb04..7e282fc1d 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_g1bitmap.py +++ b/src/conversion/accessor_specific/grib_accessor_class_g1bitmap.py @@ -6,6 +6,6 @@ class G1BitmapDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","buf") : arg.Arg("DataPointer","buf"), + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataPointer","buf"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_md5.py b/src/conversion/accessor_specific/grib_accessor_class_md5.py index af42be793..2b51f1e81 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_md5.py +++ b/src/conversion/accessor_specific/grib_accessor_class_md5.py @@ -6,6 +6,6 @@ class Md5DataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","mess") : arg.Arg("DataPointer","mess"), + arg.Arg("unsigned char*","mess") : arg.Arg("AccessorDataPointer","mess"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_message_copy.py b/src/conversion/accessor_specific/grib_accessor_class_message_copy.py index 161da120b..197063cce 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_message_copy.py +++ b/src/conversion/accessor_specific/grib_accessor_class_message_copy.py @@ -6,6 +6,6 @@ class MessageCopyDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","v") : arg.Arg("DataPointer","v"), + arg.Arg("unsigned char*","v") : arg.Arg("AccessorDataPointer","v"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_uint64.py b/src/conversion/accessor_specific/grib_accessor_class_uint64.py index 045530eac..d08e2e7ce 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_uint64.py +++ b/src/conversion/accessor_specific/grib_accessor_class_uint64.py @@ -6,6 +6,6 @@ class Uint64DataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","data") : arg.Arg("DataPointer","data"), + arg.Arg("unsigned char*","data") : arg.Arg("AccessorDataPointer","data"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_uint64_little_endian.py b/src/conversion/accessor_specific/grib_accessor_class_uint64_little_endian.py index cab44e57b..f49bc3dd6 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_uint64_little_endian.py +++ b/src/conversion/accessor_specific/grib_accessor_class_uint64_little_endian.py @@ -6,6 +6,6 @@ class Uint64LittleEndianDataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","data") : arg.Arg("DataPointer","data"), + arg.Arg("unsigned char*","data") : arg.Arg("AccessorDataPointer","data"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_uint8.py b/src/conversion/accessor_specific/grib_accessor_class_uint8.py index a8da7d17d..82472b367 100644 --- a/src/conversion/accessor_specific/grib_accessor_class_uint8.py +++ b/src/conversion/accessor_specific/grib_accessor_class_uint8.py @@ -6,6 +6,6 @@ class Uint8DataAccessorSpecific(AccessorSpecific): super().__init__() self._custom_arg_transforms = { - arg.Arg("unsigned char*","data") : arg.Arg("DataPointer","data"), + arg.Arg("unsigned char*","data") : arg.Arg("AccessorDataPointer","data"), } diff --git a/src/conversion/accessor_specific/grib_accessor_class_unsigned.py b/src/conversion/accessor_specific/grib_accessor_class_unsigned.py new file mode 100644 index 000000000..f8e0c8b68 --- /dev/null +++ b/src/conversion/accessor_specific/grib_accessor_class_unsigned.py @@ -0,0 +1,48 @@ +from accessor_specific.default import AccessorSpecific + +from converter_collection import Converter +import static_func_funcsig_conv +import private_method_funcsig_conv +from funcsig import FuncSig +from arg_indexes import ArgIndexes +from arg import Arg +import arg +from funcsig_mapping import FuncSigMapping + +class UnsignedDataFuncSigConverter(static_func_funcsig_conv.StaticFunctionFuncSigConverter): + func_conversions = [ + FuncSigMapping(FuncSig("int", "value_is_missing", [Arg("long", "val")]), + FuncSig("int", "valueIsMissing", [Arg("long", "val")])), + ] + + def __init__(self, cfuncsig): + super().__init__(cfuncsig) + self._conversions.extend(self.func_conversions) + +class UnsignedDataPrivateMethodFuncSigConverter(private_method_funcsig_conv.PrivateMethodFuncSigConverter): + func_conversions = [ + FuncSigMapping(FuncSig("int", "pack_long_unsigned_helper", [Arg("grib_accessor*", "a"), Arg("const long*", "val"), Arg("size_t*", "len"), Arg("int", "check")]), + FuncSig("GribStatus", "packLongUnsignedHelper", [None, Arg("std::vector const&", "longValues"), None, Arg("int", "check")]), + ArgIndexes(cbuffer=1, clength=2, cpp_container=1)), + ] + + def __init__(self, cfuncsig): + super().__init__(cfuncsig) + self._conversions.extend(self.func_conversions) + +class UnsignedDataAccessorSpecific(AccessorSpecific): + def __init__(self) -> None: + super().__init__() + + self._custom_arg_transforms = { + arg.Arg("unsigned char*","buf") : arg.Arg("AccessorDataBuffer","buf"), + } + + self._custom_member_arg_transforms = { + arg.Arg("grib_arguments*","arg") : arg.Arg("AccessorInitData","arg"), + } + + def update_converters(self, converters): + converters[Converter.STATIC_FUNC_FUNCSIG] = UnsignedDataFuncSigConverter + converters[Converter.PRIVATE_METHOD_FUNCSIG] = UnsignedDataPrivateMethodFuncSigConverter + return converters diff --git a/src/conversion/arg.py b/src/conversion/arg.py index 5cb9e7894..f3475e08b 100755 --- a/src/conversion/arg.py +++ b/src/conversion/arg.py @@ -96,6 +96,7 @@ container_types = [ "std::array", "std::vector", "std::map", + "AccessorDataBuffer", ] # Return True if type is a container (std::vector etc) diff --git a/src/conversion/constructor_method_conv.py b/src/conversion/constructor_method_conv.py index 4d75effef..bbc8cea55 100755 --- a/src/conversion/constructor_method_conv.py +++ b/src/conversion/constructor_method_conv.py @@ -12,38 +12,6 @@ class ConstructorMethodConverter(MethodConverter): def create_cpp_function(self, cppfuncsig): return constructor_method.ConstructorMethod(cppfuncsig, self._transforms.types["self"]) - # overridden to short-circuit well-knwon transforms! - def convert_cfunction_calls(self, line): - - # Transform the argument getters - m = re.search(r"((self->)?(\w+)\s+=\s+)?\bgrib_arguments_get_(\w+)\([^,]+, [^,]+, ([^\)]+)\)", line) - if m: - ctype = assignment_text = "" - if m.group(1): - assignment_text = m.group(1) - member_name = m.group(3) - for cmember, cppmember in self._transforms.members.items(): - if cmember.name == member_name: - ctype = cppmember.type - break - - get_what = m.group(4) - if get_what == "expression": - get_what = "GribExpressionPtr" - elif get_what in ["string", "name"]: - get_what = "std::string" - if not ctype: - ctype = "AccessorName" - - if ctype == "AccessorName": - line = re.sub(m.re, f"{assignment_text}AccessorName(std::get<{get_what}>(initData.args[{m.group(5)}].second))", line) - else: - line = re.sub(m.re, f"{assignment_text}std::get<{get_what}>(initData.args[{m.group(5)}].second)", line) - - debug.line("convert_cfunction_calls", f"Updated [bgrib_arguments_get_expression] line=[{line}]") - - return super().convert_cfunction_calls(line) - # Overridden to get correct InitData "set size" def container_func_call_for(self, cpparg, action, data=""): if cpparg.underlying_type == "AccessorInitData": diff --git a/src/conversion/convert.py b/src/conversion/convert.py index 524d4251a..82bcb5004 100755 --- a/src/conversion/convert.py +++ b/src/conversion/convert.py @@ -41,8 +41,9 @@ env = Environment( ) def parse_file(path): - in_definition = False - in_implementation = False + in_class_def_section = False + in_class_imp_section = False + in_main_code_section = False in_function = False includes = [] template = None @@ -104,31 +105,32 @@ def parse_file(path): line = line.rstrip() if stripped_line.startswith("START_CLASS_DEF"): - in_definition = True + in_class_def_section = True continue if stripped_line.startswith("END_CLASS_DEF"): - in_definition = False + in_class_def_section = False continue if stripped_line.startswith("/* START_CLASS_IMP */"): - in_implementation = True + in_class_imp_section = True # Discard any global lines captured before here... global_function.clear_lines() continue if stripped_line.startswith("/* END_CLASS_IMP */"): - in_implementation = False + in_class_imp_section = False + in_main_code_section = True continue - if in_implementation: + if in_class_imp_section: m = re.match(r"\s*\"(\w+)\",\s+/\* name \*/", stripped_line) if m: definitions["FACTORY"] = [m.group(1)] continue - if in_definition: + if in_class_def_section: if stripped_line.strip() == "": continue bits = [s.strip() for s in re.split(r"[=;]+", stripped_line)] @@ -141,6 +143,10 @@ def parse_file(path): raise continue + if not in_main_code_section: + debug.line("parse_file",f"[IGNORING] [{line}]") + continue + # Try and create a FuncSig from the line, if successful then it's a function definition! cfuncsig = funcsig.FuncSig.from_string(line) if cfuncsig: diff --git a/src/conversion/destructor_method_conv.py b/src/conversion/destructor_method_conv.py index 006dbe8ab..c9b910d47 100755 --- a/src/conversion/destructor_method_conv.py +++ b/src/conversion/destructor_method_conv.py @@ -9,3 +9,13 @@ class DestructorMethodConverter(MethodConverter): def create_cpp_function(self, cppfuncsig): return destructor_method.DestructorMethod(cppfuncsig, self._transforms.types["self"]) + + # Overridden to create an empty constructor if name is None + def create_cpp_body(self): + if self._cppfunction.name is None: + debug.line("create_cpp_body", f"\n============================== {self._cfunction.name} [IN] ==============================\n") + debug.line("create_cpp_body", f"Creating empty destructor body as no conversion defined (name is None)") + debug.line("create_cpp_body", f"\n============================== {self._cfunction.name} [OUT] ==============================\n") + return ["/* Destructor has been deleted */"] + + return super().create_cpp_body() diff --git a/src/conversion/func_conv.py b/src/conversion/func_conv.py index b656f7425..19fc718fe 100755 --- a/src/conversion/func_conv.py +++ b/src/conversion/func_conv.py @@ -894,22 +894,26 @@ class FunctionConverter: # First, check for malloc # Note: Group 2 (\()? and group 6 (\)) ensure we match the correct number of braces (grib_X()) vs grib_X() # Note: Group 4 ([^,]+,)? is an optional match for the first param (usually c) which we discard, but may have already been removed! - m = re.search(r"\s*(\([^\)]+\))?(\()?grib_context_malloc(_\w+)?\(([^,]+,)?(.+)\)(\))[,;]", post_match_string) - + m = re.search(r"\s*(\([^\)]+\))?(\()?grib_context_malloc(_\w+)?\(([^,]+,)?([^\)]*\)+)([,;])", post_match_string) if m: + malloc_type = m.group(3) if m.group(3) else "" match_string = m.group(5) - if not m.group(2): - match_string += m.group(6) + + # Strip trailing ')' so parens match! + open_parens, close_parens = utils.count_parentheses(match_string) + extra_close_parens = close_parens-open_parens + if extra_close_parens > 0: + match_string = match_string[:len(match_string)-extra_close_parens] # Check if we're creating (new arg) or resizing (existing arg) if cpp_container_arg in self._new_cppargs_list: - transformed_line = f"{cpp_container_arg.name}({match_string});" - debug.line("transform_cpp_container_assignment", f"[CREATION] Replaced [{cpp_container_arg.name} = grib_context_malloc_X({match_string})] with [{transformed_line}]") + transformed_line = f"{cpp_container_arg.name}({match_string}{m.group(6)}" + debug.line("transform_cpp_container_assignment", f"[CREATION] Replaced [{cpp_container_arg.name} = grib_context_malloc{malloc_type}{m.group(3)}({match_string})] with [{transformed_line}]") return transformed_line else: container_func_call = self.container_func_call_for(cpp_container_arg, "resize", match_string) - transformed_line = cpp_container_arg.name + "." + container_func_call + ";" - debug.line("transform_cpp_container_assignment", f"[EXISTING] Replaced {cpp_container_arg.name} = grib_context_malloc_X({match_string}) with [{transformed_line}]") + transformed_line = cpp_container_arg.name + "." + container_func_call + m.group(6) + debug.line("transform_cpp_container_assignment", f"[EXISTING] Replaced {cpp_container_arg.name} = grib_context_malloc_{malloc_type}({match_string}) with [{transformed_line}]") return transformed_line # Extract the assigned value @@ -1001,6 +1005,8 @@ class FunctionConverter: debug.line("transform_cpp_container_non_assignment", f"INDEX OP: Replaced [{cpp_container_arg.name}{match_token.as_string()}{m.group(1)}] with post_match_string=[{cpp_container_arg.name}{post_match_string}]") return cpp_container_arg.name + post_match_string + elif match_token.value in [",",")"]: + pass #assert False, f"FUNC ARG? [{arg.arg_string(cpp_container_arg)}]" # TODO: Handle other comparisons? @@ -1220,24 +1226,13 @@ class FunctionConverter: return line - # Specific check for if(c) or if(!c) where c is a container - def process_if_test(self, line): - m = re.search(r"\b(if\s*\(!?)(\w+)\)", line) - if m: - container_arg = self._transforms.cpparg_for_cppname(m.group(2)) - if container_arg and arg.is_container(container_arg): - container_func_call = self.container_func_call_for(container_arg, "size") - transformed_call = f"{container_arg.name}.{container_func_call}" - line = re.sub(re.escape(m.group(2)), f"{transformed_call}", line) - debug.line("process_if_test", f"Replaced [{m.group(0)}] with [{transformed_call}] line:[{line}]") + # Specific check for TEST(arg) or TEST(!arg) where TEST is if, assert etc + # Supports special handling for container types + def process_boolean_test(self, line): + m = re.search(r"\b(\w+)(\s*\(!?)(\w+)\)", line) - return line - - # Specific check for if(c) or if(!c) where c is a container (or other special types) - def process_assert_test(self, line): - m = re.search(r"\b(Assert\s*\(!?)(\w+)\)", line) - if m: - test_arg = self._transforms.cpparg_for_cppname(m.group(2)) + if m and m.group(1) in ["if", "Assert"]: + test_arg = self._transforms.cpparg_for_cppname(m.group(3)) if test_arg: transformed_call = None @@ -1248,15 +1243,14 @@ class FunctionConverter: transformed_call = f"{test_arg.name}.get().size()" if transformed_call: - line = re.sub(re.escape(m.group(2)), f"{transformed_call}", line) + line = re.sub(re.escape(m.group(3)), f"{transformed_call}", line) debug.line("process_assert_test", f"Replaced [{m.group(0)}] with [{transformed_call}] line:[{line}]") return line # Override for any final updates... def final_updates(self, line): - line = self.process_if_test(line) - line = self.process_assert_test(line) + line = self.process_boolean_test(line) return line diff --git a/src/conversion/funcsig_conversions/grib_cpp_funcsig_conversions/grib_bits_funcsig_conv.py b/src/conversion/funcsig_conversions/grib_cpp_funcsig_conversions/grib_bits_funcsig_conv.py index 2354084da..9ec5e97e0 100755 --- a/src/conversion/funcsig_conversions/grib_cpp_funcsig_conversions/grib_bits_funcsig_conv.py +++ b/src/conversion/funcsig_conversions/grib_cpp_funcsig_conversions/grib_bits_funcsig_conv.py @@ -6,15 +6,15 @@ from funcsig_mapping import FuncSigMapping grib_bits_funcsig_conversions = [ FuncSigMapping( FuncSig("void", "grib_set_bit_on", [Arg("unsigned char*", "p"), Arg("long*", "bitp")]), - FuncSig("void", "gribSetBitOn", [Arg("DataPointer", "p"), Arg("long&", "bitp")])), + FuncSig("void", "gribSetBitOn", [Arg("AccessorDataPointer", "p"), Arg("long&", "bitp")])), FuncSigMapping( FuncSig("void", "grib_set_bits_on", [Arg("unsigned char*", "p"), Arg("long*", "bitp"), Arg("long", "nbits")]), - FuncSig("void", "gribSetBitsOn", [Arg("DataPointer", "p"), Arg("long&", "bitp"), Arg("long", "nbits")])), + FuncSig("void", "gribSetBitsOn", [Arg("AccessorDataPointer", "p"), Arg("long&", "bitp"), Arg("long", "nbits")])), FuncSigMapping( FuncSig("void", "grib_set_bit_off", [Arg("unsigned char*", "p"), Arg("long*", "bitp")]), - FuncSig("void", "gribSetBitOff", [Arg("DataPointer", "p"), Arg("long&", "bitp")])), + FuncSig("void", "gribSetBitOff", [Arg("AccessorDataPointer", "p"), Arg("long&", "bitp")])), FuncSigMapping( FuncSig("void", "grib_set_bit", [Arg("unsigned char*", "p"), Arg("long", "bitp"), Arg("int", "val")]), - FuncSig("void", "gribSetBit", [Arg("DataPointer", "p"), Arg("long&", "bitp"), Arg("int", "val")])), + FuncSig("void", "gribSetBit", [Arg("AccessorDataPointer", "p"), Arg("long&", "bitp"), Arg("int", "val")])), ] diff --git a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/all_grib_stub_funcsig_conv.py b/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/all_grib_stub_funcsig_conv.py index ab4ce0016..200397a2a 100755 --- a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/all_grib_stub_funcsig_conv.py +++ b/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/all_grib_stub_funcsig_conv.py @@ -2,7 +2,6 @@ import funcsig_conversions.grib_stub_funcsig_conversions.grib_accessor_class_stub_funcsig_conv as grib_accessor_class_stub_funcsig_conv import funcsig_conversions.grib_stub_funcsig_conversions.grib_accessor_stub_funcsig_conv as grib_accessor_stub_funcsig_conv import funcsig_conversions.grib_stub_funcsig_conversions.grib_bits_any_endian_stub_funcsig_conv as grib_bits_any_endian_stub_funcsig_conv -import funcsig_conversions.grib_stub_funcsig_conversions.grib_bits_fast_big_endian_stub_funcsig_conv as grib_bits_fast_big_endian_stub_funcsig_conv import funcsig_conversions.grib_stub_funcsig_conversions.grib_buffer_stub_funcsig_conv as grib_buffer_stub_funcsig_conv import funcsig_conversions.grib_stub_funcsig_conversions.grib_date_stub_funcsig_conv as grib_date_stub_funcsig_conv import funcsig_conversions.grib_stub_funcsig_conversions.grib_util_stub_funcsig_conv as grib_util_stub_funcsig_conv @@ -14,7 +13,6 @@ grib_stub_funcsig_conversions = [ grib_accessor_class_stub_funcsig_conv.grib_accessor_class_stub_funcsig_conversions, grib_accessor_stub_funcsig_conv.grib_accessor_stub_funcsig_conversions, grib_bits_any_endian_stub_funcsig_conv.grib_bits_any_endian_stub_funcsig_conversions, - grib_bits_fast_big_endian_stub_funcsig_conv.grib_bits_fast_big_endian_stub_funcsig_conversions, grib_buffer_stub_funcsig_conv.grib_buffer_stub_funcsig_conversions, grib_date_stub_funcsig_conv.grib_date_stub_funcsig_conversions, grib_util_stub_funcsig_conv.grib_util_stub_funcsig_conversions, diff --git a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_any_endian_stub_funcsig_conv.py b/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_any_endian_stub_funcsig_conv.py index 3f1584707..dfff4f80a 100755 --- a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_any_endian_stub_funcsig_conv.py +++ b/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_any_endian_stub_funcsig_conv.py @@ -6,5 +6,11 @@ from funcsig_mapping import FuncSigMapping grib_bits_any_endian_stub_funcsig_conversions = [ FuncSigMapping( FuncSig("unsigned long", "grib_decode_unsigned_long", [Arg("const unsigned char*", "p"), Arg("long*", "p"), Arg("long", "nbits")]), - FuncSig("unsigned long", "gribDecodeUnsignedLong", [Arg("AccessorDataBuffer::const_pointer", "input"), Arg("long&", "bitPos"), Arg("long", "numBits")])), + FuncSig("unsigned long", "gribDecodeUnsignedLong", [Arg("const AccessorDataPointer", "input"), Arg("long&", "bitPos"), Arg("long", "numBits")])), + + FuncSigMapping( FuncSig("int", "grib_encode_unsigned_long", [Arg("unsigned char*", "p"), Arg("unsigned long", "val"), Arg("long*", "bitp"), Arg("long", "nbits")]), + FuncSig("GribStatus", "gribEncodeUnsignedLong", [Arg("AccessorDataPointer", "input"), Arg("unsigned long", "val"), Arg("long&", "bitPos"), Arg("long", "numBits")])), + + FuncSigMapping( FuncSig("int", "grib_encode_unsigned_longb", [Arg("unsigned char*", "p"), Arg("unsigned long", "val"), Arg("long*", "bitp"), Arg("long", "nbits")]), + FuncSig("GribStatus", "gribEncodeUnsignedLongb", [Arg("AccessorDataPointer", "input"), Arg("unsigned long", "val"), Arg("long&", "bitPos"), Arg("long", "numBits")])), ] diff --git a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_fast_big_endian_stub_funcsig_conv.py b/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_fast_big_endian_stub_funcsig_conv.py deleted file mode 100755 index 365711ef1..000000000 --- a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_bits_fast_big_endian_stub_funcsig_conv.py +++ /dev/null @@ -1,10 +0,0 @@ - -from funcsig import FuncSig -from arg_indexes import ArgIndexes -from arg import Arg -from funcsig_mapping import FuncSigMapping - -grib_bits_fast_big_endian_stub_funcsig_conversions = [ - FuncSigMapping( FuncSig("int", "grib_encode_unsigned_longb", [Arg("const unsigned char*", "p"), Arg("unsigned long", "val"), Arg("long*", "bitp"), Arg("long", "nbits")]), - FuncSig("GribStatus", "gribEncodeUnsignedLongb", [Arg("AccessorDataBuffer::const_pointer", "input"), Arg("unsigned long", "val"), Arg("long&", "bitPos"), Arg("long", "numBits")])), -] diff --git a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_buffer_stub_funcsig_conv.py b/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_buffer_stub_funcsig_conv.py index aebfebc31..389905f18 100755 --- a/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_buffer_stub_funcsig_conv.py +++ b/src/conversion/funcsig_conversions/grib_stub_funcsig_conversions/grib_buffer_stub_funcsig_conv.py @@ -6,13 +6,13 @@ from funcsig_mapping import FuncSigMapping grib_buffer_stub_funcsig_conversions = [ FuncSigMapping( FuncSig("void", "grib_buffer_delete", [Arg("const grib_context*", "c"), Arg("grib_buffer*", "b")]), - FuncSig("void", "griBufferDelete", [None, Arg("AccessorDataBuffer", "b")])), + FuncSig("void", "griBufferDelete", [None, Arg("AccessorDataBuffer&", "b")])), FuncSigMapping( FuncSig("void", "grib_buffer_replace", [Arg("grib_accessor*", "a"), Arg("const unsigned char*", "data"), Arg("size_t", "newsize"), Arg("int", "update_lengths"), Arg("int", "update_paddings")]), - FuncSig("void", "gribBufferReplace", [Arg("AccessorPtr", "ptr"), Arg("AccessorDataBuffer", "data"), Arg("size_t", "newsize"), Arg("int", "updateLengths"), Arg("int", "updatePaddings")])), + FuncSig("void", "gribBufferReplace", [None, Arg("AccessorDataBuffer&", "data"), Arg("size_t", "newsize"), Arg("int", "updateLengths"), Arg("int", "updatePaddings")])), FuncSigMapping( FuncSig("void", "grib_buffer_set_ulength_bits", [Arg("const grib_context*", "c"), Arg("grib_buffer*", "b"), Arg("size_t", "length_bits")]), - FuncSig("void", "gribBufferSetUlengthBits", [None, Arg("AccessorDataBuffer", "b"), Arg("size_t", "lengthBits")])), + FuncSig("void", "gribBufferSetUlengthBits", [None, Arg("AccessorDataBuffer&", "b"), Arg("size_t", "lengthBits")])), FuncSigMapping( FuncSig("grib_buffer*", "grib_create_growable_buffer", [Arg("const grib_context*", "c")]), FuncSig("AccessorDataBuffer", "gribCreateGrowableBuffer", [None])), diff --git a/src/conversion/grib_accessor_conv.py b/src/conversion/grib_accessor_conv.py index 410d1af7c..cad4d18f2 100755 --- a/src/conversion/grib_accessor_conv.py +++ b/src/conversion/grib_accessor_conv.py @@ -60,7 +60,7 @@ base_members_map = { arg.Arg("long","offset") : arg.Arg("long","offset_"), arg.Arg("unsigned long","flags") : arg.Arg("unsigned long","flags_"), arg.Arg("int","dirty") : arg.Arg("int","dirty_"), - arg.Arg("grib_virtual_value*","vvalue") : arg.Arg("std::unique_ptr","vvalue_"), + arg.Arg("grib_virtual_value*","vvalue") : arg.Arg("GribVirtualValuePtr","vvalue_"), arg.Arg("const char*","set") : arg.Arg("std::string","set_") } @@ -259,20 +259,12 @@ class GribAccessorConverter: self._transforms.add_to_members(cmember, cppmember) def add_constructor_method(self): - # Create a default constructor if none exists - if self._grib_accessor.constructor: - constructor_method_converter = self._converters[Converter.CONSTRUCTOR_METHOD]() - self._accessor_data._constructor = constructor_method_converter.to_cpp_function(self._grib_accessor.constructor, self._transforms) - else: - self._accessor_data._constructor = self._converters[Converter.CONSTRUCTOR_METHOD]() + constructor_method_converter = self._converters[Converter.CONSTRUCTOR_METHOD]() + self._accessor_data._constructor = constructor_method_converter.to_cpp_function(self._grib_accessor.constructor, self._transforms) def add_destructor_method(self): - # Create a default destructor if none exists - if self._grib_accessor.destructor: - destructor_method_converter = self._converters[Converter.DESTRUCTOR_METHOD]() - self._accessor_data._destructor = destructor_method_converter.to_cpp_function(self._grib_accessor.destructor, self._transforms) - else: - self._accessor_data._destructor = self._converters[Converter.DESTRUCTOR_METHOD]() + destructor_method_converter = self._converters[Converter.DESTRUCTOR_METHOD]() + self._accessor_data._destructor = destructor_method_converter.to_cpp_function(self._grib_accessor.destructor, self._transforms) def add_inherited_methods(self): for cfunc in self._grib_accessor.inherited_methods: diff --git a/src/conversion/method_conv.py b/src/conversion/method_conv.py index 0927947b1..4aeff868e 100755 --- a/src/conversion/method_conv.py +++ b/src/conversion/method_conv.py @@ -12,6 +12,43 @@ class MethodConverter(FunctionConverter): def create_cpp_function(self, cppfuncsig): return method.Method(cppfuncsig, self._transforms.types["self"]) + # overridden to short-circuit well-knwon transforms! + def convert_cfunction_calls(self, line): + + # Transform the argument getters + m = re.search(r"((self->)?(\w+)\s+=\s+)?\bgrib_arguments_get_(\w+)\([^,]+, ([^,]+), ([^\)]+)\)", line) + if m: + ctype = assignment_text = "" + if m.group(1): + assignment_text = m.group(1) + member_name = m.group(3) + for cmember, cppmember in self._transforms.members.items(): + if cmember.name == member_name: + ctype = cppmember.type + break + + get_what = m.group(4) + if get_what == "expression": + get_what = "GribExpressionPtr" + elif get_what in ["string", "name"]: + get_what = "std::string" + if not ctype: + ctype = "AccessorName" + + if m.group(5).startswith("self->"): + grib_arguments_arg_name = m.group(5) + else: + grib_arguments_arg_name = "initData" + + if ctype == "AccessorName": + line = re.sub(m.re, f"{assignment_text}AccessorName(std::get<{get_what}>({grib_arguments_arg_name}.args[{m.group(6)}].second))", line) + else: + line = re.sub(m.re, f"{assignment_text}std::get<{get_what}>({grib_arguments_arg_name}.args[{m.group(6)}].second)", line) + + debug.line("convert_cfunction_calls", f"Updated [bgrib_arguments_get_expression] line=[{line}]") + + return super().convert_cfunction_calls(line) + # WARNING: CAN CAUSE CONFLICTS WITH e.g. "self->owner" member and "owner" local variable # The former is detected via self-> struct access instead # We only validate vars that end in "_" are indeed members, or return None @@ -53,10 +90,17 @@ class MethodConverter(FunctionConverter): if not cppstruct_member: cppstruct_member = struct_arg.StructArg("", cppmember.name, cstruct_member.index) if cstruct_member.member: - # TODO: Additonal members here means that we've not processed something correctly - need to fix! - cppstruct_member_member = self.apply_default_cstruct_arg_transform(cstruct_member.member) - cppstruct_member.member = cppstruct_member_member - debug.line("transform_cstruct_arg_member", f"WARNING: Unexpected member, so not processed correctly: {cstruct_member.member.as_string()}") + if cstruct_member.name == "vvalue": + # This is a direct mapping + cppstruct_member.member = cstruct_member.member + elif cppmember and cppmember.type == "AccessorInitData": + # This is a direct mapping + cppstruct_member.member = cstruct_member.member + else: + # TODO: Additonal members here means that we've not processed something correctly - need to fix! + cppstruct_member_member = self.apply_default_cstruct_arg_transform(cstruct_member.member) + cppstruct_member.member = cppstruct_member_member + debug.line("transform_cstruct_arg_member", f"WARNING: Unexpected member, so not processed correctly: {cstruct_member.member.as_string()}") break # If super-> then replace with the correct AccessorName:: call, else remove top-level (self->, a-> etc) @@ -95,7 +139,7 @@ class MethodConverter(FunctionConverter): return cppstruct_arg - # transform and a->foo where foo is a non-member + # transform any a->foo where foo is a non-member def transform_cstruct_arg_a_nonmember(self, cstruct_arg): cppstruct_arg = None @@ -250,23 +294,26 @@ class MethodConverter(FunctionConverter): # Overridden to handle member types e.g. AccessorName x = NULL def custom_transform_cppvariable_access(self, cppvariable, original_var, match_token, post_match_string): - accessor_arg = None + access_arg = None - for cpparg in self._transforms.all_args.values(): - if cpparg and cpparg.name == cppvariable.name and cpparg.type == "AccessorPtr": - accessor_arg = cpparg + for cpparg_list in [self._transforms.all_args.values(), + self._transforms.members.values()]: + for cpparg in cpparg_list: + if cpparg and cpparg.name == cppvariable.name: + access_arg = cpparg break - if not accessor_arg: - return None + if not access_arg: + return super().custom_transform_cppvariable_access(cppvariable, original_var, match_token, post_match_string) if match_token.is_assignment: - m = re.match(r"\s*(NULL)", post_match_string) - if m: - post_match_string = re.sub(m.re, "nullptr", post_match_string) - return cppvariable.as_string() + match_token.as_string() + post_match_string + if access_arg.type == "AccessorPtr": + m = re.match(r"\s*(NULL)", post_match_string) + if m: + post_match_string = re.sub(m.re, "nullptr", post_match_string) + return cppvariable.as_string() + match_token.as_string() + post_match_string - return None + return super().custom_transform_cppvariable_access(cppvariable, original_var, match_token, post_match_string) # Find any overloaded virtual function calls that are not implemented in this class, and add to the # "using" list so we can add a "using base::func" directive in the header @@ -366,30 +413,11 @@ class MethodConverter(FunctionConverter): return super().transform_container_cppvariable_access(cppvariable, original_var, match_token, post_match_string) # Overridden for member checks - def process_if_test(self, line): - m = re.search(r"\b(if\s*\(!?)(\w+)\)", line) - if m: - arg_name = m.group(2) - container_arg = None - for cppmember in self._transforms.members.values(): - if cppmember.name == arg_name and arg.is_container(cppmember): - container_arg = cppmember - break + def process_boolean_test(self, line): + m = re.search(r"\b(\w+)(\s*\(!?)(\w+)\)", line) - if container_arg: - container_func_call = self.container_func_call_for(container_arg, "size") - transformed_call = f"{container_arg.name}.{container_func_call}" - line = re.sub(re.escape(m.group(2)), f"{transformed_call}", line) - debug.line("process_if_test", f"Replaced [{m.group(0)}] with [{transformed_call}] line:[{line}]") - return line - - return super().process_if_test(line) - - # Overridden for member checks - def process_assert_test(self, line): - m = re.search(r"\b(Assert\s*\(!?)(\w+)\)", line) - if m: - arg_name = m.group(2) + if m and m.group(1) in ["if", "Assert"]: + arg_name = m.group(3) test_arg = None for cppmember in self._transforms.members.values(): if cppmember.name == arg_name: @@ -403,13 +431,15 @@ class MethodConverter(FunctionConverter): transformed_call = f"{test_arg.name}.{container_func_call}" elif test_arg.type == "AccessorName": transformed_call = f"{test_arg.name}.get()" + elif test_arg.type == "AccessorInitData": + transformed_call = f"{test_arg.name}.args.size()" if transformed_call: - line = re.sub(re.escape(m.group(2)), f"{transformed_call}", line) + line = re.sub(re.escape(m.group(3)), f"{transformed_call}", line) debug.line("process_assert_test", f"Replaced [{m.group(0)}] with [{transformed_call}] line:[{line}]") return line - return super().process_assert_test(line) + return super().process_boolean_test(line) # Return a list of all pre-defined conversions def method_conversions_list(self): diff --git a/src/cpp/CMakeLists.txt b/src/cpp/CMakeLists.txt index 94f412758..63e460290 100644 --- a/src/cpp/CMakeLists.txt +++ b/src/cpp/CMakeLists.txt @@ -76,8 +76,6 @@ set(accessor_grib_stub_src_files ${accessor_grib_stub_dir}/GribActionStub.h ${accessor_grib_stub_dir}/GribBitsAnyEndianStub.cc ${accessor_grib_stub_dir}/GribBitsAnyEndianStub.h - ${accessor_grib_stub_dir}/GribBitsFastBigEndianStub.cc - ${accessor_grib_stub_dir}/GribBitsFastBigEndianStub.h ${accessor_grib_stub_dir}/GribBufferStub.cc ${accessor_grib_stub_dir}/GribBufferStub.h ${accessor_grib_stub_dir}/GribContextStub.cc @@ -90,6 +88,7 @@ set(accessor_grib_stub_src_files ${accessor_grib_stub_dir}/GribUtilStub.h ${accessor_grib_stub_dir}/GribParseUtilsStub.cc ${accessor_grib_stub_dir}/GribParseUtilsStub.h + ${accessor_grib_stub_dir}/GribVirtualValueStub.h ) # Variables to be used in the parent CMakeLists.txt diff --git a/src/cpp/eccodes/accessor/Accessor.cc b/src/cpp/eccodes/accessor/Accessor.cc index 3b0cf30fb..ecb0ea8fd 100644 --- a/src/cpp/eccodes/accessor/Accessor.cc +++ b/src/cpp/eccodes/accessor/Accessor.cc @@ -52,12 +52,12 @@ int Accessor::isMissing() const return data_->isMissing(); } -bool Accessor::newBuffer(AccessorDataBuffer const& accBuffer) +bool Accessor::newBuffer(AccessorDataView const& accBuffer) { return data_->newBuffer(accBuffer); } -AccessorDataBuffer Accessor::currentBuffer() const +AccessorDataView Accessor::currentBuffer() const { return data_->currentBuffer(); } diff --git a/src/cpp/eccodes/accessor/Accessor.h b/src/cpp/eccodes/accessor/Accessor.h index 4d953920d..2354dd9d4 100644 --- a/src/cpp/eccodes/accessor/Accessor.h +++ b/src/cpp/eccodes/accessor/Accessor.h @@ -27,8 +27,8 @@ public: int compare(AccessorPtr const rhs) const; int isMissing() const; - bool newBuffer(AccessorDataBuffer const& accBuffer); - AccessorDataBuffer currentBuffer() const; + bool newBuffer(AccessorDataView const& accBuffer); + AccessorDataView currentBuffer() const; // Required to support C -> C++ Conversion - Start long byteCount() const; diff --git a/src/cpp/eccodes/accessor/AccessorBuffer.h b/src/cpp/eccodes/accessor/AccessorBuffer.h index 72710f9ef..b692efdf0 100644 --- a/src/cpp/eccodes/accessor/AccessorBuffer.h +++ b/src/cpp/eccodes/accessor/AccessorBuffer.h @@ -5,7 +5,7 @@ #include #include -// Provides a non-owning view to a contiguous block of memory, accessed as std::byte +// Provides a non-owning view to a contiguous block of memory, accessed as unsigned char // // Required because we have to use C++17, so don't have access to std::span // @@ -15,23 +15,19 @@ namespace eccodes::accessor { -template -class AccessorBuffer { +class AccessorDataView { public: - using value_type = T; + using value_type = unsigned char; using pointer = value_type*; using const_pointer = value_type const*; - using reference = value_type&; - using const_reference = value_type const&; using size_type = size_t; - using difference_type = ptrdiff_t; - constexpr AccessorBuffer() noexcept : data_{ nullptr }, size_{ 0 } {}; + constexpr AccessorDataView() noexcept : data_{ nullptr }, size_{ 0 } {}; - constexpr AccessorBuffer(AccessorBuffer const&) noexcept = default; - constexpr AccessorBuffer& operator=(AccessorBuffer const&) noexcept = default; + constexpr AccessorDataView(AccessorDataView const&) noexcept = default; + constexpr AccessorDataView& operator=(AccessorDataView const&) noexcept = default; - constexpr AccessorBuffer(value_type *const buffer, const size_type num_elements) noexcept + constexpr AccessorDataView(value_type *const buffer, const size_type num_elements) noexcept : data_(reinterpret_cast(buffer)), size_(sizeof(value_type) * num_elements) {} [[nodiscard]] constexpr size_type size_bytes() const noexcept { @@ -51,7 +47,8 @@ private: size_type size_; }; -using AccessorDataBuffer = AccessorBuffer; -using DataPointer = unsigned char*; +using AccessorDataPointer = unsigned char*; + +using AccessorDataBuffer = std::vector; } diff --git a/src/cpp/eccodes/accessor/AccessorData/AccessorData.cc b/src/cpp/eccodes/accessor/AccessorData/AccessorData.cc index 656941584..7e313d18a 100644 --- a/src/cpp/eccodes/accessor/AccessorData/AccessorData.cc +++ b/src/cpp/eccodes/accessor/AccessorData/AccessorData.cc @@ -15,13 +15,13 @@ AccessorData::AccessorData(AccessorInitData const& initData) AccessorData::~AccessorData() = default; -bool AccessorData::newBuffer(AccessorDataBuffer const& accBuffer) +bool AccessorData::newBuffer(AccessorDataView const& accBuffer) { buffer_ = accBuffer; return true; } -AccessorDataBuffer AccessorData::currentBuffer() const +AccessorDataView AccessorData::currentBuffer() const { return buffer_; } diff --git a/src/cpp/eccodes/accessor/AccessorData/AccessorData.h b/src/cpp/eccodes/accessor/AccessorData/AccessorData.h index e8e6e653e..a9793f620 100644 --- a/src/cpp/eccodes/accessor/AccessorData/AccessorData.h +++ b/src/cpp/eccodes/accessor/AccessorData/AccessorData.h @@ -6,6 +6,7 @@ #include "AccessorTraits.h" #include "GribCpp/GribType.h" #include "GribCpp/GribStatus.h" +#include "GribStub/GribVirtualValueStub.h" #include #include @@ -22,8 +23,8 @@ public: AccessorData(AccessorInitData const& initData); virtual ~AccessorData() = 0; - bool newBuffer(AccessorDataBuffer const& accBuffer); - AccessorDataBuffer currentBuffer() const; + bool newBuffer(AccessorDataView const& accBuffer); + AccessorDataView currentBuffer() const; virtual void dump() const; virtual std::size_t stringLength() const; @@ -80,12 +81,12 @@ public: // Ideally these would be private, but that makes the conversion much harder so they are protected instead // This will be revisited later... protected: - AccessorDataBuffer buffer_{}; + AccessorDataView buffer_{}; long length_{}; long offset_{}; unsigned long flags_{}; int dirty_{}; - std::unique_ptr vvalue_{}; + GribVirtualValuePtr vvalue_{}; std::string set_{}; }; diff --git a/src/cpp/eccodes/accessor/GribCpp/GribBits.cc b/src/cpp/eccodes/accessor/GribCpp/GribBits.cc index 1e46d8dde..e6472eace 100644 --- a/src/cpp/eccodes/accessor/GribCpp/GribBits.cc +++ b/src/cpp/eccodes/accessor/GribCpp/GribBits.cc @@ -5,14 +5,14 @@ namespace eccodes::accessor { -void gribSetBitOn(DataPointer p, long& bitp) +void gribSetBitOn(AccessorDataPointer p, long& bitp) { p += bitp / 8; *p |= (1u << (7 - (bitp % 8))); bitp++; } -void gribSetBitsOn(DataPointer p, long& bitp, long nbits) +void gribSetBitsOn(AccessorDataPointer p, long& bitp, long nbits) { int i; for (i = 0; i < nbits; i++) { @@ -20,14 +20,14 @@ void gribSetBitsOn(DataPointer p, long& bitp, long nbits) } } -void gribSetBitOff(DataPointer p, long& bitp) +void gribSetBitOff(AccessorDataPointer p, long& bitp) { p += bitp / 8; *p &= ~(1u << (7 - (bitp % 8))); bitp++; } -void gribSetBit(DataPointer p, long bitp, int val) +void gribSetBit(AccessorDataPointer p, long bitp, int val) { if (val == 0) gribSetBitOff(p, bitp); diff --git a/src/cpp/eccodes/accessor/GribCpp/GribBits.h b/src/cpp/eccodes/accessor/GribCpp/GribBits.h index 80420c60c..359152263 100644 --- a/src/cpp/eccodes/accessor/GribCpp/GribBits.h +++ b/src/cpp/eccodes/accessor/GribCpp/GribBits.h @@ -7,10 +7,10 @@ namespace eccodes::accessor { -void gribSetBitOn(DataPointer p, long& bitp); -void gribSetBitsOn(DataPointer p, long& bitp, long nbits); -void gribSetBitOff(DataPointer p, long& bitp); -void gribSetBit(DataPointer p, long bitp, int val); +void gribSetBitOn(AccessorDataPointer p, long& bitp); +void gribSetBitsOn(AccessorDataPointer p, long& bitp, long nbits); +void gribSetBitOff(AccessorDataPointer p, long& bitp); +void gribSetBit(AccessorDataPointer p, long bitp, int val); } diff --git a/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.cc b/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.cc index cf930a111..6ad69bc88 100644 --- a/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.cc +++ b/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.cc @@ -5,17 +5,34 @@ namespace eccodes::accessor { -// A mask with x least-significant bits set, possibly 0 or >=32 */ -// -1UL is 1111111... in every bit in binary representation -#define BIT_MASK(x) \ - (((x) == max_nbits) ? (unsigned long)-1UL : (1UL << (x)) - 1) - -// decode a value consisting of nbits from an octet-bitstream to long-representation -unsigned long gribDecodeUnsignedLong(DataPointer input, long& bitPos, long numBits) +unsigned long gribDecodeUnsignedLong(const AccessorDataPointer input, long& bitPos, long numBits) { assert(false); // TODO return 0; } +unsigned long gribDecodeUnsignedLong(const AccessorDataBuffer& input, long& bitPos, long numBits) +{ + assert(false); // TODO + return 0; +} + +GribStatus gribEncodeUnsignedLong(AccessorDataPointer p, unsigned long val, long& bitPos, long numBits) +{ + assert(false); // TODO + return GribStatus::NOT_IMPLEMENTED; +} + +GribStatus gribEncodeUnsignedLong(AccessorDataBuffer& p, unsigned long val, long& bitPos, long numBits) +{ + assert(false); // TODO + return GribStatus::NOT_IMPLEMENTED; +} + +GribStatus gribEncodeUnsignedLongb(AccessorDataPointer p, unsigned long val, long& bitPos, long nnumBitsb) +{ + assert(false); // TODO + return GribStatus::NOT_IMPLEMENTED; +} } diff --git a/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.h b/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.h index 33a154dec..e2645072c 100644 --- a/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.h +++ b/src/cpp/eccodes/accessor/GribStub/GribBitsAnyEndianStub.h @@ -3,9 +3,19 @@ // C++ implementation of the existing grib_bits_any_endian.cc #include "AccessorBuffer.h" +#include "GribCpp/GribStatus.h" namespace eccodes::accessor { -unsigned long gribDecodeUnsignedLong(DataPointer input, long& bitPos, long numBits); +// AccessorDataBuffer& overload added to support conversion from C to C++ +unsigned long gribDecodeUnsignedLong(const AccessorDataPointer input, long& bitPos, long numBits); +unsigned long gribDecodeUnsignedLong(const AccessorDataBuffer& input, long& bitPos, long numBits); + +// AccessorDataBuffer& overload added to support conversion from C to C++ +GribStatus gribEncodeUnsignedLong(AccessorDataPointer p, unsigned long val, long& bitp, long nbits); +GribStatus gribEncodeUnsignedLong(AccessorDataBuffer& p, unsigned long val, long& bitPos, long numBits); + +//int grib_encode_unsigned_longb(unsigned char* p, unsigned long val, long* bitp, long nb); +GribStatus gribEncodeUnsignedLongb(AccessorDataPointer p, unsigned long val, long& bitPos, long numBits); } diff --git a/src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.cc b/src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.cc deleted file mode 100644 index fa1155378..000000000 --- a/src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.cc +++ /dev/null @@ -1,14 +0,0 @@ -#include "GribBitsFastBigEndianStub.h" - -#include - -namespace eccodes::accessor { - -GribStatus gribEncodeUnsignedLongb(DataPointer p, unsigned long val, long& bitp, long nbits) -{ - assert(false); // TODO - return GribStatus::NOT_IMPLEMENTED; -} - - -} diff --git a/src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.h b/src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.h deleted file mode 100644 index bc96e1375..000000000 --- a/src/cpp/eccodes/accessor/GribStub/GribBitsFastBigEndianStub.h +++ /dev/null @@ -1,12 +0,0 @@ -#pragma once - -// C++ implementation of the existing grib_bits_fast_big_endian.cc - -#include "AccessorBuffer.h" -#include "GribCpp/GribStatus.h" - -namespace eccodes::accessor { - -GribStatus gribEncodeUnsignedLongb(DataPointer p, unsigned long val, long& bitp, long nbits); - -} diff --git a/src/cpp/eccodes/accessor/GribStub/GribBufferStub.cc b/src/cpp/eccodes/accessor/GribStub/GribBufferStub.cc index c0c1a49ac..cc7ddfb72 100644 --- a/src/cpp/eccodes/accessor/GribStub/GribBufferStub.cc +++ b/src/cpp/eccodes/accessor/GribStub/GribBufferStub.cc @@ -5,18 +5,17 @@ namespace eccodes::accessor { -void griBufferDelete(AccessorDataBuffer b) +void griBufferDelete(AccessorDataBuffer& b) { assert(false); } -void gribBufferReplace(AccessorPtr ptr, AccessorDataBuffer data, - size_t newsize, int update_lengths, int update_paddings) +void gribBufferReplace(AccessorDataBuffer& data, size_t newsize, int update_lengths, int update_paddings) { assert(false); } -void gribBufferSetUlengthBits(AccessorDataBuffer b, size_t length_bits) +void gribBufferSetUlengthBits(AccessorDataBuffer& b, size_t length_bits) { assert(false); } diff --git a/src/cpp/eccodes/accessor/GribStub/GribBufferStub.h b/src/cpp/eccodes/accessor/GribStub/GribBufferStub.h index 520d586c7..bdacd0371 100644 --- a/src/cpp/eccodes/accessor/GribStub/GribBufferStub.h +++ b/src/cpp/eccodes/accessor/GribStub/GribBufferStub.h @@ -7,10 +7,9 @@ namespace eccodes::accessor { -void griBufferDelete(AccessorDataBuffer b); -void gribBufferReplace(AccessorPtr ptr, AccessorDataBuffer data, - size_t newsize, int updateLengths, int updatePaddings); -void gribBufferSetUlengthBits(AccessorDataBuffer b, size_t lengthBits); +void griBufferDelete(AccessorDataBuffer& b); +void gribBufferReplace(AccessorDataBuffer& data, size_t newsize, int updateLengths, int updatePaddings); +void gribBufferSetUlengthBits(AccessorDataBuffer& b, size_t lengthBits); AccessorDataBuffer gribCreateGrowableBuffer(); } diff --git a/src/cpp/eccodes/accessor/GribStub/GribStubIncludes.h b/src/cpp/eccodes/accessor/GribStub/GribStubIncludes.h index 13f65eddf..3d859afde 100644 --- a/src/cpp/eccodes/accessor/GribStub/GribStubIncludes.h +++ b/src/cpp/eccodes/accessor/GribStub/GribStubIncludes.h @@ -6,10 +6,10 @@ #include "GribActionStub.h" #include "GribAccessorStub.h" #include "GribBitsAnyEndianStub.h" -#include "GribBitsFastBigEndianStub.h" #include "GribBufferStub.h" #include "GribContextStub.h" #include "GribDateStub.h" #include "GribExpressionStub.h" #include "GribUtilStub.h" #include "GribParseUtilsStub.h" +#include "GribVirtualValueStub.h" diff --git a/src/cpp/eccodes/accessor/GribStub/GribVirtualValueStub.h b/src/cpp/eccodes/accessor/GribStub/GribVirtualValueStub.h new file mode 100644 index 000000000..189711711 --- /dev/null +++ b/src/cpp/eccodes/accessor/GribStub/GribVirtualValueStub.h @@ -0,0 +1,21 @@ +#pragma once + +#include "GribCpp/GribType.h" +#include +#include + +namespace eccodes::accessor { + +struct GribVirtualValue +{ + long lval; + double dval; + std::string cval; + int missing; + int length; + GribType type; +}; + +using GribVirtualValuePtr = std::shared_ptr; + +} diff --git a/src/cpp/eccodes/accessor/Test/GribFileTests.cc b/src/cpp/eccodes/accessor/Test/GribFileTests.cc index 78b36b1bc..1e404bdf1 100644 --- a/src/cpp/eccodes/accessor/Test/GribFileTests.cc +++ b/src/cpp/eccodes/accessor/Test/GribFileTests.cc @@ -45,7 +45,7 @@ void createAccessors(LayoutEntries const& entries, GribBuffer& buffer) { auto accessor = AccessorFactory::instance().build(AccessorType(entry.type_), AccessorName(entry.name_), AccessorNameSpace(""), AccessorInitData{}); - AccessorDataBuffer accBuffer{buffer.data() + offset, static_cast(entry.byteCount_)}; + AccessorDataView accBuffer{buffer.data() + offset, static_cast(entry.byteCount_)}; offset += entry.byteCount_; accessor->newBuffer(accBuffer); diff --git a/src/grib_accessor_class_unsigned.cc b/src/grib_accessor_class_unsigned.cc index f1202b0d0..b3a7cf2ae 100644 --- a/src/grib_accessor_class_unsigned.cc +++ b/src/grib_accessor_class_unsigned.cc @@ -118,7 +118,7 @@ grib_accessor_class* grib_accessor_class_unsigned = &_grib_accessor_class_unsign static void init(grib_accessor* a, const long len, grib_arguments* arg) { grib_accessor_unsigned* self = (grib_accessor_unsigned*)a; - self->arg = NULL; + //self->arg = NULL; self->arg = arg; self->nbytes = len;