Session name conflicts between drivers are reported with error code 1, which is ambiguous
bkeryan opened this issue · comments
If the session name passed to a session creation RPC (like nidaqmx CreateTask or RF/MI Initialize RPCs) is used by a different driver, the grpc-device server returns error code 1 as a driver API error. However, looking up this error code using the driver API's error message function causes the example programs to displays "Warning: 1" or an inappropriate error message like "Command requires GPIB Controller to be Controller-In-Charge."
Steps to reproduce:
- Change
examples/nidcpower/measure-record.py
to setSESSION_NAME = "my task"
- Run
examples/nidcpower/measure-record.py
, then while it is running, runexamples/nidaqmx/analog-input.py
:
(.venv) PS Z:\grpc-device\examples\nidaqmx> python .\analog-input.py
Traceback (most recent call last):
File ".\analog-input.py", line 77, in <module>
raise_if_error(response)
File ".\analog-input.py", line 63, in raise_if_error
raise Exception(f"Error: {response.error_string}")
Exception: Error: Command requires GPIB Controller to be Controller-In-Charge.
- Restart the grpc-device server.
- Add
time.sleep(60.0)
to the nidaqmx example. - Run the nidaqmx example, then while it is running, run the nidcpower example:
(.venv) PS Z:\grpc-device\examples\nidcpower> python .\measure-record.py
Warning: 1
Traceback (most recent call last):
File ".\measure-record.py", line 107, in <module>
check_for_error(vi, configure_measure_when.status)
File ".\measure-record.py", line 68, in check_for_error
raise Exception(error_message_response.error_message)
Exception: IVI: The session handle is not valid.
It didn't create a NI-DCPower session, but the example program kept going because it reported error code 1 as a warning.
Note that NI software already uses error code 1 for two different error messages:
In my opinion, the grpc-device server should report this error in one of two ways:
- Return a gRPC status code of
GRPC_STATUS_INVALID_ARGUMENT
- Return a driver API error code with an appropriate error message (such as
niapalerr_invalidParameter
). For RF/MI drivers, it might also make sense to callIvi_SetErrorInfo
so that theGetError
function reflects that the error occurred.
Thanks for catching this! When we address it, I think your first suggestion of returning a gRPC status code of GRPC_STATUS_INVALID_ARGUMENT
makes sense. I think we've typically tried to keep the status
field on the response message tied to warnings/errors coming from a driver call and any grpc-device related errors tied to the returned gRPC status code.
Also, there's a precedence with returning this specific gRPC status code if the user doesn't specify a value for Enum fields: https://github.com/ni/grpc-device/blob/main/generated/nidaqmx/nidaqmx_service.cpp#L222
@bkeryan , do you mind validating / closing this when you get a chance? I'll leave it to you if you want to validate from main or trust my manual testing in the PR.
Validated against main branch using the validate_examples.py script. Trying to reproduce in either order produced the new exception/error message from the examples:
-> Running example: analog-input.py
The session name "my task" is being used by a different driver.
-> Running example: measure-record.py
The session name "my task" is being used by a different driver.