From 4e8280a02a37fd6bdac85b2c907a33309f290764 Mon Sep 17 00:00:00 2001 From: Rahul R Date: Tue, 15 Jul 2025 12:24:48 +0530 Subject: [PATCH 1/6] Including Common changes for 3d numpy --- build/helper/codegen_helper.py | 5 ++- build/helper/helper.py | 2 +- build/helper/metadata_add_all.py | 7 +++ build/templates/_library_interpreter.py.mako | 8 +++- .../session.py/numpy_3d_array_method.py.mako | 44 +++++++++++++++++++ build/unit_tests/test_codegen_helper.py | 36 +++++++++++++++ build/unit_tests/test_metadata_add_all.py | 14 ++++++ .../nifake/nifake/_grpc_stub_interpreter.py | 3 ++ generated/nifake/nifake/_library.py | 9 ++++ .../nifake/nifake/_library_interpreter.py | 15 ++++++- generated/nifake/nifake/session.py | 19 ++++++++ .../nifake/nifake/unit_tests/_mock_helper.py | 9 ++++ .../unit_tests/test_library_interpreter.py | 44 +++++++++++++++++++ .../nirfsg/nirfsg/_library_interpreter.py | 8 +++- src/nifake/metadata/functions.py | 43 ++++++++++++++++++ .../unit_tests/test_library_interpreter.py | 44 +++++++++++++++++++ 16 files changed, 302 insertions(+), 8 deletions(-) create mode 100644 build/templates/session.py/numpy_3d_array_method.py.mako diff --git a/build/helper/codegen_helper.py b/build/helper/codegen_helper.py index 86b83c476..4bde6d061 100644 --- a/build/helper/codegen_helper.py +++ b/build/helper/codegen_helper.py @@ -132,7 +132,10 @@ def _get_library_interpreter_output_param_return_snippet(output_parameter, param val_suffix = '' if is_custom_type else '.value' if output_parameter['use_array']: - snippet = '{}_array'.format(output_parameter['python_name']) + if output_parameter['numpy'] and output_parameter['complex_type'] is not None: + snippet = 'list({}_array)'.format(output_parameter['python_name']) + else: + snippet = '{}_array'.format(output_parameter['python_name']) elif output_parameter['is_buffer']: if output_parameter['size']['mechanism'] == 'fixed': size = str(output_parameter['size']['value']) diff --git a/build/helper/helper.py b/build/helper/helper.py index b2f7c86e4..f0c48db83 100644 --- a/build/helper/helper.py +++ b/build/helper/helper.py @@ -26,7 +26,7 @@ 'ViChar[]': { 'array_type': None, 'python_type': 'str', 'numpy_type': None, }, # noqa: E201, E202, E241 'ViBoolean': { 'array_type': None, 'python_type': 'bool', 'numpy_type': None, }, # noqa: E201, E202, E241 'ViRsrc': { 'array_type': None, 'python_type': 'str', 'numpy_type': 'bool_', }, # noqa: E201, E202, E241 - 'NIComplexNumber': { 'array_type': None, 'python_type': None, 'numpy_type': 'complex128', }, # noqa: E201, E202, E241 + 'NIComplexNumber': { 'array_type': 'P', 'python_type': None, 'numpy_type': 'complex128', }, # noqa: E201, E202, E241 'NIComplexNumberF32': { 'array_type': None, 'python_type': None, 'numpy_type': 'complex64', }, # noqa: E201, E202, E241 'NIComplexI16': { 'array_type': None, 'python_type': None, 'numpy_type': 'int16', }, # noqa: E201, E202, E241 } diff --git a/build/helper/metadata_add_all.py b/build/helper/metadata_add_all.py index a9e2f0a0d..6d041472d 100644 --- a/build/helper/metadata_add_all.py +++ b/build/helper/metadata_add_all.py @@ -132,6 +132,12 @@ def _add_complex_type(parameter): parameter['complex_type'] = None +def _add_multidimension(parameter): + '''Adds a multidimension parameter to the metadata for 3d arrays''' + if 'multidimension' not in parameter: + parameter['multidimension'] = 0 + + def _add_numpy_info(parameter, parameters, config): '''Adds the following numpy-related information: @@ -457,6 +463,7 @@ def add_all_function_metadata(functions, config): _add_ctypes_variable_name(p) _add_ctypes_type(p, config) _add_complex_type(p) + _add_multidimension(p) _add_numpy_info(p, functions[f]['parameters'], config) _add_default_value_name(p) _add_default_value_name_for_docs(p, config['module_name']) diff --git a/build/templates/_library_interpreter.py.mako b/build/templates/_library_interpreter.py.mako index 24e5e12a4..474a204f6 100644 --- a/build/templates/_library_interpreter.py.mako +++ b/build/templates/_library_interpreter.py.mako @@ -53,8 +53,12 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): % if are_complex_parameters_used: if library_type in (_complextype.NIComplexI16, _complextype.NIComplexNumberF32, _complextype.NIComplexNumber): complex_dtype = numpy.dtype(library_type) - structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + if value.ndim > 1: + flattened_array = value.ravel().view(complex_dtype) + return flattened_array.ctypes.data_as(ctypes.POINTER(library_type)) + else: + structured_array = value.view(complex_dtype) + return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) % else: diff --git a/build/templates/session.py/numpy_3d_array_method.py.mako b/build/templates/session.py/numpy_3d_array_method.py.mako new file mode 100644 index 000000000..121316e3f --- /dev/null +++ b/build/templates/session.py/numpy_3d_array_method.py.mako @@ -0,0 +1,44 @@ +<%page args="f, config, method_template"/>\ +<% + '''Renders a Session method for writing numpy.array corresponding to the passed-in function metadata.''' + + import build.helper as helper + + parameters = f['parameters'] + enum_input_parameters = helper.filter_parameters(parameters, helper.ParameterUsageOptions.INPUT_ENUM_PARAMETERS) + output_parameters = helper.filter_parameters(parameters, helper.ParameterUsageOptions.API_NUMPY_OUTPUT_PARAMETERS) + output_parameters_snippet = ', '.join(p['python_name'] for p in output_parameters) + suffix = method_template['method_python_name_suffix'] +%>\ + def ${f['python_name']}${suffix}(${helper.get_params_snippet(f, helper.ParameterUsageOptions.SESSION_METHOD_DECLARATION)}): + r'''${f['python_name']}${suffix} + + ${helper.get_function_docstring(f, True, config, indent=8)} + ''' + import numpy + +% for parameter in enum_input_parameters: + ${helper.get_enum_type_check_snippet(parameter, indent=12)} +% endfor +% for size_check_snippet in helper.get_parameter_size_check_snippets(parameters): + ${size_check_snippet} +% endfor +% for parameter in helper.filter_parameters(parameters, helper.ParameterUsageOptions.NUMPY_PARAMETERS): + if type(${parameter['python_name']}) is not numpy.ndarray: + raise TypeError('${parameter['python_name']} must be {0}, is {1}'.format(numpy.ndarray, type(${parameter['python_name']}))) + if numpy.isfortran(${parameter['python_name']}) is True: + raise TypeError('${parameter['python_name']} must be in C-order') + if ${parameter['python_name']}.ndim != ${parameter['multidimension']}: + raise TypeError('${parameter['python_name']} must be numpy.ndarray of dimension=${parameter['multidimension']}, is ' + str(${parameter['python_name']}.ndim)) +% endfor +% for p in helper.filter_parameters(parameters, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL): +% if 'python_api_converter_name' in p: + ${p['python_name']} = _converters.${p['python_api_converter_name']}(${p['python_name']}) +% endif +% endfor +% if output_parameters: + ${output_parameters_snippet} = self._interpreter.${f['interpreter_name']}${suffix}(${helper.get_params_snippet(f, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL)}) + ${helper.get_session_method_return_snippet(parameters, config, use_numpy_array=True)} +% else: + self._interpreter.${f['interpreter_name']}${suffix}(${helper.get_params_snippet(f, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL)}) +% endif diff --git a/build/unit_tests/test_codegen_helper.py b/build/unit_tests/test_codegen_helper.py index 4b5f50466..c2e5c7268 100644 --- a/build/unit_tests/test_codegen_helper.py +++ b/build/unit_tests/test_codegen_helper.py @@ -42,6 +42,7 @@ 'type': 'ViSession', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 1 @@ -71,6 +72,7 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 2 @@ -99,6 +101,7 @@ 'type': 'ViString', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 3 @@ -128,6 +131,7 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 4 @@ -154,6 +158,7 @@ 'type': 'ViInt32', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 5 @@ -182,6 +187,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 6 @@ -211,6 +217,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 7 @@ -239,6 +246,7 @@ 'type': 'ViInt64', 'numpy': True, 'complex_type': None, + 'multidimension': 0, 'numpy_type': 'int64', 'numpy_type_library_call': 'numpy.int64', 'use_in_python_api': True, @@ -261,6 +269,7 @@ 'name': 'numberOfElementsPythonCode', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'number_of_elements_python_code', 'python_name_with_default': 'number_of_elements_python_code', 'python_name_with_doc_default': 'number_of_elements_python_code', @@ -287,6 +296,7 @@ 'name': 'input', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'input', 'python_name_with_default': 'input', 'python_name_with_doc_default': 'input', @@ -316,6 +326,7 @@ 'name': 'inputArray', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'input_array', 'python_name_with_default': 'input_array=None', 'python_name_with_doc_default': 'input_array=None', @@ -342,6 +353,7 @@ 'name': 'inputArraySize', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'input_array_size', 'python_name_with_default': 'input_array_size', 'python_name_with_doc_default': 'input_array_size', @@ -368,6 +380,7 @@ 'name': 'stringSize', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'string_size', 'python_name_with_default': 'string_size', 'python_name_with_doc_default': 'string_size', @@ -394,6 +407,7 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -421,6 +435,7 @@ 'name': 'Timeout', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'timeout', 'python_name_with_default': 'timeout=1.0', 'python_name_with_doc_default': 'timeout=1.0', @@ -450,6 +465,7 @@ 'name': 'channelList', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'original_type': 'ViChar[]', 'python_name': 'channel_list', 'python_name_with_default': 'channel_list', @@ -477,6 +493,7 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -510,6 +527,7 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 18 @@ -540,6 +558,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 19 @@ -560,6 +579,7 @@ 'name': 'aString2', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_string_2', 'python_name_with_default': 'a_string_2', 'python_name_with_doc_default': 'a_string_2', @@ -586,6 +606,7 @@ 'name': 'aStrin3g', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_string_3', 'python_name_with_default': 'a_string_3', 'python_name_with_doc_default': 'a_string_3', @@ -612,6 +633,7 @@ 'name': 'aStringTwist', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_string_twist', 'python_name_with_default': 'a_string_twist', 'python_name_with_doc_default': 'a_string_twist', @@ -647,6 +669,7 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, { # 23 @@ -667,6 +690,7 @@ 'name': 'stringSizeTwist', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'string_size_twist', 'python_name_with_default': 'string_size_twist', 'python_name_with_doc_default': 'string_size_twist', @@ -693,6 +717,7 @@ 'name': 'aBufferArray', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_buffer_array', 'python_name_with_default': 'a_buffer_array', 'python_name_with_doc_default': 'a_buffer_array', @@ -721,6 +746,7 @@ 'name': 'aBufferList', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_buffer_list', 'python_name_with_default': 'a_buffer_list', 'python_name_with_doc_default': 'a_buffer_list', @@ -749,6 +775,7 @@ 'name': 'aBufferTwistArray', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_buffer_twist_array', 'python_name_with_default': 'a_buffer_twist_array', 'python_name_with_doc_default': 'a_buffer_twist_array', @@ -777,6 +804,7 @@ 'name': 'aBufferTwistList', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_buffer_twist_list', 'python_name_with_default': 'a_buffer_twist_list', 'python_name_with_doc_default': 'a_buffer_twist_list', @@ -808,6 +836,7 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', 'python_name_with_doc_default': 'input_array_2=None', @@ -837,6 +866,7 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', @@ -867,6 +897,7 @@ 'name': 'inputArray3', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_3', 'python_name_with_default': 'input_array_3=None', @@ -897,6 +928,7 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -927,6 +959,7 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -954,6 +987,7 @@ 'name': 'aStringEnum', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'python_name': 'a_string_enum', 'python_name_with_default': 'a_string_enum', 'python_name_with_doc_default': 'a_string_enum', @@ -982,6 +1016,7 @@ 'name': 'indices', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'original_type': 'ViChar[]', 'python_api_converter_name': 'convert_repeated_capabilities_without_prefix', 'python_name': 'indices', @@ -1019,6 +1054,7 @@ 'type': 'ViInt8', 'numpy': False, 'complex_type': None, + 'multidimension': 0, 'use_in_python_api': True, }, ] diff --git a/build/unit_tests/test_metadata_add_all.py b/build/unit_tests/test_metadata_add_all.py index f32828c64..e23eb3886 100644 --- a/build/unit_tests/test_metadata_add_all.py +++ b/build/unit_tests/test_metadata_add_all.py @@ -260,6 +260,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'vi', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'name_ctype', @@ -294,6 +295,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'name', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'pin_data_buffer_size_ctype', @@ -331,6 +333,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'pin_data_buffer_size', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'python_code_input_ctype', @@ -368,6 +371,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'python_code_input', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'None if actual_num_pin_data_ctype is None else (ctypes.pointer(actual_num_pin_data_ctype))', @@ -405,6 +409,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'actual_num_pin_data', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'expected_pin_states_ctype', @@ -444,6 +449,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'expected_pin_states', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'custom_type_input_ctype', @@ -481,6 +487,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_input', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'None if custom_type_output_ctype is None else (ctypes.pointer(custom_type_output_ctype))', @@ -518,6 +525,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_output', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'custom_type_without_struct_prefix_input_ctype', @@ -555,6 +563,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_without_struct_prefix_input', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'None if custom_type_without_struct_prefix_output_ctype is None else (ctypes.pointer(custom_type_without_struct_prefix_output_ctype))', @@ -592,6 +601,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_without_struct_prefix_output', 'complex_type': None, + 'multidimension': 0, }, ], 'python_name': 'make_a_foo', @@ -640,6 +650,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'vi', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'status_ctype', @@ -677,6 +688,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'status', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'data_buffer_size_ctype', @@ -714,6 +726,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'data_buffer_size', 'complex_type': None, + 'multidimension': 0, }, { 'ctypes_method_call_snippet': 'data_ctype', @@ -752,6 +765,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'data', 'complex_type': None, + 'multidimension': 0, }, ], 'documentation': { diff --git a/generated/nifake/nifake/_grpc_stub_interpreter.py b/generated/nifake/nifake/_grpc_stub_interpreter.py index 829c8657e..8432e127a 100644 --- a/generated/nifake/nifake/_grpc_stub_interpreter.py +++ b/generated/nifake/nifake/_grpc_stub_interpreter.py @@ -150,6 +150,9 @@ def function_with_intflag_parameter(self, flag): # noqa: N802 grpc_types.FunctionWithIntflagParameterRequest(vi=self._vi, flag=flag.value), ) + def function_with_numpy3d_array_input_parameter(self, frequency): # noqa: N802 + raise NotImplementedError('numpy-specific methods are not supported over gRPC') + def function_with_repeated_capability_type(self, site_list): # noqa: N802 raise NotImplementedError('function_with_repeated_capability_type is not supported over gRPC') diff --git a/generated/nifake/nifake/_library.py b/generated/nifake/nifake/_library.py index 0033ec0a5..a24075fd3 100644 --- a/generated/nifake/nifake/_library.py +++ b/generated/nifake/nifake/_library.py @@ -37,6 +37,7 @@ def __init__(self, ctypes_library): self.niFake_ExportAttributeConfigurationBuffer_cfunc = None self.niFake_FetchWaveform_cfunc = None self.niFake_FunctionWithIntflagParameter_cfunc = None + self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc = None self.niFake_FunctionWithRepeatedCapabilityType_cfunc = None self.niFake_GetABoolean_cfunc = None self.niFake_GetANumber_cfunc = None @@ -196,6 +197,14 @@ def niFake_FunctionWithIntflagParameter(self, vi, flag): # noqa: N802 self.niFake_FunctionWithIntflagParameter_cfunc.restype = ViStatus # noqa: F405 return self.niFake_FunctionWithIntflagParameter_cfunc(vi, flag) + def niFake_FunctionWithNumpy3dArrayInputParameter(self, vi, frequency): # noqa: N802 + with self._func_lock: + if self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc is None: + self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc = self._get_library_function('niFake_FunctionWithNumpy3dArrayInputParameter') + self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc.argtypes = [ViSession, ctypes.POINTER(NIComplexNumber)] # noqa: F405 + self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc.restype = ViStatus # noqa: F405 + return self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc(vi, frequency) + def niFake_FunctionWithRepeatedCapabilityType(self, vi, site_list): # noqa: N802 with self._func_lock: if self.niFake_FunctionWithRepeatedCapabilityType_cfunc is None: diff --git a/generated/nifake/nifake/_library_interpreter.py b/generated/nifake/nifake/_library_interpreter.py index 380a13954..aaeb04f2f 100644 --- a/generated/nifake/nifake/_library_interpreter.py +++ b/generated/nifake/nifake/_library_interpreter.py @@ -32,8 +32,12 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): import numpy if library_type in (_complextype.NIComplexI16, _complextype.NIComplexNumberF32, _complextype.NIComplexNumber): complex_dtype = numpy.dtype(library_type) - structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + if value.ndim > 1: + flattened_array = value.ravel().view(complex_dtype) + return flattened_array.ctypes.data_as(ctypes.POINTER(library_type)) + else: + structured_array = value.view(complex_dtype) + return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) elif isinstance(value, bytes): @@ -225,6 +229,13 @@ def function_with_intflag_parameter(self, flag): # noqa: N802 errors.handle_error(self, error_code, ignore_warnings=False, is_error_handling=False) return + def function_with_numpy3d_array_input_parameter(self, frequency): # noqa: N802 + vi_ctype = _visatype.ViSession(self._vi) # case S110 + frequency_ctype = _get_ctypes_pointer_for_buffer(value=frequency, library_type=_complextype.NIComplexNumber) # case B510 + error_code = self._library.niFake_FunctionWithNumpy3dArrayInputParameter(vi_ctype, frequency_ctype) + errors.handle_error(self, error_code, ignore_warnings=False, is_error_handling=False) + return + def function_with_repeated_capability_type(self, site_list): # noqa: N802 vi_ctype = _visatype.ViSession(self._vi) # case S110 site_list_ctype = ctypes.create_string_buffer(site_list.encode(self._encoding)) # case C010 diff --git a/generated/nifake/nifake/session.py b/generated/nifake/nifake/session.py index 5e88e6ce5..1e9bdeaac 100644 --- a/generated/nifake/nifake/session.py +++ b/generated/nifake/nifake/session.py @@ -959,6 +959,25 @@ def function_with_intflag_parameter(self, flag): raise TypeError('Parameter flag must be of type ' + str(enums.IntFlagEnum)) self._interpreter.function_with_intflag_parameter(flag) + def function_with_numpy3d_array_input_parameter(self, frequency): + r'''function_with_numpy3d_array_input_parameter + + Method that takes a 3D numpy array as an input parameter. + + Args: + frequency (numpy.array(dtype=numpy.complex128)): Specifies the 3D array of complex numbers to write. + + ''' + import numpy + + if type(frequency) is not numpy.ndarray: + raise TypeError('frequency must be {0}, is {1}'.format(numpy.ndarray, type(frequency))) + if numpy.isfortran(frequency) is True: + raise TypeError('frequency must be in C-order') + if frequency.ndim != 3: + raise TypeError('frequency must be numpy.ndarray of dimension=3, is ' + str(frequency.ndim)) + self._interpreter.function_with_numpy3d_array_input_parameter(frequency) + @ivi_synchronized def get_a_boolean(self): r'''get_a_boolean diff --git a/generated/nifake/nifake/unit_tests/_mock_helper.py b/generated/nifake/nifake/unit_tests/_mock_helper.py index 4bdda748f..51c59a387 100644 --- a/generated/nifake/nifake/unit_tests/_mock_helper.py +++ b/generated/nifake/nifake/unit_tests/_mock_helper.py @@ -44,6 +44,8 @@ def __init__(self): self._defaults['FetchWaveform']['actualNumberOfSamples'] = None self._defaults['FunctionWithIntflagParameter'] = {} self._defaults['FunctionWithIntflagParameter']['return'] = 0 + self._defaults['FunctionWithNumpy3dArrayInputParameter'] = {} + self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] = 0 self._defaults['FunctionWithRepeatedCapabilityType'] = {} self._defaults['FunctionWithRepeatedCapabilityType']['return'] = 0 self._defaults['GetABoolean'] = {} @@ -344,6 +346,11 @@ def niFake_FunctionWithIntflagParameter(self, vi, flag): # noqa: N802 return self._defaults['FunctionWithIntflagParameter']['return'] return self._defaults['FunctionWithIntflagParameter']['return'] + def niFake_FunctionWithNumpy3dArrayInputParameter(self, vi, frequency): # noqa: N802 + if self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] != 0: + return self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] + return self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] + def niFake_FunctionWithRepeatedCapabilityType(self, vi, site_list): # noqa: N802 if self._defaults['FunctionWithRepeatedCapabilityType']['return'] != 0: return self._defaults['FunctionWithRepeatedCapabilityType']['return'] @@ -1045,6 +1052,8 @@ def set_side_effects_and_return_values(self, mock_library): mock_library.niFake_FetchWaveform.return_value = 0 mock_library.niFake_FunctionWithIntflagParameter.side_effect = MockFunctionCallError("niFake_FunctionWithIntflagParameter") mock_library.niFake_FunctionWithIntflagParameter.return_value = 0 + mock_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = MockFunctionCallError("niFake_FunctionWithNumpy3dArrayInputParameter") + mock_library.niFake_FunctionWithNumpy3dArrayInputParameter.return_value = 0 mock_library.niFake_FunctionWithRepeatedCapabilityType.side_effect = MockFunctionCallError("niFake_FunctionWithRepeatedCapabilityType") mock_library.niFake_FunctionWithRepeatedCapabilityType.return_value = 0 mock_library.niFake_GetABoolean.side_effect = MockFunctionCallError("niFake_GetABoolean") diff --git a/generated/nifake/nifake/unit_tests/test_library_interpreter.py b/generated/nifake/nifake/unit_tests/test_library_interpreter.py index bf9542186..987d26479 100644 --- a/generated/nifake/nifake/unit_tests/test_library_interpreter.py +++ b/generated/nifake/nifake/unit_tests/test_library_interpreter.py @@ -899,6 +899,50 @@ def test_write_waveform_numpy_complex_interleaved_i16_valid_input(self): _matchers.NIComplexI16PointerMatcher(waveform_data_pointer, number_of_samples) ) + def test_create_deembedding_sparameter_table_array(self): + from nifake._complextype import NIComplexNumber + + array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) + number_of_samples = array_3d.size + flattened_array = array_3d.flatten() + complex_array = (NIComplexNumber * len(flattened_array))() + for i, value in enumerate(flattened_array): + complex_array[i] = NIComplexNumber(value.real, value.imag) + array_3d_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) + self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + interpreter = self.get_initialized_library_interpreter() + interpreter.function_with_numpy3d_array_input_parameter(array_3d) + self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.assert_called_once_with( + _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST), + _matchers.NIComplexNumberPointerMatcher(array_3d_ptr, number_of_samples) + ) + + def test_numpy3dcomplexarrayinput_nomemorycopy(self): + array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) + self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + interpreter = self.get_initialized_library_interpreter() + interpreter.function_with_numpy3d_array_input_parameter(array_3d) + args, kwargs = self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.call_args + actual_pointer = args[1] + numpy_addr = array_3d.__array_interface__['data'][0] + ctypes_addr = ctypes.addressof(actual_pointer.contents) + assert numpy_addr == ctypes_addr, f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + + def test_numpy1dcomplexarrayinput_nomemorycopy(self): + waveform_data = numpy.full(1000, 0.707 + 0.707j, dtype=numpy.complex128) + self.patched_library.niFake_WriteWaveformNumpyComplex64.side_effect = ( + self.side_effects_helper.niFake_WriteWaveformNumpyComplex64 + ) + interpreter = self.get_initialized_library_interpreter() + interpreter.write_waveform_numpy_complex64(waveform_data) + args, kwargs = self.patched_library.niFake_WriteWaveformNumpyComplex64.call_args + actual_pointer = args[2] + numpy_addr = waveform_data.__array_interface__['data'][0] + ctypes_addr = ctypes.addressof(actual_pointer.contents) + assert numpy_addr == ctypes_addr, ( + f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + ) + def test_matcher_prints(self): assert _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST).__repr__() == "ViSessionMatcher(" + str(nifake._visatype.ViSession) + ", 42)" assert _matchers.ViAttrMatcher(SESSION_NUM_FOR_TEST).__repr__() == "ViAttrMatcher(" + str(nifake._visatype.ViAttr) + ", 42)" diff --git a/generated/nirfsg/nirfsg/_library_interpreter.py b/generated/nirfsg/nirfsg/_library_interpreter.py index bee7a62fe..e2a5383a0 100644 --- a/generated/nirfsg/nirfsg/_library_interpreter.py +++ b/generated/nirfsg/nirfsg/_library_interpreter.py @@ -21,8 +21,12 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): import numpy if library_type in (_complextype.NIComplexI16, _complextype.NIComplexNumberF32, _complextype.NIComplexNumber): complex_dtype = numpy.dtype(library_type) - structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + if value.ndim > 1: + flattened_array = value.ravel().view(complex_dtype) + return flattened_array.ctypes.data_as(ctypes.POINTER(library_type)) + else: + structured_array = value.view(complex_dtype) + return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) elif isinstance(value, bytes): diff --git a/src/nifake/metadata/functions.py b/src/nifake/metadata/functions.py index 4ebff5b4e..1828ab049 100644 --- a/src/nifake/metadata/functions.py +++ b/src/nifake/metadata/functions.py @@ -2990,6 +2990,49 @@ ], 'returns': 'ViStatus' }, + 'FunctionWithNumpy3dArrayInputParameter': { + 'codegen_method': 'public', + 'documentation': { + 'description': 'Function that takes a 3D numpy array as an input parameter.' + }, + 'included_in_proto': False, + 'is_error_handling': False, + 'method_templates': [ + { + 'documentation_filename': 'numpy_method', + 'library_interpreter_filename': 'numpy_write_method', + 'method_python_name_suffix': '', + 'session_filename': 'numpy_3d_array_method' + } + ], + 'parameters': [ + { + 'direction': 'in', + 'name': 'vi', + 'documentation': { + 'description': 'Identifies a particular instrument session.' + }, + 'type': 'ViSession', + 'use_array': False, + 'use_in_python_api': True + }, + { + 'complex_type': 'numpy', + 'direction': 'in', + 'documentation': { + 'description': 'Specifies the 3D array of complex numbers to write. ' + }, + 'name': 'frequency', + 'type': 'NIComplexNumber[]', + 'numpy': True, + 'use_numpy_array': True, + 'use_in_python_api': True, + 'multidimension': 3 + }, + ], + 'returns': 'ViStatus', + 'use_session_lock': False + }, 'close': { 'codegen_method': 'private', 'documentation': { diff --git a/src/nifake/unit_tests/test_library_interpreter.py b/src/nifake/unit_tests/test_library_interpreter.py index bf9542186..987d26479 100644 --- a/src/nifake/unit_tests/test_library_interpreter.py +++ b/src/nifake/unit_tests/test_library_interpreter.py @@ -899,6 +899,50 @@ def test_write_waveform_numpy_complex_interleaved_i16_valid_input(self): _matchers.NIComplexI16PointerMatcher(waveform_data_pointer, number_of_samples) ) + def test_create_deembedding_sparameter_table_array(self): + from nifake._complextype import NIComplexNumber + + array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) + number_of_samples = array_3d.size + flattened_array = array_3d.flatten() + complex_array = (NIComplexNumber * len(flattened_array))() + for i, value in enumerate(flattened_array): + complex_array[i] = NIComplexNumber(value.real, value.imag) + array_3d_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) + self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + interpreter = self.get_initialized_library_interpreter() + interpreter.function_with_numpy3d_array_input_parameter(array_3d) + self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.assert_called_once_with( + _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST), + _matchers.NIComplexNumberPointerMatcher(array_3d_ptr, number_of_samples) + ) + + def test_numpy3dcomplexarrayinput_nomemorycopy(self): + array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) + self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + interpreter = self.get_initialized_library_interpreter() + interpreter.function_with_numpy3d_array_input_parameter(array_3d) + args, kwargs = self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.call_args + actual_pointer = args[1] + numpy_addr = array_3d.__array_interface__['data'][0] + ctypes_addr = ctypes.addressof(actual_pointer.contents) + assert numpy_addr == ctypes_addr, f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + + def test_numpy1dcomplexarrayinput_nomemorycopy(self): + waveform_data = numpy.full(1000, 0.707 + 0.707j, dtype=numpy.complex128) + self.patched_library.niFake_WriteWaveformNumpyComplex64.side_effect = ( + self.side_effects_helper.niFake_WriteWaveformNumpyComplex64 + ) + interpreter = self.get_initialized_library_interpreter() + interpreter.write_waveform_numpy_complex64(waveform_data) + args, kwargs = self.patched_library.niFake_WriteWaveformNumpyComplex64.call_args + actual_pointer = args[2] + numpy_addr = waveform_data.__array_interface__['data'][0] + ctypes_addr = ctypes.addressof(actual_pointer.contents) + assert numpy_addr == ctypes_addr, ( + f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + ) + def test_matcher_prints(self): assert _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST).__repr__() == "ViSessionMatcher(" + str(nifake._visatype.ViSession) + ", 42)" assert _matchers.ViAttrMatcher(SESSION_NUM_FOR_TEST).__repr__() == "ViAttrMatcher(" + str(nifake._visatype.ViAttr) + ", 42)" From 44abea930e2aad2670cea86a09180eeb77198d81 Mon Sep 17 00:00:00 2001 From: Rahul R Date: Tue, 15 Jul 2025 13:55:25 +0530 Subject: [PATCH 2/6] Updating comments and multidimension --- build/helper/metadata_add_all.py | 10 +-- build/templates/_library_interpreter.py.mako | 6 +- .../session.py/numpy_3d_array_method.py.mako | 4 +- build/unit_tests/test_codegen_helper.py | 72 +++++++++---------- build/unit_tests/test_metadata_add_all.py | 28 ++++---- .../nifake/nifake/_library_interpreter.py | 6 +- .../nirfsg/nirfsg/_library_interpreter.py | 6 +- src/nifake/metadata/functions.py | 2 +- 8 files changed, 67 insertions(+), 67 deletions(-) diff --git a/build/helper/metadata_add_all.py b/build/helper/metadata_add_all.py index 6d041472d..23113d6c1 100644 --- a/build/helper/metadata_add_all.py +++ b/build/helper/metadata_add_all.py @@ -132,10 +132,10 @@ def _add_complex_type(parameter): parameter['complex_type'] = None -def _add_multidimension(parameter): - '''Adds a multidimension parameter to the metadata for 3d arrays''' - if 'multidimension' not in parameter: - parameter['multidimension'] = 0 +def _add_array_dimension(parameter): + '''Adds a array_dimension parameter to the metadata for 3d arrays''' + if 'array_dimension' not in parameter: + parameter['array_dimension'] = 0 def _add_numpy_info(parameter, parameters, config): @@ -463,7 +463,7 @@ def add_all_function_metadata(functions, config): _add_ctypes_variable_name(p) _add_ctypes_type(p, config) _add_complex_type(p) - _add_multidimension(p) + _add_array_dimension(p) _add_numpy_info(p, functions[f]['parameters'], config) _add_default_value_name(p) _add_default_value_name_for_docs(p, config['module_name']) diff --git a/build/templates/_library_interpreter.py.mako b/build/templates/_library_interpreter.py.mako index 474a204f6..b9f237142 100644 --- a/build/templates/_library_interpreter.py.mako +++ b/build/templates/_library_interpreter.py.mako @@ -54,11 +54,11 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): if library_type in (_complextype.NIComplexI16, _complextype.NIComplexNumberF32, _complextype.NIComplexNumber): complex_dtype = numpy.dtype(library_type) if value.ndim > 1: - flattened_array = value.ravel().view(complex_dtype) - return flattened_array.ctypes.data_as(ctypes.POINTER(library_type)) + # we create a flattened view of the multi-dimensional numpy array + structured_array = value.reshape(-1).view(complex_dtype) else: structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) % else: diff --git a/build/templates/session.py/numpy_3d_array_method.py.mako b/build/templates/session.py/numpy_3d_array_method.py.mako index 121316e3f..f537b5e06 100644 --- a/build/templates/session.py/numpy_3d_array_method.py.mako +++ b/build/templates/session.py/numpy_3d_array_method.py.mako @@ -28,8 +28,8 @@ raise TypeError('${parameter['python_name']} must be {0}, is {1}'.format(numpy.ndarray, type(${parameter['python_name']}))) if numpy.isfortran(${parameter['python_name']}) is True: raise TypeError('${parameter['python_name']} must be in C-order') - if ${parameter['python_name']}.ndim != ${parameter['multidimension']}: - raise TypeError('${parameter['python_name']} must be numpy.ndarray of dimension=${parameter['multidimension']}, is ' + str(${parameter['python_name']}.ndim)) + if ${parameter['python_name']}.ndim != ${parameter['array_dimension']}: + raise TypeError('${parameter['python_name']} must be numpy.ndarray of dimension=${parameter['array_dimension']}, is ' + str(${parameter['python_name']}.ndim)) % endfor % for p in helper.filter_parameters(parameters, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL): % if 'python_api_converter_name' in p: diff --git a/build/unit_tests/test_codegen_helper.py b/build/unit_tests/test_codegen_helper.py index c2e5c7268..6daded26a 100644 --- a/build/unit_tests/test_codegen_helper.py +++ b/build/unit_tests/test_codegen_helper.py @@ -42,7 +42,7 @@ 'type': 'ViSession', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 1 @@ -72,7 +72,7 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 2 @@ -101,7 +101,7 @@ 'type': 'ViString', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 3 @@ -131,7 +131,7 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 4 @@ -158,7 +158,7 @@ 'type': 'ViInt32', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 5 @@ -187,7 +187,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 6 @@ -217,7 +217,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 7 @@ -246,7 +246,7 @@ 'type': 'ViInt64', 'numpy': True, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'numpy_type': 'int64', 'numpy_type_library_call': 'numpy.int64', 'use_in_python_api': True, @@ -269,7 +269,7 @@ 'name': 'numberOfElementsPythonCode', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'number_of_elements_python_code', 'python_name_with_default': 'number_of_elements_python_code', 'python_name_with_doc_default': 'number_of_elements_python_code', @@ -296,7 +296,7 @@ 'name': 'input', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'input', 'python_name_with_default': 'input', 'python_name_with_doc_default': 'input', @@ -326,7 +326,7 @@ 'name': 'inputArray', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'input_array', 'python_name_with_default': 'input_array=None', 'python_name_with_doc_default': 'input_array=None', @@ -353,7 +353,7 @@ 'name': 'inputArraySize', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'input_array_size', 'python_name_with_default': 'input_array_size', 'python_name_with_doc_default': 'input_array_size', @@ -380,7 +380,7 @@ 'name': 'stringSize', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'string_size', 'python_name_with_default': 'string_size', 'python_name_with_doc_default': 'string_size', @@ -407,7 +407,7 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -435,7 +435,7 @@ 'name': 'Timeout', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'timeout', 'python_name_with_default': 'timeout=1.0', 'python_name_with_doc_default': 'timeout=1.0', @@ -465,7 +465,7 @@ 'name': 'channelList', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'original_type': 'ViChar[]', 'python_name': 'channel_list', 'python_name_with_default': 'channel_list', @@ -493,7 +493,7 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -527,7 +527,7 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 18 @@ -558,7 +558,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 19 @@ -579,7 +579,7 @@ 'name': 'aString2', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_string_2', 'python_name_with_default': 'a_string_2', 'python_name_with_doc_default': 'a_string_2', @@ -606,7 +606,7 @@ 'name': 'aStrin3g', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_string_3', 'python_name_with_default': 'a_string_3', 'python_name_with_doc_default': 'a_string_3', @@ -633,7 +633,7 @@ 'name': 'aStringTwist', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_string_twist', 'python_name_with_default': 'a_string_twist', 'python_name_with_doc_default': 'a_string_twist', @@ -669,7 +669,7 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, { # 23 @@ -690,7 +690,7 @@ 'name': 'stringSizeTwist', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'string_size_twist', 'python_name_with_default': 'string_size_twist', 'python_name_with_doc_default': 'string_size_twist', @@ -717,7 +717,7 @@ 'name': 'aBufferArray', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_buffer_array', 'python_name_with_default': 'a_buffer_array', 'python_name_with_doc_default': 'a_buffer_array', @@ -746,7 +746,7 @@ 'name': 'aBufferList', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_buffer_list', 'python_name_with_default': 'a_buffer_list', 'python_name_with_doc_default': 'a_buffer_list', @@ -775,7 +775,7 @@ 'name': 'aBufferTwistArray', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_buffer_twist_array', 'python_name_with_default': 'a_buffer_twist_array', 'python_name_with_doc_default': 'a_buffer_twist_array', @@ -804,7 +804,7 @@ 'name': 'aBufferTwistList', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_buffer_twist_list', 'python_name_with_default': 'a_buffer_twist_list', 'python_name_with_doc_default': 'a_buffer_twist_list', @@ -836,7 +836,7 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', 'python_name_with_doc_default': 'input_array_2=None', @@ -866,7 +866,7 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', @@ -897,7 +897,7 @@ 'name': 'inputArray3', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_3', 'python_name_with_default': 'input_array_3=None', @@ -928,7 +928,7 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -959,7 +959,7 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -987,7 +987,7 @@ 'name': 'aStringEnum', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'python_name': 'a_string_enum', 'python_name_with_default': 'a_string_enum', 'python_name_with_doc_default': 'a_string_enum', @@ -1016,7 +1016,7 @@ 'name': 'indices', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'original_type': 'ViChar[]', 'python_api_converter_name': 'convert_repeated_capabilities_without_prefix', 'python_name': 'indices', @@ -1054,7 +1054,7 @@ 'type': 'ViInt8', 'numpy': False, 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, 'use_in_python_api': True, }, ] diff --git a/build/unit_tests/test_metadata_add_all.py b/build/unit_tests/test_metadata_add_all.py index e23eb3886..4261ecf44 100644 --- a/build/unit_tests/test_metadata_add_all.py +++ b/build/unit_tests/test_metadata_add_all.py @@ -260,7 +260,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'vi', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'name_ctype', @@ -295,7 +295,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'name', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'pin_data_buffer_size_ctype', @@ -333,7 +333,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'pin_data_buffer_size', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'python_code_input_ctype', @@ -371,7 +371,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'python_code_input', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'None if actual_num_pin_data_ctype is None else (ctypes.pointer(actual_num_pin_data_ctype))', @@ -409,7 +409,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'actual_num_pin_data', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'expected_pin_states_ctype', @@ -449,7 +449,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'expected_pin_states', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'custom_type_input_ctype', @@ -487,7 +487,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_input', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'None if custom_type_output_ctype is None else (ctypes.pointer(custom_type_output_ctype))', @@ -525,7 +525,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_output', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'custom_type_without_struct_prefix_input_ctype', @@ -563,7 +563,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_without_struct_prefix_input', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'None if custom_type_without_struct_prefix_output_ctype is None else (ctypes.pointer(custom_type_without_struct_prefix_output_ctype))', @@ -601,7 +601,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_without_struct_prefix_output', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, ], 'python_name': 'make_a_foo', @@ -650,7 +650,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'vi', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'status_ctype', @@ -688,7 +688,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'status', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'data_buffer_size_ctype', @@ -726,7 +726,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'data_buffer_size', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, { 'ctypes_method_call_snippet': 'data_ctype', @@ -765,7 +765,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'data', 'complex_type': None, - 'multidimension': 0, + 'array_dimension': 0, }, ], 'documentation': { diff --git a/generated/nifake/nifake/_library_interpreter.py b/generated/nifake/nifake/_library_interpreter.py index aaeb04f2f..15780714e 100644 --- a/generated/nifake/nifake/_library_interpreter.py +++ b/generated/nifake/nifake/_library_interpreter.py @@ -33,11 +33,11 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): if library_type in (_complextype.NIComplexI16, _complextype.NIComplexNumberF32, _complextype.NIComplexNumber): complex_dtype = numpy.dtype(library_type) if value.ndim > 1: - flattened_array = value.ravel().view(complex_dtype) - return flattened_array.ctypes.data_as(ctypes.POINTER(library_type)) + # we create a flattened view of the multi-dimensional numpy array + structured_array = value.reshape(-1).view(complex_dtype) else: structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) elif isinstance(value, bytes): diff --git a/generated/nirfsg/nirfsg/_library_interpreter.py b/generated/nirfsg/nirfsg/_library_interpreter.py index e2a5383a0..756620d7e 100644 --- a/generated/nirfsg/nirfsg/_library_interpreter.py +++ b/generated/nirfsg/nirfsg/_library_interpreter.py @@ -22,11 +22,11 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): if library_type in (_complextype.NIComplexI16, _complextype.NIComplexNumberF32, _complextype.NIComplexNumber): complex_dtype = numpy.dtype(library_type) if value.ndim > 1: - flattened_array = value.ravel().view(complex_dtype) - return flattened_array.ctypes.data_as(ctypes.POINTER(library_type)) + # we create a flattened view of the multi-dimensional numpy array + structured_array = value.reshape(-1).view(complex_dtype) else: structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) elif isinstance(value, bytes): diff --git a/src/nifake/metadata/functions.py b/src/nifake/metadata/functions.py index 1828ab049..efed77aad 100644 --- a/src/nifake/metadata/functions.py +++ b/src/nifake/metadata/functions.py @@ -3027,7 +3027,7 @@ 'numpy': True, 'use_numpy_array': True, 'use_in_python_api': True, - 'multidimension': 3 + 'array_dimension': 3 }, ], 'returns': 'ViStatus', From f070fe8a8bb1ad403b816e5fb7ce5489fdc1f0d5 Mon Sep 17 00:00:00 2001 From: Rahul R Date: Fri, 18 Jul 2025 15:17:28 +0530 Subject: [PATCH 3/6] Updating the test case name --- build/helper/helper.py | 2 +- generated/nifake/nifake/unit_tests/test_library_interpreter.py | 2 +- src/nifake/unit_tests/test_library_interpreter.py | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/build/helper/helper.py b/build/helper/helper.py index f0c48db83..b2f7c86e4 100644 --- a/build/helper/helper.py +++ b/build/helper/helper.py @@ -26,7 +26,7 @@ 'ViChar[]': { 'array_type': None, 'python_type': 'str', 'numpy_type': None, }, # noqa: E201, E202, E241 'ViBoolean': { 'array_type': None, 'python_type': 'bool', 'numpy_type': None, }, # noqa: E201, E202, E241 'ViRsrc': { 'array_type': None, 'python_type': 'str', 'numpy_type': 'bool_', }, # noqa: E201, E202, E241 - 'NIComplexNumber': { 'array_type': 'P', 'python_type': None, 'numpy_type': 'complex128', }, # noqa: E201, E202, E241 + 'NIComplexNumber': { 'array_type': None, 'python_type': None, 'numpy_type': 'complex128', }, # noqa: E201, E202, E241 'NIComplexNumberF32': { 'array_type': None, 'python_type': None, 'numpy_type': 'complex64', }, # noqa: E201, E202, E241 'NIComplexI16': { 'array_type': None, 'python_type': None, 'numpy_type': 'int16', }, # noqa: E201, E202, E241 } diff --git a/generated/nifake/nifake/unit_tests/test_library_interpreter.py b/generated/nifake/nifake/unit_tests/test_library_interpreter.py index 987d26479..b272e65d1 100644 --- a/generated/nifake/nifake/unit_tests/test_library_interpreter.py +++ b/generated/nifake/nifake/unit_tests/test_library_interpreter.py @@ -899,7 +899,7 @@ def test_write_waveform_numpy_complex_interleaved_i16_valid_input(self): _matchers.NIComplexI16PointerMatcher(waveform_data_pointer, number_of_samples) ) - def test_create_deembedding_sparameter_table_array(self): + def test_function_with_numpy3d_array_input_parameter(self): from nifake._complextype import NIComplexNumber array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) diff --git a/src/nifake/unit_tests/test_library_interpreter.py b/src/nifake/unit_tests/test_library_interpreter.py index 987d26479..b272e65d1 100644 --- a/src/nifake/unit_tests/test_library_interpreter.py +++ b/src/nifake/unit_tests/test_library_interpreter.py @@ -899,7 +899,7 @@ def test_write_waveform_numpy_complex_interleaved_i16_valid_input(self): _matchers.NIComplexI16PointerMatcher(waveform_data_pointer, number_of_samples) ) - def test_create_deembedding_sparameter_table_array(self): + def test_function_with_numpy3d_array_input_parameter(self): from nifake._complextype import NIComplexNumber array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) From 19fa2899ec664ab257d3da4cc45ff7c6f6c8cf63 Mon Sep 17 00:00:00 2001 From: Rahul R Date: Fri, 18 Jul 2025 17:18:11 +0530 Subject: [PATCH 4/6] Updated the api names and test cases --- build/helper/codegen_helper.py | 5 +- build/helper/metadata_add_all.py | 4 +- build/templates/_library_interpreter.py.mako | 6 +- .../session.py/numpy_3d_array_method.py.mako | 44 ------------ .../session.py/numpy_write_method.py.mako | 4 ++ build/unit_tests/test_codegen_helper.py | 72 +++++++++---------- build/unit_tests/test_metadata_add_all.py | 28 ++++---- .../nifake/nifake/_grpc_stub_interpreter.py | 6 +- generated/nifake/nifake/_library.py | 18 ++--- .../nifake/nifake/_library_interpreter.py | 18 ++--- generated/nifake/nifake/session.py | 40 ++++++----- .../nifake/nifake/unit_tests/_mock_helper.py | 18 ++--- .../unit_tests/test_library_interpreter.py | 36 +++++----- .../nirfsg/nirfsg/_library_interpreter.py | 6 +- src/nifake/metadata/functions.py | 10 +-- .../unit_tests/test_library_interpreter.py | 36 +++++----- 16 files changed, 155 insertions(+), 196 deletions(-) delete mode 100644 build/templates/session.py/numpy_3d_array_method.py.mako diff --git a/build/helper/codegen_helper.py b/build/helper/codegen_helper.py index 4bde6d061..86b83c476 100644 --- a/build/helper/codegen_helper.py +++ b/build/helper/codegen_helper.py @@ -132,10 +132,7 @@ def _get_library_interpreter_output_param_return_snippet(output_parameter, param val_suffix = '' if is_custom_type else '.value' if output_parameter['use_array']: - if output_parameter['numpy'] and output_parameter['complex_type'] is not None: - snippet = 'list({}_array)'.format(output_parameter['python_name']) - else: - snippet = '{}_array'.format(output_parameter['python_name']) + snippet = '{}_array'.format(output_parameter['python_name']) elif output_parameter['is_buffer']: if output_parameter['size']['mechanism'] == 'fixed': size = str(output_parameter['size']['value']) diff --git a/build/helper/metadata_add_all.py b/build/helper/metadata_add_all.py index 23113d6c1..0ff740cd3 100644 --- a/build/helper/metadata_add_all.py +++ b/build/helper/metadata_add_all.py @@ -133,9 +133,9 @@ def _add_complex_type(parameter): def _add_array_dimension(parameter): - '''Adds a array_dimension parameter to the metadata for 3d arrays''' + '''Adds a array_dimension parameter to the metadata for multi dimensional arrays''' if 'array_dimension' not in parameter: - parameter['array_dimension'] = 0 + parameter['array_dimension'] = 1 def _add_numpy_info(parameter, parameters, config): diff --git a/build/templates/_library_interpreter.py.mako b/build/templates/_library_interpreter.py.mako index b9f237142..f3eda2e79 100644 --- a/build/templates/_library_interpreter.py.mako +++ b/build/templates/_library_interpreter.py.mako @@ -55,10 +55,10 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): complex_dtype = numpy.dtype(library_type) if value.ndim > 1: # we create a flattened view of the multi-dimensional numpy array - structured_array = value.reshape(-1).view(complex_dtype) + restructured_array_view = value.ravel().view(complex_dtype) else: - structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + restructured_array_view = value.view(complex_dtype) + return restructured_array_view.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) % else: diff --git a/build/templates/session.py/numpy_3d_array_method.py.mako b/build/templates/session.py/numpy_3d_array_method.py.mako deleted file mode 100644 index f537b5e06..000000000 --- a/build/templates/session.py/numpy_3d_array_method.py.mako +++ /dev/null @@ -1,44 +0,0 @@ -<%page args="f, config, method_template"/>\ -<% - '''Renders a Session method for writing numpy.array corresponding to the passed-in function metadata.''' - - import build.helper as helper - - parameters = f['parameters'] - enum_input_parameters = helper.filter_parameters(parameters, helper.ParameterUsageOptions.INPUT_ENUM_PARAMETERS) - output_parameters = helper.filter_parameters(parameters, helper.ParameterUsageOptions.API_NUMPY_OUTPUT_PARAMETERS) - output_parameters_snippet = ', '.join(p['python_name'] for p in output_parameters) - suffix = method_template['method_python_name_suffix'] -%>\ - def ${f['python_name']}${suffix}(${helper.get_params_snippet(f, helper.ParameterUsageOptions.SESSION_METHOD_DECLARATION)}): - r'''${f['python_name']}${suffix} - - ${helper.get_function_docstring(f, True, config, indent=8)} - ''' - import numpy - -% for parameter in enum_input_parameters: - ${helper.get_enum_type_check_snippet(parameter, indent=12)} -% endfor -% for size_check_snippet in helper.get_parameter_size_check_snippets(parameters): - ${size_check_snippet} -% endfor -% for parameter in helper.filter_parameters(parameters, helper.ParameterUsageOptions.NUMPY_PARAMETERS): - if type(${parameter['python_name']}) is not numpy.ndarray: - raise TypeError('${parameter['python_name']} must be {0}, is {1}'.format(numpy.ndarray, type(${parameter['python_name']}))) - if numpy.isfortran(${parameter['python_name']}) is True: - raise TypeError('${parameter['python_name']} must be in C-order') - if ${parameter['python_name']}.ndim != ${parameter['array_dimension']}: - raise TypeError('${parameter['python_name']} must be numpy.ndarray of dimension=${parameter['array_dimension']}, is ' + str(${parameter['python_name']}.ndim)) -% endfor -% for p in helper.filter_parameters(parameters, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL): -% if 'python_api_converter_name' in p: - ${p['python_name']} = _converters.${p['python_api_converter_name']}(${p['python_name']}) -% endif -% endfor -% if output_parameters: - ${output_parameters_snippet} = self._interpreter.${f['interpreter_name']}${suffix}(${helper.get_params_snippet(f, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL)}) - ${helper.get_session_method_return_snippet(parameters, config, use_numpy_array=True)} -% else: - self._interpreter.${f['interpreter_name']}${suffix}(${helper.get_params_snippet(f, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL)}) -% endif diff --git a/build/templates/session.py/numpy_write_method.py.mako b/build/templates/session.py/numpy_write_method.py.mako index 8da38befe..6b09ef738 100644 --- a/build/templates/session.py/numpy_write_method.py.mako +++ b/build/templates/session.py/numpy_write_method.py.mako @@ -30,6 +30,10 @@ raise TypeError('${parameter['python_name']} must be in C-order') if ${parameter['python_name']}.dtype is not numpy.dtype('${parameter['numpy_type']}'): raise TypeError('${parameter['python_name']} must be numpy.ndarray of dtype=${parameter['numpy_type']}, is ' + str(${parameter['python_name']}.dtype)) +% if parameter['array_dimension'] > 1: + if ${parameter['python_name']}.ndim != ${parameter['array_dimension']}: + raise TypeError('${parameter['python_name']} must be numpy.ndarray of dimension=${parameter['array_dimension']}, is ' + str(${parameter['python_name']}.ndim)) +% endif % endfor % for p in helper.filter_parameters(parameters, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL): % if 'python_api_converter_name' in p: diff --git a/build/unit_tests/test_codegen_helper.py b/build/unit_tests/test_codegen_helper.py index 6daded26a..d0cfd5907 100644 --- a/build/unit_tests/test_codegen_helper.py +++ b/build/unit_tests/test_codegen_helper.py @@ -42,7 +42,7 @@ 'type': 'ViSession', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 1 @@ -72,7 +72,7 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 2 @@ -101,7 +101,7 @@ 'type': 'ViString', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 3 @@ -131,7 +131,7 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 4 @@ -158,7 +158,7 @@ 'type': 'ViInt32', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 5 @@ -187,7 +187,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 6 @@ -217,7 +217,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 7 @@ -246,7 +246,7 @@ 'type': 'ViInt64', 'numpy': True, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'numpy_type': 'int64', 'numpy_type_library_call': 'numpy.int64', 'use_in_python_api': True, @@ -269,7 +269,7 @@ 'name': 'numberOfElementsPythonCode', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'number_of_elements_python_code', 'python_name_with_default': 'number_of_elements_python_code', 'python_name_with_doc_default': 'number_of_elements_python_code', @@ -296,7 +296,7 @@ 'name': 'input', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'input', 'python_name_with_default': 'input', 'python_name_with_doc_default': 'input', @@ -326,7 +326,7 @@ 'name': 'inputArray', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'input_array', 'python_name_with_default': 'input_array=None', 'python_name_with_doc_default': 'input_array=None', @@ -353,7 +353,7 @@ 'name': 'inputArraySize', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'input_array_size', 'python_name_with_default': 'input_array_size', 'python_name_with_doc_default': 'input_array_size', @@ -380,7 +380,7 @@ 'name': 'stringSize', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'string_size', 'python_name_with_default': 'string_size', 'python_name_with_doc_default': 'string_size', @@ -407,7 +407,7 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -435,7 +435,7 @@ 'name': 'Timeout', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'timeout', 'python_name_with_default': 'timeout=1.0', 'python_name_with_doc_default': 'timeout=1.0', @@ -465,7 +465,7 @@ 'name': 'channelList', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'original_type': 'ViChar[]', 'python_name': 'channel_list', 'python_name_with_default': 'channel_list', @@ -493,7 +493,7 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -527,7 +527,7 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 18 @@ -558,7 +558,7 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 19 @@ -579,7 +579,7 @@ 'name': 'aString2', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_string_2', 'python_name_with_default': 'a_string_2', 'python_name_with_doc_default': 'a_string_2', @@ -606,7 +606,7 @@ 'name': 'aStrin3g', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_string_3', 'python_name_with_default': 'a_string_3', 'python_name_with_doc_default': 'a_string_3', @@ -633,7 +633,7 @@ 'name': 'aStringTwist', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_string_twist', 'python_name_with_default': 'a_string_twist', 'python_name_with_doc_default': 'a_string_twist', @@ -669,7 +669,7 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, { # 23 @@ -690,7 +690,7 @@ 'name': 'stringSizeTwist', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'string_size_twist', 'python_name_with_default': 'string_size_twist', 'python_name_with_doc_default': 'string_size_twist', @@ -717,7 +717,7 @@ 'name': 'aBufferArray', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_buffer_array', 'python_name_with_default': 'a_buffer_array', 'python_name_with_doc_default': 'a_buffer_array', @@ -746,7 +746,7 @@ 'name': 'aBufferList', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_buffer_list', 'python_name_with_default': 'a_buffer_list', 'python_name_with_doc_default': 'a_buffer_list', @@ -775,7 +775,7 @@ 'name': 'aBufferTwistArray', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_buffer_twist_array', 'python_name_with_default': 'a_buffer_twist_array', 'python_name_with_doc_default': 'a_buffer_twist_array', @@ -804,7 +804,7 @@ 'name': 'aBufferTwistList', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_buffer_twist_list', 'python_name_with_default': 'a_buffer_twist_list', 'python_name_with_doc_default': 'a_buffer_twist_list', @@ -836,7 +836,7 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', 'python_name_with_doc_default': 'input_array_2=None', @@ -866,7 +866,7 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', @@ -897,7 +897,7 @@ 'name': 'inputArray3', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_3', 'python_name_with_default': 'input_array_3=None', @@ -928,7 +928,7 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -959,7 +959,7 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -987,7 +987,7 @@ 'name': 'aStringEnum', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'python_name': 'a_string_enum', 'python_name_with_default': 'a_string_enum', 'python_name_with_doc_default': 'a_string_enum', @@ -1016,7 +1016,7 @@ 'name': 'indices', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'original_type': 'ViChar[]', 'python_api_converter_name': 'convert_repeated_capabilities_without_prefix', 'python_name': 'indices', @@ -1054,7 +1054,7 @@ 'type': 'ViInt8', 'numpy': False, 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, 'use_in_python_api': True, }, ] diff --git a/build/unit_tests/test_metadata_add_all.py b/build/unit_tests/test_metadata_add_all.py index 4261ecf44..b927cc226 100644 --- a/build/unit_tests/test_metadata_add_all.py +++ b/build/unit_tests/test_metadata_add_all.py @@ -260,7 +260,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'vi', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'name_ctype', @@ -295,7 +295,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'name', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'pin_data_buffer_size_ctype', @@ -333,7 +333,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'pin_data_buffer_size', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'python_code_input_ctype', @@ -371,7 +371,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'python_code_input', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'None if actual_num_pin_data_ctype is None else (ctypes.pointer(actual_num_pin_data_ctype))', @@ -409,7 +409,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'actual_num_pin_data', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'expected_pin_states_ctype', @@ -449,7 +449,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'expected_pin_states', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'custom_type_input_ctype', @@ -487,7 +487,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_input', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'None if custom_type_output_ctype is None else (ctypes.pointer(custom_type_output_ctype))', @@ -525,7 +525,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_output', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'custom_type_without_struct_prefix_input_ctype', @@ -563,7 +563,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_without_struct_prefix_input', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'None if custom_type_without_struct_prefix_output_ctype is None else (ctypes.pointer(custom_type_without_struct_prefix_output_ctype))', @@ -601,7 +601,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'custom_type_without_struct_prefix_output', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, ], 'python_name': 'make_a_foo', @@ -650,7 +650,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'vi', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'status_ctype', @@ -688,7 +688,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'status', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'data_buffer_size_ctype', @@ -726,7 +726,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': False, 'python_name_or_default_for_init': 'data_buffer_size', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, { 'ctypes_method_call_snippet': 'data_ctype', @@ -765,7 +765,7 @@ def _compare_dicts(actual, expected): 'use_in_python_api': True, 'python_name_or_default_for_init': 'data', 'complex_type': None, - 'array_dimension': 0, + 'array_dimension': 1, }, ], 'documentation': { diff --git a/generated/nifake/nifake/_grpc_stub_interpreter.py b/generated/nifake/nifake/_grpc_stub_interpreter.py index 8432e127a..3ced5bc30 100644 --- a/generated/nifake/nifake/_grpc_stub_interpreter.py +++ b/generated/nifake/nifake/_grpc_stub_interpreter.py @@ -144,15 +144,15 @@ def fetch_waveform(self, number_of_samples): # noqa: N802 def fetch_waveform_into(self, number_of_samples): # noqa: N802 raise NotImplementedError('numpy-specific methods are not supported over gRPC') + def function_with3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): # noqa: N802 + raise NotImplementedError('numpy-specific methods are not supported over gRPC') + def function_with_intflag_parameter(self, flag): # noqa: N802 self._invoke( self._client.FunctionWithIntflagParameter, grpc_types.FunctionWithIntflagParameterRequest(vi=self._vi, flag=flag.value), ) - def function_with_numpy3d_array_input_parameter(self, frequency): # noqa: N802 - raise NotImplementedError('numpy-specific methods are not supported over gRPC') - def function_with_repeated_capability_type(self, site_list): # noqa: N802 raise NotImplementedError('function_with_repeated_capability_type is not supported over gRPC') diff --git a/generated/nifake/nifake/_library.py b/generated/nifake/nifake/_library.py index a24075fd3..95a91e2f7 100644 --- a/generated/nifake/nifake/_library.py +++ b/generated/nifake/nifake/_library.py @@ -36,8 +36,8 @@ def __init__(self, ctypes_library): self.niFake_EnumInputFunctionWithDefaults_cfunc = None self.niFake_ExportAttributeConfigurationBuffer_cfunc = None self.niFake_FetchWaveform_cfunc = None + self.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter_cfunc = None self.niFake_FunctionWithIntflagParameter_cfunc = None - self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc = None self.niFake_FunctionWithRepeatedCapabilityType_cfunc = None self.niFake_GetABoolean_cfunc = None self.niFake_GetANumber_cfunc = None @@ -189,6 +189,14 @@ def niFake_FetchWaveform(self, vi, number_of_samples, waveform_data, actual_numb self.niFake_FetchWaveform_cfunc.restype = ViStatus # noqa: F405 return self.niFake_FetchWaveform_cfunc(vi, number_of_samples, waveform_data, actual_number_of_samples) + def niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter(self, vi, multidimensional_array): # noqa: N802 + with self._func_lock: + if self.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter_cfunc is None: + self.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter_cfunc = self._get_library_function('niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter') + self.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter_cfunc.argtypes = [ViSession, ctypes.POINTER(NIComplexNumber)] # noqa: F405 + self.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter_cfunc.restype = ViStatus # noqa: F405 + return self.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter_cfunc(vi, multidimensional_array) + def niFake_FunctionWithIntflagParameter(self, vi, flag): # noqa: N802 with self._func_lock: if self.niFake_FunctionWithIntflagParameter_cfunc is None: @@ -197,14 +205,6 @@ def niFake_FunctionWithIntflagParameter(self, vi, flag): # noqa: N802 self.niFake_FunctionWithIntflagParameter_cfunc.restype = ViStatus # noqa: F405 return self.niFake_FunctionWithIntflagParameter_cfunc(vi, flag) - def niFake_FunctionWithNumpy3dArrayInputParameter(self, vi, frequency): # noqa: N802 - with self._func_lock: - if self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc is None: - self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc = self._get_library_function('niFake_FunctionWithNumpy3dArrayInputParameter') - self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc.argtypes = [ViSession, ctypes.POINTER(NIComplexNumber)] # noqa: F405 - self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc.restype = ViStatus # noqa: F405 - return self.niFake_FunctionWithNumpy3dArrayInputParameter_cfunc(vi, frequency) - def niFake_FunctionWithRepeatedCapabilityType(self, vi, site_list): # noqa: N802 with self._func_lock: if self.niFake_FunctionWithRepeatedCapabilityType_cfunc is None: diff --git a/generated/nifake/nifake/_library_interpreter.py b/generated/nifake/nifake/_library_interpreter.py index 15780714e..487ae0f4d 100644 --- a/generated/nifake/nifake/_library_interpreter.py +++ b/generated/nifake/nifake/_library_interpreter.py @@ -34,10 +34,10 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): complex_dtype = numpy.dtype(library_type) if value.ndim > 1: # we create a flattened view of the multi-dimensional numpy array - structured_array = value.reshape(-1).view(complex_dtype) + restructured_array_view = value.ravel().view(complex_dtype) else: - structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + restructured_array_view = value.view(complex_dtype) + return restructured_array_view.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) elif isinstance(value, bytes): @@ -222,17 +222,17 @@ def fetch_waveform_into(self, waveform_data): # noqa: N802 errors.handle_error(self, error_code, ignore_warnings=False, is_error_handling=False) return - def function_with_intflag_parameter(self, flag): # noqa: N802 + def function_with3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): # noqa: N802 vi_ctype = _visatype.ViSession(self._vi) # case S110 - flag_ctype = _visatype.ViUInt64(flag.value) # case S130 - error_code = self._library.niFake_FunctionWithIntflagParameter(vi_ctype, flag_ctype) + multidimensional_array_ctype = _get_ctypes_pointer_for_buffer(value=multidimensional_array, library_type=_complextype.NIComplexNumber) # case B510 + error_code = self._library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter(vi_ctype, multidimensional_array_ctype) errors.handle_error(self, error_code, ignore_warnings=False, is_error_handling=False) return - def function_with_numpy3d_array_input_parameter(self, frequency): # noqa: N802 + def function_with_intflag_parameter(self, flag): # noqa: N802 vi_ctype = _visatype.ViSession(self._vi) # case S110 - frequency_ctype = _get_ctypes_pointer_for_buffer(value=frequency, library_type=_complextype.NIComplexNumber) # case B510 - error_code = self._library.niFake_FunctionWithNumpy3dArrayInputParameter(vi_ctype, frequency_ctype) + flag_ctype = _visatype.ViUInt64(flag.value) # case S130 + error_code = self._library.niFake_FunctionWithIntflagParameter(vi_ctype, flag_ctype) errors.handle_error(self, error_code, ignore_warnings=False, is_error_handling=False) return diff --git a/generated/nifake/nifake/session.py b/generated/nifake/nifake/session.py index 1e9bdeaac..3a09ae79c 100644 --- a/generated/nifake/nifake/session.py +++ b/generated/nifake/nifake/session.py @@ -945,6 +945,27 @@ def fetch_waveform_into(self, waveform_data): raise TypeError('waveform_data must be numpy.ndarray of dtype=float64, is ' + str(waveform_data.dtype)) self._interpreter.fetch_waveform_into(waveform_data) + def function_with3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): + r'''function_with3d_numpy_array_of_numpy_complex128_input_parameter + + Method that takes a 3D numpy array of numpy complex128 as an input parameter. + + Args: + multidimensional_array (numpy.array(dtype=numpy.complex128)): Specifies the 3D array of numpy complex numbers to write. + + ''' + import numpy + + if type(multidimensional_array) is not numpy.ndarray: + raise TypeError('multidimensional_array must be {0}, is {1}'.format(numpy.ndarray, type(multidimensional_array))) + if numpy.isfortran(multidimensional_array) is True: + raise TypeError('multidimensional_array must be in C-order') + if multidimensional_array.dtype is not numpy.dtype('complex128'): + raise TypeError('multidimensional_array must be numpy.ndarray of dtype=complex128, is ' + str(multidimensional_array.dtype)) + if multidimensional_array.ndim != 3: + raise TypeError('multidimensional_array must be numpy.ndarray of dimension=3, is ' + str(multidimensional_array.ndim)) + self._interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(multidimensional_array) + @ivi_synchronized def function_with_intflag_parameter(self, flag): r'''function_with_intflag_parameter @@ -959,25 +980,6 @@ def function_with_intflag_parameter(self, flag): raise TypeError('Parameter flag must be of type ' + str(enums.IntFlagEnum)) self._interpreter.function_with_intflag_parameter(flag) - def function_with_numpy3d_array_input_parameter(self, frequency): - r'''function_with_numpy3d_array_input_parameter - - Method that takes a 3D numpy array as an input parameter. - - Args: - frequency (numpy.array(dtype=numpy.complex128)): Specifies the 3D array of complex numbers to write. - - ''' - import numpy - - if type(frequency) is not numpy.ndarray: - raise TypeError('frequency must be {0}, is {1}'.format(numpy.ndarray, type(frequency))) - if numpy.isfortran(frequency) is True: - raise TypeError('frequency must be in C-order') - if frequency.ndim != 3: - raise TypeError('frequency must be numpy.ndarray of dimension=3, is ' + str(frequency.ndim)) - self._interpreter.function_with_numpy3d_array_input_parameter(frequency) - @ivi_synchronized def get_a_boolean(self): r'''get_a_boolean diff --git a/generated/nifake/nifake/unit_tests/_mock_helper.py b/generated/nifake/nifake/unit_tests/_mock_helper.py index 51c59a387..8c76539e0 100644 --- a/generated/nifake/nifake/unit_tests/_mock_helper.py +++ b/generated/nifake/nifake/unit_tests/_mock_helper.py @@ -42,10 +42,10 @@ def __init__(self): self._defaults['FetchWaveform']['return'] = 0 self._defaults['FetchWaveform']['waveformData'] = None self._defaults['FetchWaveform']['actualNumberOfSamples'] = None + self._defaults['FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter'] = {} + self._defaults['FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter']['return'] = 0 self._defaults['FunctionWithIntflagParameter'] = {} self._defaults['FunctionWithIntflagParameter']['return'] = 0 - self._defaults['FunctionWithNumpy3dArrayInputParameter'] = {} - self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] = 0 self._defaults['FunctionWithRepeatedCapabilityType'] = {} self._defaults['FunctionWithRepeatedCapabilityType']['return'] = 0 self._defaults['GetABoolean'] = {} @@ -341,16 +341,16 @@ def niFake_FetchWaveform(self, vi, number_of_samples, waveform_data, actual_numb actual_number_of_samples.contents.value = self._defaults['FetchWaveform']['actualNumberOfSamples'] return self._defaults['FetchWaveform']['return'] + def niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter(self, vi, multidimensional_array): # noqa: N802 + if self._defaults['FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter']['return'] != 0: + return self._defaults['FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter']['return'] + return self._defaults['FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter']['return'] + def niFake_FunctionWithIntflagParameter(self, vi, flag): # noqa: N802 if self._defaults['FunctionWithIntflagParameter']['return'] != 0: return self._defaults['FunctionWithIntflagParameter']['return'] return self._defaults['FunctionWithIntflagParameter']['return'] - def niFake_FunctionWithNumpy3dArrayInputParameter(self, vi, frequency): # noqa: N802 - if self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] != 0: - return self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] - return self._defaults['FunctionWithNumpy3dArrayInputParameter']['return'] - def niFake_FunctionWithRepeatedCapabilityType(self, vi, site_list): # noqa: N802 if self._defaults['FunctionWithRepeatedCapabilityType']['return'] != 0: return self._defaults['FunctionWithRepeatedCapabilityType']['return'] @@ -1050,10 +1050,10 @@ def set_side_effects_and_return_values(self, mock_library): mock_library.niFake_ExportAttributeConfigurationBuffer.return_value = 0 mock_library.niFake_FetchWaveform.side_effect = MockFunctionCallError("niFake_FetchWaveform") mock_library.niFake_FetchWaveform.return_value = 0 + mock_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = MockFunctionCallError("niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter") + mock_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.return_value = 0 mock_library.niFake_FunctionWithIntflagParameter.side_effect = MockFunctionCallError("niFake_FunctionWithIntflagParameter") mock_library.niFake_FunctionWithIntflagParameter.return_value = 0 - mock_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = MockFunctionCallError("niFake_FunctionWithNumpy3dArrayInputParameter") - mock_library.niFake_FunctionWithNumpy3dArrayInputParameter.return_value = 0 mock_library.niFake_FunctionWithRepeatedCapabilityType.side_effect = MockFunctionCallError("niFake_FunctionWithRepeatedCapabilityType") mock_library.niFake_FunctionWithRepeatedCapabilityType.return_value = 0 mock_library.niFake_GetABoolean.side_effect = MockFunctionCallError("niFake_GetABoolean") diff --git a/generated/nifake/nifake/unit_tests/test_library_interpreter.py b/generated/nifake/nifake/unit_tests/test_library_interpreter.py index b272e65d1..4286bc35c 100644 --- a/generated/nifake/nifake/unit_tests/test_library_interpreter.py +++ b/generated/nifake/nifake/unit_tests/test_library_interpreter.py @@ -899,7 +899,7 @@ def test_write_waveform_numpy_complex_interleaved_i16_valid_input(self): _matchers.NIComplexI16PointerMatcher(waveform_data_pointer, number_of_samples) ) - def test_function_with_numpy3d_array_input_parameter(self): + def test_write_3d_numpy_array_of_numpy_complex128(self): from nifake._complextype import NIComplexNumber array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) @@ -909,38 +909,38 @@ def test_function_with_numpy3d_array_input_parameter(self): for i, value in enumerate(flattened_array): complex_array[i] = NIComplexNumber(value.real, value.imag) array_3d_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) - self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with_numpy3d_array_input_parameter(array_3d) - self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.assert_called_once_with( + interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.assert_called_once_with( _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST), _matchers.NIComplexNumberPointerMatcher(array_3d_ptr, number_of_samples) ) - def test_numpy3dcomplexarrayinput_nomemorycopy(self): + def test_no_memorycopy_with_multi_dimensional_numpy_complex128_array(self): array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) - self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with_numpy3d_array_input_parameter(array_3d) - args, kwargs = self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.call_args + interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + args, kwargs = self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.call_args actual_pointer = args[1] - numpy_addr = array_3d.__array_interface__['data'][0] - ctypes_addr = ctypes.addressof(actual_pointer.contents) - assert numpy_addr == ctypes_addr, f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + input_address = array_3d.__array_interface__['data'][0] + address_passed_to_library = ctypes.addressof(actual_pointer.contents) + assert input_address == address_passed_to_library, f"Addresses do NOT match: input_address={input_address}, address_passed_to_library={address_passed_to_library}" - def test_numpy1dcomplexarrayinput_nomemorycopy(self): - waveform_data = numpy.full(1000, 0.707 + 0.707j, dtype=numpy.complex128) + def test_no_memorycopy_with_numpy_complex64_array(self): + array_1d = numpy.full(1000, 0.707 + 0.707j, dtype=numpy.complex64) self.patched_library.niFake_WriteWaveformNumpyComplex64.side_effect = ( self.side_effects_helper.niFake_WriteWaveformNumpyComplex64 ) interpreter = self.get_initialized_library_interpreter() - interpreter.write_waveform_numpy_complex64(waveform_data) + interpreter.write_waveform_numpy_complex64(array_1d) args, kwargs = self.patched_library.niFake_WriteWaveformNumpyComplex64.call_args actual_pointer = args[2] - numpy_addr = waveform_data.__array_interface__['data'][0] - ctypes_addr = ctypes.addressof(actual_pointer.contents) - assert numpy_addr == ctypes_addr, ( - f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + input_address = array_1d.__array_interface__['data'][0] + address_passed_to_library = ctypes.addressof(actual_pointer.contents) + assert input_address == address_passed_to_library, ( + f"Addresses do NOT match: input_address={input_address}, address_passed_to_library={address_passed_to_library}" ) def test_matcher_prints(self): diff --git a/generated/nirfsg/nirfsg/_library_interpreter.py b/generated/nirfsg/nirfsg/_library_interpreter.py index 756620d7e..b8e6388c5 100644 --- a/generated/nirfsg/nirfsg/_library_interpreter.py +++ b/generated/nirfsg/nirfsg/_library_interpreter.py @@ -23,10 +23,10 @@ def _get_ctypes_pointer_for_buffer(value=None, library_type=None, size=None): complex_dtype = numpy.dtype(library_type) if value.ndim > 1: # we create a flattened view of the multi-dimensional numpy array - structured_array = value.reshape(-1).view(complex_dtype) + restructured_array_view = value.ravel().view(complex_dtype) else: - structured_array = value.view(complex_dtype) - return structured_array.ctypes.data_as(ctypes.POINTER(library_type)) + restructured_array_view = value.view(complex_dtype) + return restructured_array_view.ctypes.data_as(ctypes.POINTER(library_type)) else: return numpy.ctypeslib.as_ctypes(value) elif isinstance(value, bytes): diff --git a/src/nifake/metadata/functions.py b/src/nifake/metadata/functions.py index efed77aad..b5630883b 100644 --- a/src/nifake/metadata/functions.py +++ b/src/nifake/metadata/functions.py @@ -2990,10 +2990,10 @@ ], 'returns': 'ViStatus' }, - 'FunctionWithNumpy3dArrayInputParameter': { + 'FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter': { 'codegen_method': 'public', 'documentation': { - 'description': 'Function that takes a 3D numpy array as an input parameter.' + 'description': 'Function that takes a 3D numpy array of numpy complex128 as an input parameter.' }, 'included_in_proto': False, 'is_error_handling': False, @@ -3002,7 +3002,7 @@ 'documentation_filename': 'numpy_method', 'library_interpreter_filename': 'numpy_write_method', 'method_python_name_suffix': '', - 'session_filename': 'numpy_3d_array_method' + 'session_filename': 'numpy_write_method' } ], 'parameters': [ @@ -3020,9 +3020,9 @@ 'complex_type': 'numpy', 'direction': 'in', 'documentation': { - 'description': 'Specifies the 3D array of complex numbers to write. ' + 'description': 'Specifies the 3D array of numpy complex numbers to write. ' }, - 'name': 'frequency', + 'name': 'multidimensionalArray', 'type': 'NIComplexNumber[]', 'numpy': True, 'use_numpy_array': True, diff --git a/src/nifake/unit_tests/test_library_interpreter.py b/src/nifake/unit_tests/test_library_interpreter.py index b272e65d1..4286bc35c 100644 --- a/src/nifake/unit_tests/test_library_interpreter.py +++ b/src/nifake/unit_tests/test_library_interpreter.py @@ -899,7 +899,7 @@ def test_write_waveform_numpy_complex_interleaved_i16_valid_input(self): _matchers.NIComplexI16PointerMatcher(waveform_data_pointer, number_of_samples) ) - def test_function_with_numpy3d_array_input_parameter(self): + def test_write_3d_numpy_array_of_numpy_complex128(self): from nifake._complextype import NIComplexNumber array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) @@ -909,38 +909,38 @@ def test_function_with_numpy3d_array_input_parameter(self): for i, value in enumerate(flattened_array): complex_array[i] = NIComplexNumber(value.real, value.imag) array_3d_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) - self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with_numpy3d_array_input_parameter(array_3d) - self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.assert_called_once_with( + interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.assert_called_once_with( _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST), _matchers.NIComplexNumberPointerMatcher(array_3d_ptr, number_of_samples) ) - def test_numpy3dcomplexarrayinput_nomemorycopy(self): + def test_no_memorycopy_with_multi_dimensional_numpy_complex128_array(self): array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) - self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.side_effect = self.side_effects_helper.niFake_FunctionWithNumpy3dArrayInputParameter + self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with_numpy3d_array_input_parameter(array_3d) - args, kwargs = self.patched_library.niFake_FunctionWithNumpy3dArrayInputParameter.call_args + interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + args, kwargs = self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.call_args actual_pointer = args[1] - numpy_addr = array_3d.__array_interface__['data'][0] - ctypes_addr = ctypes.addressof(actual_pointer.contents) - assert numpy_addr == ctypes_addr, f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + input_address = array_3d.__array_interface__['data'][0] + address_passed_to_library = ctypes.addressof(actual_pointer.contents) + assert input_address == address_passed_to_library, f"Addresses do NOT match: input_address={input_address}, address_passed_to_library={address_passed_to_library}" - def test_numpy1dcomplexarrayinput_nomemorycopy(self): - waveform_data = numpy.full(1000, 0.707 + 0.707j, dtype=numpy.complex128) + def test_no_memorycopy_with_numpy_complex64_array(self): + array_1d = numpy.full(1000, 0.707 + 0.707j, dtype=numpy.complex64) self.patched_library.niFake_WriteWaveformNumpyComplex64.side_effect = ( self.side_effects_helper.niFake_WriteWaveformNumpyComplex64 ) interpreter = self.get_initialized_library_interpreter() - interpreter.write_waveform_numpy_complex64(waveform_data) + interpreter.write_waveform_numpy_complex64(array_1d) args, kwargs = self.patched_library.niFake_WriteWaveformNumpyComplex64.call_args actual_pointer = args[2] - numpy_addr = waveform_data.__array_interface__['data'][0] - ctypes_addr = ctypes.addressof(actual_pointer.contents) - assert numpy_addr == ctypes_addr, ( - f"Addresses do NOT match: numpy={numpy_addr}, ctypes={ctypes_addr}" + input_address = array_1d.__array_interface__['data'][0] + address_passed_to_library = ctypes.addressof(actual_pointer.contents) + assert input_address == address_passed_to_library, ( + f"Addresses do NOT match: input_address={input_address}, address_passed_to_library={address_passed_to_library}" ) def test_matcher_prints(self): From 951f5581b2830a618bb5059de3e716af77c2540d Mon Sep 17 00:00:00 2001 From: Rahul R Date: Tue, 22 Jul 2025 14:57:08 +0530 Subject: [PATCH 5/6] Updated code review comments. --- .../session.py/numpy_write_method.py.mako | 2 -- build/unit_tests/test_codegen_helper.py | 36 ------------------- .../nifake/nifake/_grpc_stub_interpreter.py | 2 +- .../nifake/nifake/_library_interpreter.py | 2 +- generated/nifake/nifake/session.py | 14 ++++++-- .../unit_tests/test_library_interpreter.py | 8 ++--- generated/nifgen/nifgen/session.py | 12 +++++++ generated/nirfsg/nirfsg/session.py | 6 ++++ src/nifake/metadata/functions.py | 1 + .../unit_tests/test_library_interpreter.py | 8 ++--- 10 files changed, 40 insertions(+), 51 deletions(-) diff --git a/build/templates/session.py/numpy_write_method.py.mako b/build/templates/session.py/numpy_write_method.py.mako index 6b09ef738..36fa97aad 100644 --- a/build/templates/session.py/numpy_write_method.py.mako +++ b/build/templates/session.py/numpy_write_method.py.mako @@ -30,10 +30,8 @@ raise TypeError('${parameter['python_name']} must be in C-order') if ${parameter['python_name']}.dtype is not numpy.dtype('${parameter['numpy_type']}'): raise TypeError('${parameter['python_name']} must be numpy.ndarray of dtype=${parameter['numpy_type']}, is ' + str(${parameter['python_name']}.dtype)) -% if parameter['array_dimension'] > 1: if ${parameter['python_name']}.ndim != ${parameter['array_dimension']}: raise TypeError('${parameter['python_name']} must be numpy.ndarray of dimension=${parameter['array_dimension']}, is ' + str(${parameter['python_name']}.ndim)) -% endif % endfor % for p in helper.filter_parameters(parameters, helper.ParameterUsageOptions.INTERPRETER_METHOD_CALL): % if 'python_api_converter_name' in p: diff --git a/build/unit_tests/test_codegen_helper.py b/build/unit_tests/test_codegen_helper.py index d0cfd5907..4b5f50466 100644 --- a/build/unit_tests/test_codegen_helper.py +++ b/build/unit_tests/test_codegen_helper.py @@ -42,7 +42,6 @@ 'type': 'ViSession', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 1 @@ -72,7 +71,6 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 2 @@ -101,7 +99,6 @@ 'type': 'ViString', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 3 @@ -131,7 +128,6 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 4 @@ -158,7 +154,6 @@ 'type': 'ViInt32', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 5 @@ -187,7 +182,6 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 6 @@ -217,7 +211,6 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 7 @@ -246,7 +239,6 @@ 'type': 'ViInt64', 'numpy': True, 'complex_type': None, - 'array_dimension': 1, 'numpy_type': 'int64', 'numpy_type_library_call': 'numpy.int64', 'use_in_python_api': True, @@ -269,7 +261,6 @@ 'name': 'numberOfElementsPythonCode', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'number_of_elements_python_code', 'python_name_with_default': 'number_of_elements_python_code', 'python_name_with_doc_default': 'number_of_elements_python_code', @@ -296,7 +287,6 @@ 'name': 'input', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'input', 'python_name_with_default': 'input', 'python_name_with_doc_default': 'input', @@ -326,7 +316,6 @@ 'name': 'inputArray', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'input_array', 'python_name_with_default': 'input_array=None', 'python_name_with_doc_default': 'input_array=None', @@ -353,7 +342,6 @@ 'name': 'inputArraySize', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'input_array_size', 'python_name_with_default': 'input_array_size', 'python_name_with_doc_default': 'input_array_size', @@ -380,7 +368,6 @@ 'name': 'stringSize', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'string_size', 'python_name_with_default': 'string_size', 'python_name_with_doc_default': 'string_size', @@ -407,7 +394,6 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -435,7 +421,6 @@ 'name': 'Timeout', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'timeout', 'python_name_with_default': 'timeout=1.0', 'python_name_with_doc_default': 'timeout=1.0', @@ -465,7 +450,6 @@ 'name': 'channelList', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'original_type': 'ViChar[]', 'python_name': 'channel_list', 'python_name_with_default': 'channel_list', @@ -493,7 +477,6 @@ 'name': 'aString', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_string', 'python_name_with_default': 'a_string', 'python_name_with_doc_default': 'a_string', @@ -527,7 +510,6 @@ 'type': 'custom_struct', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 18 @@ -558,7 +540,6 @@ 'type': 'ViInt16', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 19 @@ -579,7 +560,6 @@ 'name': 'aString2', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_string_2', 'python_name_with_default': 'a_string_2', 'python_name_with_doc_default': 'a_string_2', @@ -606,7 +586,6 @@ 'name': 'aStrin3g', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_string_3', 'python_name_with_default': 'a_string_3', 'python_name_with_doc_default': 'a_string_3', @@ -633,7 +612,6 @@ 'name': 'aStringTwist', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_string_twist', 'python_name_with_default': 'a_string_twist', 'python_name_with_doc_default': 'a_string_twist', @@ -669,7 +647,6 @@ 'type': 'ViInt64', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, { # 23 @@ -690,7 +667,6 @@ 'name': 'stringSizeTwist', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'string_size_twist', 'python_name_with_default': 'string_size_twist', 'python_name_with_doc_default': 'string_size_twist', @@ -717,7 +693,6 @@ 'name': 'aBufferArray', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_buffer_array', 'python_name_with_default': 'a_buffer_array', 'python_name_with_doc_default': 'a_buffer_array', @@ -746,7 +721,6 @@ 'name': 'aBufferList', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_buffer_list', 'python_name_with_default': 'a_buffer_list', 'python_name_with_doc_default': 'a_buffer_list', @@ -775,7 +749,6 @@ 'name': 'aBufferTwistArray', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_buffer_twist_array', 'python_name_with_default': 'a_buffer_twist_array', 'python_name_with_doc_default': 'a_buffer_twist_array', @@ -804,7 +777,6 @@ 'name': 'aBufferTwistList', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_buffer_twist_list', 'python_name_with_default': 'a_buffer_twist_list', 'python_name_with_doc_default': 'a_buffer_twist_list', @@ -836,7 +808,6 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', 'python_name_with_doc_default': 'input_array_2=None', @@ -866,7 +837,6 @@ 'name': 'inputArray2', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_2', 'python_name_with_default': 'input_array_2=None', @@ -897,7 +867,6 @@ 'name': 'inputArray3', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_3', 'python_name_with_default': 'input_array_3=None', @@ -928,7 +897,6 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -959,7 +927,6 @@ 'name': 'inputArray4', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_api_converter_name': 'convert_to_nitclk_session_num_list', 'python_name': 'input_array_4', 'python_name_with_default': 'input_array_4=None', @@ -987,7 +954,6 @@ 'name': 'aStringEnum', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'python_name': 'a_string_enum', 'python_name_with_default': 'a_string_enum', 'python_name_with_doc_default': 'a_string_enum', @@ -1016,7 +982,6 @@ 'name': 'indices', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'original_type': 'ViChar[]', 'python_api_converter_name': 'convert_repeated_capabilities_without_prefix', 'python_name': 'indices', @@ -1054,7 +1019,6 @@ 'type': 'ViInt8', 'numpy': False, 'complex_type': None, - 'array_dimension': 1, 'use_in_python_api': True, }, ] diff --git a/generated/nifake/nifake/_grpc_stub_interpreter.py b/generated/nifake/nifake/_grpc_stub_interpreter.py index 3ced5bc30..b9e7617da 100644 --- a/generated/nifake/nifake/_grpc_stub_interpreter.py +++ b/generated/nifake/nifake/_grpc_stub_interpreter.py @@ -144,7 +144,7 @@ def fetch_waveform(self, number_of_samples): # noqa: N802 def fetch_waveform_into(self, number_of_samples): # noqa: N802 raise NotImplementedError('numpy-specific methods are not supported over gRPC') - def function_with3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): # noqa: N802 + def function_with_3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): # noqa: N802 raise NotImplementedError('numpy-specific methods are not supported over gRPC') def function_with_intflag_parameter(self, flag): # noqa: N802 diff --git a/generated/nifake/nifake/_library_interpreter.py b/generated/nifake/nifake/_library_interpreter.py index 487ae0f4d..da7e3881a 100644 --- a/generated/nifake/nifake/_library_interpreter.py +++ b/generated/nifake/nifake/_library_interpreter.py @@ -222,7 +222,7 @@ def fetch_waveform_into(self, waveform_data): # noqa: N802 errors.handle_error(self, error_code, ignore_warnings=False, is_error_handling=False) return - def function_with3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): # noqa: N802 + def function_with_3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): # noqa: N802 vi_ctype = _visatype.ViSession(self._vi) # case S110 multidimensional_array_ctype = _get_ctypes_pointer_for_buffer(value=multidimensional_array, library_type=_complextype.NIComplexNumber) # case B510 error_code = self._library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter(vi_ctype, multidimensional_array_ctype) diff --git a/generated/nifake/nifake/session.py b/generated/nifake/nifake/session.py index 3a09ae79c..69e02ad1e 100644 --- a/generated/nifake/nifake/session.py +++ b/generated/nifake/nifake/session.py @@ -945,8 +945,8 @@ def fetch_waveform_into(self, waveform_data): raise TypeError('waveform_data must be numpy.ndarray of dtype=float64, is ' + str(waveform_data.dtype)) self._interpreter.fetch_waveform_into(waveform_data) - def function_with3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): - r'''function_with3d_numpy_array_of_numpy_complex128_input_parameter + def function_with_3d_numpy_array_of_numpy_complex128_input_parameter(self, multidimensional_array): + r'''function_with_3d_numpy_array_of_numpy_complex128_input_parameter Method that takes a 3D numpy array of numpy complex128 as an input parameter. @@ -964,7 +964,7 @@ def function_with3d_numpy_array_of_numpy_complex128_input_parameter(self, multid raise TypeError('multidimensional_array must be numpy.ndarray of dtype=complex128, is ' + str(multidimensional_array.dtype)) if multidimensional_array.ndim != 3: raise TypeError('multidimensional_array must be numpy.ndarray of dimension=3, is ' + str(multidimensional_array.ndim)) - self._interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(multidimensional_array) + self._interpreter.function_with_3d_numpy_array_of_numpy_complex128_input_parameter(multidimensional_array) @ivi_synchronized def function_with_intflag_parameter(self, flag): @@ -1703,6 +1703,8 @@ def write_waveform_numpy(self, waveform): raise TypeError('waveform must be in C-order') if waveform.dtype is not numpy.dtype('float64'): raise TypeError('waveform must be numpy.ndarray of dtype=float64, is ' + str(waveform.dtype)) + if waveform.ndim != 1: + raise TypeError('waveform must be numpy.ndarray of dimension=1, is ' + str(waveform.ndim)) self._interpreter.write_waveform_numpy(waveform) @ivi_synchronized @@ -1723,6 +1725,8 @@ def write_waveform_numpy_complex128(self, waveform_data_array): raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('complex128'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=complex128, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) self._interpreter.write_waveform_numpy_complex128(waveform_data_array) @ivi_synchronized @@ -1743,6 +1747,8 @@ def write_waveform_numpy_complex64(self, waveform_data_array): raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('complex64'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=complex64, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) self._interpreter.write_waveform_numpy_complex64(waveform_data_array) @ivi_synchronized @@ -1763,6 +1769,8 @@ def write_waveform_numpy_complex_interleaved_i16(self, waveform_data_array): raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('int16'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=int16, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) self._interpreter.write_waveform_numpy_complex_interleaved_i16(waveform_data_array) def _close(self): diff --git a/generated/nifake/nifake/unit_tests/test_library_interpreter.py b/generated/nifake/nifake/unit_tests/test_library_interpreter.py index 4286bc35c..45cfc7dc2 100644 --- a/generated/nifake/nifake/unit_tests/test_library_interpreter.py +++ b/generated/nifake/nifake/unit_tests/test_library_interpreter.py @@ -908,20 +908,20 @@ def test_write_3d_numpy_array_of_numpy_complex128(self): complex_array = (NIComplexNumber * len(flattened_array))() for i, value in enumerate(flattened_array): complex_array[i] = NIComplexNumber(value.real, value.imag) - array_3d_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) + flattened_array_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + interpreter.function_with_3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.assert_called_once_with( _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST), - _matchers.NIComplexNumberPointerMatcher(array_3d_ptr, number_of_samples) + _matchers.NIComplexNumberPointerMatcher(flattened_array_ptr, number_of_samples) ) def test_no_memorycopy_with_multi_dimensional_numpy_complex128_array(self): array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + interpreter.function_with_3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) args, kwargs = self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.call_args actual_pointer = args[1] input_address = array_3d.__array_interface__['data'][0] diff --git a/generated/nifgen/nifgen/session.py b/generated/nifgen/nifgen/session.py index 4c381e760..0edd4dec4 100644 --- a/generated/nifgen/nifgen/session.py +++ b/generated/nifgen/nifgen/session.py @@ -1703,6 +1703,8 @@ def _create_waveform_f64_numpy(self, waveform_data_array): raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('float64'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=float64, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) waveform_handle = self._interpreter.create_waveform_f64_numpy(self._repeated_capability, waveform_data_array) return waveform_handle @@ -1876,6 +1878,8 @@ def _create_waveform_i16_numpy(self, waveform_data_array): raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('int16'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=int16, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) waveform_handle = self._interpreter.create_waveform_i16_numpy(self._repeated_capability, waveform_data_array) return waveform_handle @@ -2687,6 +2691,8 @@ def _write_binary16_waveform_numpy(self, waveform_handle, data): raise TypeError('data must be in C-order') if data.dtype is not numpy.dtype('int16'): raise TypeError('data must be numpy.ndarray of dtype=int16, is ' + str(data.dtype)) + if data.ndim != 1: + raise TypeError('data must be numpy.ndarray of dimension=1, is ' + str(data.ndim)) self._interpreter.write_binary16_waveform_numpy(self._repeated_capability, waveform_handle, data) @ivi_synchronized @@ -2781,6 +2787,8 @@ def _write_named_waveform_f64_numpy(self, waveform_name, data): raise TypeError('data must be in C-order') if data.dtype is not numpy.dtype('float64'): raise TypeError('data must be numpy.ndarray of dtype=float64, is ' + str(data.dtype)) + if data.ndim != 1: + raise TypeError('data must be numpy.ndarray of dimension=1, is ' + str(data.ndim)) self._interpreter.write_named_waveform_f64_numpy(self._repeated_capability, waveform_name, data) @ivi_synchronized @@ -2824,6 +2832,8 @@ def _write_named_waveform_i16_numpy(self, waveform_name, data): raise TypeError('data must be in C-order') if data.dtype is not numpy.dtype('int16'): raise TypeError('data must be numpy.ndarray of dtype=int16, is ' + str(data.dtype)) + if data.ndim != 1: + raise TypeError('data must be numpy.ndarray of dimension=1, is ' + str(data.ndim)) self._interpreter.write_named_waveform_i16_numpy(self._repeated_capability, waveform_name, data) @ivi_synchronized @@ -2947,6 +2957,8 @@ def _write_waveform_numpy(self, waveform_handle, data): raise TypeError('data must be in C-order') if data.dtype is not numpy.dtype('float64'): raise TypeError('data must be numpy.ndarray of dtype=float64, is ' + str(data.dtype)) + if data.ndim != 1: + raise TypeError('data must be numpy.ndarray of dimension=1, is ' + str(data.ndim)) self._interpreter.write_waveform_numpy(self._repeated_capability, waveform_handle, data) @ivi_synchronized diff --git a/generated/nirfsg/nirfsg/session.py b/generated/nirfsg/nirfsg/session.py index a420436c5..b4c02b02b 100644 --- a/generated/nirfsg/nirfsg/session.py +++ b/generated/nirfsg/nirfsg/session.py @@ -8217,6 +8217,8 @@ def _write_arb_waveform_complex_f32(self, waveform_name, waveform_data_array, mo raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('complex64'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=complex64, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) self._interpreter.write_arb_waveform_complex_f32(waveform_name, waveform_data_array, more_data_pending) def _write_arb_waveform_complex_f64(self, waveform_name, waveform_data_array, more_data_pending): @@ -8255,6 +8257,8 @@ def _write_arb_waveform_complex_f64(self, waveform_name, waveform_data_array, mo raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('complex128'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=complex128, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) self._interpreter.write_arb_waveform_complex_f64(waveform_name, waveform_data_array, more_data_pending) def _write_arb_waveform_complex_i16(self, waveform_name, waveform_data_array): @@ -8288,6 +8292,8 @@ def _write_arb_waveform_complex_i16(self, waveform_name, waveform_data_array): raise TypeError('waveform_data_array must be in C-order') if waveform_data_array.dtype is not numpy.dtype('int16'): raise TypeError('waveform_data_array must be numpy.ndarray of dtype=int16, is ' + str(waveform_data_array.dtype)) + if waveform_data_array.ndim != 1: + raise TypeError('waveform_data_array must be numpy.ndarray of dimension=1, is ' + str(waveform_data_array.ndim)) self._interpreter.write_arb_waveform_complex_i16(waveform_name, waveform_data_array) def write_arb_waveform(self, waveform_name, waveform_data_array, more_data_pending=False): diff --git a/src/nifake/metadata/functions.py b/src/nifake/metadata/functions.py index b5630883b..1e0933dee 100644 --- a/src/nifake/metadata/functions.py +++ b/src/nifake/metadata/functions.py @@ -3030,6 +3030,7 @@ 'array_dimension': 3 }, ], + 'python_name': 'function_with_3d_numpy_array_of_numpy_complex128_input_parameter', 'returns': 'ViStatus', 'use_session_lock': False }, diff --git a/src/nifake/unit_tests/test_library_interpreter.py b/src/nifake/unit_tests/test_library_interpreter.py index 4286bc35c..45cfc7dc2 100644 --- a/src/nifake/unit_tests/test_library_interpreter.py +++ b/src/nifake/unit_tests/test_library_interpreter.py @@ -908,20 +908,20 @@ def test_write_3d_numpy_array_of_numpy_complex128(self): complex_array = (NIComplexNumber * len(flattened_array))() for i, value in enumerate(flattened_array): complex_array[i] = NIComplexNumber(value.real, value.imag) - array_3d_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) + flattened_array_ptr = ctypes.cast(complex_array, ctypes.POINTER(NIComplexNumber)) self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + interpreter.function_with_3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.assert_called_once_with( _matchers.ViSessionMatcher(SESSION_NUM_FOR_TEST), - _matchers.NIComplexNumberPointerMatcher(array_3d_ptr, number_of_samples) + _matchers.NIComplexNumberPointerMatcher(flattened_array_ptr, number_of_samples) ) def test_no_memorycopy_with_multi_dimensional_numpy_complex128_array(self): array_3d = numpy.full((2, 3, 4), 1.0 + 2.0j, dtype=numpy.complex128) self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.side_effect = self.side_effects_helper.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter interpreter = self.get_initialized_library_interpreter() - interpreter.function_with3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) + interpreter.function_with_3d_numpy_array_of_numpy_complex128_input_parameter(array_3d) args, kwargs = self.patched_library.niFake_FunctionWith3dNumpyArrayOfNumpyComplex128InputParameter.call_args actual_pointer = args[1] input_address = array_3d.__array_interface__['data'][0] From f3488beb32e56924b3046fd8eeb892dda96dd575 Mon Sep 17 00:00:00 2001 From: Rahul R Date: Wed, 23 Jul 2025 11:19:11 +0530 Subject: [PATCH 6/6] consistency in description of arb waveform --- generated/nifake/nifake/session.py | 2 +- src/nifake/metadata/functions.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/generated/nifake/nifake/session.py b/generated/nifake/nifake/session.py index 69e02ad1e..eb4627054 100644 --- a/generated/nifake/nifake/session.py +++ b/generated/nifake/nifake/session.py @@ -1711,7 +1711,7 @@ def write_waveform_numpy(self, waveform): def write_waveform_numpy_complex128(self, waveform_data_array): r'''write_waveform_numpy_complex128 - A method that writes a waveform of numpy complex128 numbers + A method that writes a waveform of numpy complex128 numbers. Args: waveform_data_array (numpy.array(dtype=numpy.complex128)): Specifies the array of data to load into the waveform. Array should be numberOfSamples big. diff --git a/src/nifake/metadata/functions.py b/src/nifake/metadata/functions.py index 1e0933dee..0b45a5fd6 100644 --- a/src/nifake/metadata/functions.py +++ b/src/nifake/metadata/functions.py @@ -2883,7 +2883,7 @@ 'WriteWaveformNumpyComplex128': { 'codegen_method': 'public', 'documentation': { - 'description': 'A function that writes a waveform of numpy complex128 numbers' + 'description': 'A function that writes a waveform of numpy complex128 numbers.' }, 'included_in_proto': False, 'is_error_handling': False,