From 0886d0dee6788ead296ab1040225979f02762f11 Mon Sep 17 00:00:00 2001 From: "Jens H. Nielsen" Date: Sat, 6 Aug 2022 07:43:44 +0200 Subject: [PATCH 1/5] rename basel drivers to be consistent --- qcodes/instrument_drivers/basel/BaselSP983.py | 80 ++++++++++++ .../instrument_drivers/basel/BaselSP983a.py | 119 ++++++++++++++++++ .../instrument_drivers/basel/BaselSP983c.py | 17 +++ qcodes/instrument_drivers/basel/__init__.py | 5 + qcodes/instrument_drivers/basel/sp983c.py | 73 +---------- .../instrument_drivers/basel/sp983c_remote.py | 110 +--------------- 6 files changed, 231 insertions(+), 173 deletions(-) create mode 100644 qcodes/instrument_drivers/basel/BaselSP983.py create mode 100644 qcodes/instrument_drivers/basel/BaselSP983a.py create mode 100644 qcodes/instrument_drivers/basel/BaselSP983c.py diff --git a/qcodes/instrument_drivers/basel/BaselSP983.py b/qcodes/instrument_drivers/basel/BaselSP983.py new file mode 100644 index 00000000000..267811f1fd5 --- /dev/null +++ b/qcodes/instrument_drivers/basel/BaselSP983.py @@ -0,0 +1,80 @@ +from typing import Any, Dict, Optional + +from qcodes.instrument.base import Instrument +from qcodes.parameters import DelegateParameter, Parameter +from qcodes.validators import Enum, Numbers + + +class BaselSP983(Instrument): + """ + A virtual driver for the Basel SP 983 and SP 983c current to voltage + converter. + + This driver supports both the SP 983 and SP 983c models. These differ only + in their handling of input offset voltage. It is the responsibility of the + user to capture the input offset, (from the voltage supply) and compensate + that as needed for SP 983. For SP 983c model, 'input_offset_voltage' + argument can be used to set up offset (This doesn't work for SP 983c01 + model). + + Note that, as this is a purely virtual driver, there is no support + for the remote control interface (SP 983a). It is the responsibility of + the user to ensure that values set here are in accordance with the values + set on the instrument. + + Args: + name + input_offset_voltage: (Optional) A source input offset voltage + parameter. The range for input is -10 to 10 Volts and it is + user's responsibility to ensure this. This source parameter is + used to set offset voltage parameter of the preamp and the + source parameter should represent a voltage source that is + connected to the "Offset Input Voltage" connector of the SP983C. + """ + + def __init__( + self, name: str, input_offset_voltage: Optional[Parameter] = None, **kwargs: Any + ): + super().__init__(name, **kwargs) + + self.add_parameter( + "gain", + initial_value=1e8, + label="Gain", + unit="V/A", + get_cmd=None, + set_cmd=None, + vals=Enum(1e09, 1e08, 1e07, 1e06, 1e05), + ) + + self.add_parameter( + "fcut", + initial_value=1e3, + label="Cutoff frequency", + unit="Hz", + get_cmd=None, + set_cmd=None, + vals=Enum(30.0, 100.0, 300.0, 1e3, 3e3, 10e3, 30e3, 100e3, 1e6), + ) + + self.add_parameter( + "offset_voltage", + label="Offset Voltage", + unit="V", + vals=Numbers(-0.1, 0.1), + scale=100, + source=input_offset_voltage, + parameter_class=DelegateParameter, + ) + + def get_idn(self) -> Dict[str, Optional[str]]: + vendor = "Physics Basel" + model = "SP 983" + serial = None + firmware = None + return { + "vendor": vendor, + "model": model, + "serial": serial, + "firmware": firmware, + } diff --git a/qcodes/instrument_drivers/basel/BaselSP983a.py b/qcodes/instrument_drivers/basel/BaselSP983a.py new file mode 100644 index 00000000000..f4ce82186cf --- /dev/null +++ b/qcodes/instrument_drivers/basel/BaselSP983a.py @@ -0,0 +1,119 @@ +from typing import Any, Dict, Optional + +import numpy as np + +from qcodes import validators as vals +from qcodes.instrument import VisaInstrument +from qcodes.parameters import DelegateParameter, Parameter + + +class BaselSP983a(VisaInstrument): + """ + A driver for Basel Preamp's (SP983a) Remote Instrument - Model SP983a. + + Args: + name: name for your instrument driver instance + address: address of the connected remote controller of basel preamp + input_offset_voltage: (Optional) A source input offset voltage + parameter. The range for input is -10 to 10 Volts and it is + user's responsibility to ensure this. This source parameter is + used to set offset voltage parameter of the preamp and the + source parameter should represent a voltage source that is + connected to the "Offset Input Volgate" connector of the SP983C. + """ + + def __init__( + self, + name: str, + address: str, + input_offset_voltage: Optional[Parameter] = None, + terminator: str = "\r\n", + **kwargs: Any, + ) -> None: + super().__init__(name, address, terminator=terminator, **kwargs) + + self.connect_message() + + self.add_parameter( + "gain", + label="Gain", + unit="V/A", + set_cmd=self._set_gain, + get_cmd=self._get_gain, + vals=vals.Enum(1e5, 1e6, 1e7, 1e8, 1e9), + ) + self.add_parameter( + "fcut", + unit="Hz", + label="Filter Cut-Off Frequency", + get_cmd=self._get_filter, + get_parser=self._parse_filter_value, + set_cmd=self._set_filter, + val_mapping={ + 30: "30", + 100: "100", + 300: "300", + 1000: "1k", + 3000: "3k", + 10e3: "10k", + 30e3: "30k", + 100e3: "100k", + 1e6: "FULL", + }, + ) + self.add_parameter( + "overload_status", label="Overload Status", set_cmd=False, get_cmd="GET O" + ) + + self.add_parameter( + "offset_voltage", + label="Offset Voltage for SP983C", + unit="V", + vals=vals.Numbers(-0.1, 0.1), + scale=100, + source=input_offset_voltage, + parameter_class=DelegateParameter, + ) + + def get_idn(self) -> Dict[str, Optional[str]]: + vendor = "Physics Basel" + model = "SP 983A" + serial = None + firmware = None + return { + "vendor": vendor, + "model": model, + "serial": serial, + "firmware": firmware, + } + + def _set_gain(self, value: float) -> None: + r = self.ask(f"SET G 1E{int(np.log10(value))}") + if r != "OK": + raise ValueError(f"Expected OK return but got: {r}") + + def _get_gain(self) -> float: + s = self.ask("GET G") + r = s.split("Gain: ")[1] + return float(r) + + def _set_filter(self, value: str) -> None: + r = self.ask(f"SET F {value}") + if r != "OK": + raise ValueError(f"Expected OK return but got: {r}") + + def _get_filter(self) -> str: + s = self.ask("GET F") + return s.split("Filter: ")[1] + + @staticmethod + def _parse_filter_value(val: str) -> str: + if val.startswith("F"): + return "FULL" + elif val[-3::] == "kHz": + return str(int(val[0:-3])) + "k" + + elif val[-2::] == "Hz": + return str(int(val[0:-2])) + else: + raise ValueError(f"Could not interpret result. Got: {val}") diff --git a/qcodes/instrument_drivers/basel/BaselSP983c.py b/qcodes/instrument_drivers/basel/BaselSP983c.py new file mode 100644 index 00000000000..3677b0d7648 --- /dev/null +++ b/qcodes/instrument_drivers/basel/BaselSP983c.py @@ -0,0 +1,17 @@ +from typing import Dict, Optional + +from .BaselSP983 import BaselSP983 + + +class BaselSP983c(BaselSP983): + def get_idn(self) -> Dict[str, Optional[str]]: + vendor = "Physics Basel" + model = "SP 983c" + serial = None + firmware = None + return { + "vendor": vendor, + "model": model, + "serial": serial, + "firmware": firmware, + } diff --git a/qcodes/instrument_drivers/basel/__init__.py b/qcodes/instrument_drivers/basel/__init__.py index e69de29bb2d..6df099eb176 100644 --- a/qcodes/instrument_drivers/basel/__init__.py +++ b/qcodes/instrument_drivers/basel/__init__.py @@ -0,0 +1,5 @@ +from .BaselSP983 import BaselSP983 +from .BaselSP983a import BaselSP983a +from .BaselSP983c import BaselSP983c + +__all__ = ["BaselSP983a", "BaselSP983c", "BaselSP983"] diff --git a/qcodes/instrument_drivers/basel/sp983c.py b/qcodes/instrument_drivers/basel/sp983c.py index cc720a3ee44..4b92c3caad8 100644 --- a/qcodes/instrument_drivers/basel/sp983c.py +++ b/qcodes/instrument_drivers/basel/sp983c.py @@ -1,69 +1,6 @@ -from typing import Any, Dict, Optional +""" +Legacy module kept around for backwards compatibility reasons. +Will eventually be deprecated and removed -from qcodes.instrument.base import Instrument -from qcodes.parameters import DelegateParameter, Parameter -from qcodes.validators import Enum, Numbers - - -class SP983C(Instrument): - """ - A virtual driver for the Basel SP 983 and SP 983C current to voltage - converter. - - This driver supports both the SP 983 and SP 983C models. These differ only - in their handling of input offset voltage. It is the responsibility of the - user to capture the input offset, (from the voltage supply) and compensate - that as needed for SP 983. For SP 983C model, 'input_offset_voltage' - argument can be used to set up offset (This doesn't work for SP 983c01 - model). - - Note that, as this is a purely virtual driver, there is no support - for the the remote control interface (SP 983a). It is the responsibility of - the user to ensure that values set here are in accordance with the values - set on the instrument. - - Args: - name - input_offset_voltage: (Optional) A source input offset voltage - parameter. The range for input is -10 to 10 Volts and it is - user's responsibility to ensure this. This source parameter is - used to set offset voltage parameter of the preamp and the - source parameter should represent a voltage source that is - connected to the "Offset Input Volgate" connector of the SP983C. - """ - - def __init__(self, name: str, - input_offset_voltage: Optional[Parameter] = None, - **kwargs: Any): - super().__init__(name, **kwargs) - - self.add_parameter('gain', - initial_value=1e8, - label='Gain', - unit='V/A', - get_cmd=None, set_cmd=None, - vals=Enum(1e09, 1e08, 1e07, 1e06, 1e05)) - - self.add_parameter('fcut', - initial_value=1e3, - label='Cutoff frequency', - unit='Hz', - get_cmd=None, set_cmd=None, - vals=Enum(30., 100., 300., 1e3, 3e3, 10e3, 30e3, - 100e3, 1e6)) - - self.add_parameter('offset_voltage', - label="Offset Voltage", - unit='V', - vals=Numbers(-0.1, 0.1), - scale=100, - source=input_offset_voltage, - parameter_class=DelegateParameter) - - def get_idn(self) -> Dict[str, Optional[str]]: - vendor = 'Physics Basel' - model = 'SP 983(c)' - serial = None - firmware = None - return {'vendor': vendor, 'model': model, - 'serial': serial, 'firmware': firmware} +""" +from .BaselSP983c import BaselSP983c as SP983C diff --git a/qcodes/instrument_drivers/basel/sp983c_remote.py b/qcodes/instrument_drivers/basel/sp983c_remote.py index 069b6a03f51..d2e53479604 100644 --- a/qcodes/instrument_drivers/basel/sp983c_remote.py +++ b/qcodes/instrument_drivers/basel/sp983c_remote.py @@ -1,106 +1,6 @@ -from typing import Any, Dict, Optional +""" +Legacy module kept around for backwards compatibility reasons. +Will eventually be deprecated and removed -import numpy as np - -from qcodes import validators as vals -from qcodes.instrument import VisaInstrument -from qcodes.parameters import DelegateParameter, Parameter - - -class SP983A(VisaInstrument): - """ - A driver for Basel Preamp's (SP983C) Remote Instrument - Model SP983A. - - Args: - name: name for your instrument driver instance - address: address of the connected remote controller of basel preamp - input_offset_voltage: (Optional) A source input offset voltage - parameter. The range for input is -10 to 10 Volts and it is - user's responsibility to ensure this. This source parameter is - used to set offset voltage parameter of the preamp and the - source parameter should represent a voltage source that is - connected to the "Offset Input Volgate" connector of the SP983C. - """ - def __init__(self, - name: str, - address: str, - input_offset_voltage: Optional[Parameter] = None, - terminator: str = "\r\n", - **kwargs: Any) -> None: - super().__init__(name, address, terminator=terminator, **kwargs) - - self.connect_message() - - self.add_parameter( - "gain", - label="Gain", - unit="V/A", - set_cmd=self._set_gain, - get_cmd=self._get_gain, - vals=vals.Enum(1e5, 1e6, 1e7, 1e8, 1e9), - ) - self.add_parameter( - "fcut", - unit="Hz", - label="Filter Cut-Off Frequency", - get_cmd=self._get_filter, - get_parser=self._parse_filter_value, - set_cmd=self._set_filter, - val_mapping={30: '30', 100: '100', 300: '300', 1000: '1k', - 3000: '3k', 10e3: '10k', 30e3: '30k', - 100e3: '100k', 1e6: 'FULL'}, - ) - self.add_parameter( - "overload_status", - label="Overload Status", - set_cmd=False, - get_cmd="GET O" - ) - - self.add_parameter( - "offset_voltage", - label="Offset Voltage for SP983C", - unit="V", - vals=vals.Numbers(-0.1, 0.1), - scale=100, - source=input_offset_voltage, - parameter_class=DelegateParameter) - - def get_idn(self) -> Dict[str, Optional[str]]: - vendor = 'Physics Basel' - model = 'SP 983A' - serial = None - firmware = None - return {'vendor': vendor, 'model': model, - 'serial': serial, 'firmware': firmware} - - def _set_gain(self, value: float) -> None: - r = self.ask(f"SET G 1E{int(np.log10(value))}") - if r != "OK": - raise ValueError(f"Expected OK return but got: {r}") - - def _get_gain(self) -> float: - s = self.ask("GET G") - r = s.split("Gain: ")[1] - return float(r) - - def _set_filter(self, value: str) -> None: - r = self.ask(f"SET F {value}") - if r != "OK": - raise ValueError(f"Expected OK return but got: {r}") - - def _get_filter(self) -> str: - s = self.ask("GET F") - return s.split("Filter: ")[1] - - @staticmethod - def _parse_filter_value(val: str) -> str: - if val.startswith("F"): - return "FULL" - elif val[-3::] == "kHz": - return str(int(val[0:-3]))+'k' - - elif val[-2::] == "Hz": - return str(int(val[0:-2])) - else: - raise ValueError(f"Could not interpret result. Got: {val}") +""" +from .BaselSP983a import BaselSP983a as SP983A From 68e06896b3fee254069465e1b43312a115a745fb Mon Sep 17 00:00:00 2001 From: "Jens H. Nielsen" Date: Sat, 6 Aug 2022 08:06:10 +0200 Subject: [PATCH 2/5] Better docstrings --- qcodes/instrument_drivers/basel/BaselSP983.py | 5 ++-- .../instrument_drivers/basel/BaselSP983c.py | 25 +++++++++++++++++++ 2 files changed, 27 insertions(+), 3 deletions(-) diff --git a/qcodes/instrument_drivers/basel/BaselSP983.py b/qcodes/instrument_drivers/basel/BaselSP983.py index 267811f1fd5..b7b98afd5c7 100644 --- a/qcodes/instrument_drivers/basel/BaselSP983.py +++ b/qcodes/instrument_drivers/basel/BaselSP983.py @@ -1,14 +1,13 @@ from typing import Any, Dict, Optional -from qcodes.instrument.base import Instrument +from qcodes.instrument import Instrument from qcodes.parameters import DelegateParameter, Parameter from qcodes.validators import Enum, Numbers class BaselSP983(Instrument): """ - A virtual driver for the Basel SP 983 and SP 983c current to voltage - converter. + A virtual driver for the Basel SP 983 current to voltage converter. This driver supports both the SP 983 and SP 983c models. These differ only in their handling of input offset voltage. It is the responsibility of the diff --git a/qcodes/instrument_drivers/basel/BaselSP983c.py b/qcodes/instrument_drivers/basel/BaselSP983c.py index 3677b0d7648..369e2713e58 100644 --- a/qcodes/instrument_drivers/basel/BaselSP983c.py +++ b/qcodes/instrument_drivers/basel/BaselSP983c.py @@ -4,6 +4,31 @@ class BaselSP983c(BaselSP983): + """ + A virtual driver for the Basel SP 983c current to voltage converter. + + This driver supports both the SP 983 and SP 983c models. These differ only + in their handling of input offset voltage. It is the responsibility of the + user to capture the input offset, (from the voltage supply) and compensate + that as needed for SP 983. For SP 983c model, 'input_offset_voltage' + argument can be used to set up offset (This doesn't work for SP 983c01 + model). + + Note that, as this is a purely virtual driver, there is no support + for the remote control interface (SP 983a). It is the responsibility of + the user to ensure that values set here are in accordance with the values + set on the instrument. + + Args: + name + input_offset_voltage: (Optional) A source input offset voltage + parameter. The range for input is -10 to 10 Volts and it is + user's responsibility to ensure this. This source parameter is + used to set offset voltage parameter of the preamp and the + source parameter should represent a voltage source that is + connected to the "Offset Input Voltage" connector of the SP983C. + """ + def get_idn(self) -> Dict[str, Optional[str]]: vendor = "Physics Basel" model = "SP 983c" From 90f5435f71cd0c9d7a44eaddd8bcb96bf75f1839 Mon Sep 17 00:00:00 2001 From: "Jens H. Nielsen" Date: Sat, 6 Aug 2022 08:06:32 +0200 Subject: [PATCH 3/5] Add new api docs for basel --- docs/drivers_api/Basel.rst | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 docs/drivers_api/Basel.rst diff --git a/docs/drivers_api/Basel.rst b/docs/drivers_api/Basel.rst new file mode 100644 index 00000000000..ee9494b3e8a --- /dev/null +++ b/docs/drivers_api/Basel.rst @@ -0,0 +1,7 @@ +.. _Basel_api : + +Basel Drivers +============= + +.. automodule:: qcodes.instrument_drivers.basel + :autosummary: From 681523ea3c46bb4762b843107f5e5c9c6f07fb62 Mon Sep 17 00:00:00 2001 From: "Jens H. Nielsen" Date: Sat, 6 Aug 2022 08:06:59 +0200 Subject: [PATCH 4/5] exclude basel from old api docs --- docs/Makefile | 1 + docs/make.bat | 1 + 2 files changed, 2 insertions(+) diff --git a/docs/Makefile b/docs/Makefile index cf87c74833f..53296748673 100644 --- a/docs/Makefile +++ b/docs/Makefile @@ -28,6 +28,7 @@ genapi: sphinx-apidoc -o _auto -d 10 ../qcodes \ ../qcodes/instrument_drivers/agilent \ ../qcodes/instrument_drivers/AimTTi \ + ../qcodes/instrument_drivers/basel \ ../qcodes/instrument_drivers/HP \ ../qcodes/instrument_drivers/ithaco \ ../qcodes/instrument_drivers/keysight \ diff --git a/docs/make.bat b/docs/make.bat index e997c5980c1..0949ac47303 100644 --- a/docs/make.bat +++ b/docs/make.bat @@ -39,6 +39,7 @@ REM for storing drivers, not the lower-case one). sphinx-apidoc -o _auto -d 10 ..\qcodes ^ ..\qcodes\instrument_drivers\agilent\* ^ ..\qcodes\instrument_drivers\AimTTi ^ + ..\qcodes\instrument_drivers\basel ^ ..\qcodes\instrument_drivers\HP ^ ..\qcodes\instrument_drivers\ithaco ^ ..\qcodes\instrument_drivers\Lakeshore ^ From e47dfff6e0f3db65efb26881ef2c098d05e6c5d5 Mon Sep 17 00:00:00 2001 From: "Jens H. Nielsen" Date: Mon, 8 Aug 2022 10:17:28 +0200 Subject: [PATCH 5/5] let old driver match existing idn --- qcodes/instrument_drivers/basel/sp983c.py | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/qcodes/instrument_drivers/basel/sp983c.py b/qcodes/instrument_drivers/basel/sp983c.py index 4b92c3caad8..7bc560e73ef 100644 --- a/qcodes/instrument_drivers/basel/sp983c.py +++ b/qcodes/instrument_drivers/basel/sp983c.py @@ -3,4 +3,20 @@ Will eventually be deprecated and removed """ -from .BaselSP983c import BaselSP983c as SP983C +from typing import Dict, Optional + +from .BaselSP983c import BaselSP983c + + +class SP983C(BaselSP983c): + def get_idn(self) -> Dict[str, Optional[str]]: + vendor = "Physics Basel" + model = "SP 983(c)" + serial = None + firmware = None + return { + "vendor": vendor, + "model": model, + "serial": serial, + "firmware": firmware, + }