Code Monkey home page Code Monkey logo

diode-measurement's Introduction

Diode Measurement

IV/CV measurements for silicon sensors.

Run

On Windows download a pre-built executable from the release section and run it.

Install

Install using pip in a virtual environment.

pip install git+https://github.com/hephy-dd/diode-measurement.git@{version}

Build Executable

Building a Windows executable using PyInstaller.

# Create build environment
python -m venv build_env
. build_env/Scripts/activate

# Install dependencies
pip install -U pip
pip install wheel pyusb pyserial gpib-ctypes
pip install pyinstaller==4.10.* pyinstaller-versionfile==2.0.*
pip install .

# Build executable
pyinstaller pyinstaller.spec

An executable will be created in dist/diode-measurement-{version}.exe

Supported Instruments

Source Meter Units

  • Keithley K237
  • Keithley K2410
  • Keithley K2470
  • Keithley K2657A

Electro Meter

  • Keithley K6514
  • Keithley K6517B

LCR Meter

  • Keithley K595
  • Keysight E4980A
  • Agilent 4284A

DMM (Temperature)

  • Keithley K2700

Switching Matrix

  • HEPHY BrandBox (HV Switch)

Setup

To interface instruments using a GPIB interface the NI-VISA drivers need to be installed. Interfacing instruments using TCPIP, USB or Serial port is supported out of the box by using PyVISA-py, pyusb and pyserial.

The instrument resource name inputs accept follwing formats:

Format Example Result
<n> 16 GPIB::16::INSTR
<ip>:<port> 0.0.0.0:1080 TCPIP::0.0.0.0::1080::SOCKET
<host>:<port> localhost:1080 TCPIP::localhost::1080::SOCKET
<visa> GPIB1::16::INSTR GPIB1::16::INSTR

Data formats

The used plain text format consists of a header containing meta data in key and value pairs and one or more CSV data tables with headers using \t separators.

Synopsis

<key>: <value>
...
<<series>[<unit>]\t...>
<<value>\t...>
...

IV

IV measurement data consist of up to two CSV tables with the second (optional) table containing continuous measurement data.

Example

sample: Unnamed
measurement_type: iv
voltage_begin[V]: +5.000E+00
voltage_end[V]: -1.000E+01
voltage_step[V]: +1.000E+00
waiting_time[s]: +1.000E-01
current_compliance[A]: +1.000E-06

timestamp[s]	voltage[V]	v_smu[V]	i_smu[A]	i_elm[A]	i_elm2[A]	temperature[degC]
1629455368.29	+5.000E+00	+5.038E+00	+4.261E-08	+3.740E-08	+NAN	+NAN
1629455369.71	+4.000E+00	+4.065E+00	+7.708E-08	+9.495E-08	+NAN	+NAN
1629455370.49	+3.000E+00	+3.007E+00	+3.460E-08	+6.264E-08	+NAN	+NAN
...          	...       	...       	...       	...       	...       	...

timestamp[s]	voltage[V]	v_smu[V]	i_smu[A]	i_elm[A]	i_elm2[A]	temperature[degC]
1629455385.69	+3.000E+00	+3.046E+00	+3.996E-04	+7.137E-08	+NAN	+NAN
1629455387.65	+3.000E+00	+3.034E+00	+7.353E-04	+3.079E-08	+NAN	+NAN
1629455389.56	+3.000E+00	+3.021E+00	+9.081E-04	+1.266E-08	+NAN	+NAN
...          	...       	...       	...       	...       	...       	...

IV Bias

IV bias measurement data consist of up to two CSV tables with the second (optional) table containing continuous bias measurement data.

Example

sample: Unnamed
measurement_type: iv_bias
bias_voltage[V]: +1.000E+01
voltage_begin[V]: +5.000E+00
voltage_end[V]: -1.000E+01
voltage_step[V]: +1.000E+00
waiting_time[s]: +1.000E-01
current_compliance[A]: +1.000E-06

timestamp[s]	voltage[V]	v_smu[V]	i_smu[A]	v_smu2[V]	i_smu2[A]	i_elm[A]	i_elm2[A]	temperature[degC]
1629455368.29	+5.000E+00	+5.038E+00	+4.261E-08	+1.063E+01	+3.723E-08	+3.740E-08	+NAN	+NAN
1629455369.71	+4.000E+00	+4.065E+00	+7.708E-08	+1.051E+01	+6.513E-08	+9.495E-08	+NAN	+NAN
1629455370.49	+3.000E+00	+3.007E+00	+3.460E-08	+1.058E+01	+2.410E-08	+6.264E-08	+NAN	+NAN
...          	...       	...       	...       	...       	...       	...       	...       	...

timestamp[s]	voltage[V]	v_smu[V]	i_smu[A]	v_smu2[V]	i_smu2[A]	i_elm[A]	i_elm2[A]	temperature[degC]
1629455385.69	+3.000E+00	+3.046E+00	+3.996E-08	+1.063E+01	+2.657E-08	+7.137E-08	+NAN	+NAN
1629455387.65	+3.000E+00	+3.034E+00	+7.353E-08	+1.063E+01	+6.154E-08	+3.079E-08	+NAN	+NAN
1629455389.56	+3.000E+00	+3.021E+00	+9.081E-08	+1.063E+01	+8.426E-08	+1.266E-08	+NAN	+NAN
...          	...       	...       	...       	...       	...       	...       	...       	...

CV

CV measurement data consist of a single CSV table containing the measurement data.

Example

sample: Unnamed
measurement_type: cv
voltage_begin[V]: +5.000E+00
voltage_end[V]: -1.000E+01
voltage_step[V]: +1.000E+00
waiting_time[s]: +1.000E-01
current_compliance[A]: +1.000E-08

timestamp[s]	voltage[V]	v_smu[V]	i_smu[A]	c_lcr[F]	c2_lcr[F]	r_lcr[Ohm]	temperature[degC]
1629455368.29	+5.000E+00	+5.065E+00	+4.261E-08	+3.740E-05	7.149E+08	3.459932E-01	+NAN
1629455369.71	+4.000E+00	+4.037E+00	+7.708E-08	+9.495E-05	1.109E+08	3.015286E-01	+NAN
1629455370.49	+3.000E+00	+3.043E+00	+3.460E-08	+6.264E-05	2.549E+08	2.482018E-01	+NAN
...          	...       	...       	...       	...      	...      	...

JSON-RPC

The application provides an JSON-RPC (remote procedure call) version 2.0 interface using a TCP server.

Methods

Start

Start notification starts a new measurement.

{"jsonrpc": "2.0", "method": "start"}

Optional parameters are continuous (Boolean), reset (Boolean), auto_reconnect (Boolean), begin_voltage (Volt), end_voltage (Volt), step_voltage (Volt), waiting_time (seconds), compliance (Ampere) and waiting_time_continuous (seconds). Specified values will be applied to the user interface before starting the measurement.

{
  "jsonrpc": "2.0",
  "method": "start",
  "params": {
    "reset": true,
    "end_voltage": -100.0,
    "step_voltage": 10.0,
    "waiting_time": 1.0
  }
}

Stop

Stop notification stops an active measurement.

{"jsonrpc": "2.0", "method": "stop"}

Change voltage

Change voltage notification applies only during continuous It measurement.

Required parameter end_voltage (Volt).

Optional parameters with default values are step_voltage (default is 1.0 Volt) and waiting_time (default is 1.0 seconds).

{
  "jsonrpc": "2.0",
  "method": "change_voltage",
  "params": {
    "end_voltage": 100.0,
    "step_voltage": 10.0,
    "waiting_time": 0.25
  }
}

State

Request an application state snapshot.

{"jsonrpc": "2.0", "method": "state", "id": 0}

This will return application state parameters.

{
  "jsonrpc": "2.0",
  "result": {
    "state": "ramping",
    "measurement_type": "iv",
    "sample": "VPX1",
    "source_voltage": 24.0,
    "smu_voltage": 24.026,
    "smu_current": 0.0025,
    "smu2_voltage": null,
    "smu2_current": null,
    "elm_current": 0.0021,
    "elm2_current": null,
    "lcr_capacity": null,
    "temperature": 24.031
  },
  "id": 0
}

States

Following states are exposed by the state snapshot: idle, configure, ramping, continuous, stopping.

State diagram

Example

Example using netcat to initiate a new measurement and applies a new end voltage.

echo '{"jsonrpc": "2.0", "method": "start", "params": {"end_voltage": 100.0}}' | nc localhost 8000

Example using Python to read application state from TCP server.

import json
import socket

with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as sock:
    sock.connect(('localhost', 8000))
    request = {
      "jsonrpc": "2.0",
      "method": "state",
      "id": None
    }
    sock.sendall(json.dumps(request).encode('utf-8'))
    print(sock.recv(4096).decode('utf-8'))

diode-measurement's People

Contributors

arnobaer avatar prakhub avatar

Watchers

 avatar

Forkers

prakhub arnobaer

diode-measurement's Issues

Issue with step in linear range function

Linear range class functions.LinearRange does return an empty sequence if step exceeds the absolute ramp distance.

>>> list(LinearRange(0, 1, 5))
[]

It should return

>>> list(LinearRange(0, 1, 5))
[0.0, 1.0]

Test instrument connection and identification

To verify a connection to an instrument it would be convenient to have an action to manually test the connection specified in role resource settings (resource name, termination, timeout) an returning the instrument identification to verify the instrument used.

Add colored stop button

To catch the attention of the operator it would be useful to have the stop button colored in red while a measurement is running.

It might be required to switch the application to Fusion style (native Windows style lacks decent coloring).

Improve plot performance at high rates

Propagate It readings using a thread-safe queue rather then Qt's signal/slot mechanism to prevent slow down of the measurement loop when measuring at high rates (eg. up to 200Hz).

Also writing to an output file should be decoupled using a dedicated thread and queue.

Add IV Bias measurement

To apply a bias voltage and monitor a bias current add a new role SMU2 and a new measurement type "IV Bias".

Allow pA for sense range

Currently the Electrometer sense ranges are limited to 0.001 uA in the user interface, however some measurements require a sense range in the pA range.

A quick fix might be to increase the decimals from 3 to six.

minimal waiting time

the two fields with "waiting time" (one for IV and the other for IT) should be restricted to a minimum of 1 second. This is related to issue #12

Add K6517B as voltage source

Note: for IV measurements, when selecting only ELM instrument, the ELM acts as voltage source (if the instrument supports it).

Implement following methods for K6517B drivers:

  • get_output_enabled() -> bool
  • set_output_enabled(enabled: bool) -> None
  • get_voltage_level() -> float
  • set_voltage_level(level: float) -> None
  • set_voltage_range(level: float) -> None
  • set_current_compliance_level(level: float) -> None
  • compliance_tripped() -> bool

Remote control

Add remote control using an embedded micro TCPIP server and JSON protocol.

Proposal using JSON-RPC protocol via TCP socket:

Start notification.

{"jsonrpc": "2.0", "method": "start", "id": 0}

Stop notification.

{"jsonrpc": "2.0", "method": "stop", "id": 0}

Change voltage notification.

Applies only during continuous It measurement.

Requires parameter end_voltage and optional parameters step_voltage
(default is 1.0 Volt) and waiting_time (default is 1.0 seconds).

{"jsonrpc": "2.0", "method": "change_voltage", "params": {"end_voltage": 100.0, "step_voltage": 10.0, "waiting_time": 0.25}, "id": 0}

State snapshot.

{"jsonrpc": "2.0", "method": "state", "id": 0}

This will return application state parameters.

{"jsonrpc": "2.0", "result": {"measurement_type": "iv", "sample": "VPX1", "source_voltage": 24.0, "smu_current": 0.0025, "elm_current": 0.0021, "lcr_capacity": null, "temperature": 24.031}, "id": 0}

Save screenshot of plots

Add an option to save also a screenshot of the displayed plots at the end of a measurement (together with the measurement data file).

Add route terminals option

Add route terminals option for Keithely 2410 and 2470 SMUs to switch between front/rear terminals.

:ROUTe:TERMinals (FRON|REAR)

Filter count of 1 not supported by some instruments

A range of Keithley Instruments (2410, 6514, 6517B) do not support a filter (average) count of 1 although the valid range in the User Manuals is defined as 1...100. Setting the value to 1 creates an Invalid Parameter error in the queue.

It was proposed to limit the input range to 2...100.

Improve reading performance for fast measurements

To increase the performance for fast measurements (waiting time = 0) polling for compliance tripped can be limited to once every second (no need to poll multiple times per second in case of fast measurements).

CV yields division by zero

An LCR measurement x of value zero crashes the application applying the formula: 1. / x ** 2 due to an unhandled DivisionByZeroError exception.

Validate that the measured value is not zero, else ignore and do not add to the plot.

Change voltage yields range error

Using change voltage to reduce the voltage during It measurements yields a range error due to the fact that the source range is set to the target voltage before ramping down.

Change voltage needs two strategies: increase voltage and decrease voltage, eg. (pseudo code)

def increase_voltage(current_voltage, target_voltage, step_voltage):
    context.set_source_range(target_voltage)  # set higher target range
    for voltage in linear_range(current_voltage, target_voltage, step_voltage):
        context.set_source_voltage(voltage)

def decrease_voltage(current_voltage, target_voltage, step_voltage):
    for voltage in linear_range(current_voltage, target_voltage, step_voltage):
        context.set_source_voltage(voltage)
    context.set_source_range(target_voltage)  # set lower target range

def change_voltage(current_voltage, target_voltage, step_voltage):
    if abs(current_voltage) > abs(target_voltage):
        decrease_voltage(current_voltage, target_voltage, step_voltage)
    else:
        increase_voltage(current_voltage, target_voltage, step_voltage)

Anzeige der Loop-Zeit (Messzeit)

Es wäre hilfreich, in der Status bar unten die loop-Zeit (Messzeit) anzuzeigen, um minimale "Waiting Time" herauszufinden. Sowohl für IV als auch für IT.
(Hintergrund: Es gibt Leute, die stellen eine Waiting time von 0.1 sec ein und wundern sich, warum nicht alle zehntel Sekunde eine Messung passiert..)

Invalid plot values yield unhandled exceptions

Invalid plot values (None, NaN, +inf, -inf) from either measurement or data file can cause application crashes as plots can only accept finite float values.

Use math.nan as defaults for dictionary keys (avoiding None) and math.isfinite(x) to verify if the value can be added to a plot.

In addition it would beneficial to refactor class PlotsController into independent classes IVPlotsController and CVPlotsController for better modularization.

Model specific persistent settings

To make it more convenient to switch between instruments of the same role (ie. SMU), resource settings and parameters should be persistent for every model independently.

Crashes on file permission errors

File permission error exceptions are not handled and result in application crashes.

The cause seems to be connecting the file writer methods using Qt signals while executing the measurement in another thread. A workaround might be to add a simple callback mechanism to the measurement object (avoiding using Qt signals and executing file writer operations in the measurement thread).

Read temperature from DMM

Add DMM (digital multi-meter) role to enable reading temperature, supporting Keithley K2700.

The DMM has to be configured manually by the user to provide readings in degC, no reset by software.

Auto reconnect and retry in case of GPIB bus error

Operating old instruments (K237) using GPIB bus yields sporadic connection losses during measurements (VISA invalid resource identifier).

To overcome this problem the instrument resource should provide an auto-reconnect-and-retry feature that closes the current connection and opens a new connection end repeats the query in case of an connection related error.

Precision of timestamps

When using the tool in conjunction with a Keithley 2470 source meter, the precision of the timestamp is insufficient. The Keithley 2470 measures 100 samples or more per second. However, writer.py only uses timestamps with a precision of 10ms (safe_format(data.get('timestamp'), '.2f')). This leads to multiple sampes having the same timestamp. Timestamps with ms or µs precision would be preferrable.

Timeout error on start

Setup:

  1. sim SMU: python -m comet.emulator.keithley.k2410 -p 11002
  2. on start the communication works:
INFO:root:send (54, 'b'Spanish Inquisition Inc., Model 2410, 43768438, v1.0\r\n'')
INFO:root:recv (13, 'b':OUTP:STAT?\r\n'')
INFO:root:send (3, 'b'0\r\n'')
INFO:root:recv (26, 'b':SOUR:VOLT:LEV 0.000E+00\r\n'')
INFO:root:recv (7, 'b'*OPC?\r\n'')
INFO:root:send (3, 'b'1\r\n'')
INFO:root:recv (6, 'b'*CLS\r\n'')
INFO:root:recv (7, 'b'*OPC?\r\n'')
INFO:root:send (3, 'b'1\r\n'')
INFO:root:recv (17, 'b':ROUT:TERM FRON\r\n'')
INFO:root:recv (7, 'b'*OPC?\r\n'')
INFO:root:send (3, 'b'1\r\n'')
INFO:root:recv (24, 'b':SOUR:FUNC VOLT\r\n*OPC?\r\n'')
INFO:root:send (3, 'b'1\r\n'')
INFO:root:recv (33, 'b':SENS:CURR:AVER:TCON MOV\r\n*OPC?\r\n'')
...
  1. The exception occurs at some time after the start command (few secs):
2022-05-09T09:50:20::diode_measurement.measurement::ERROR::K2470: TCPIP0::localhost::11002::SOCKET: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.
Traceback (most recent call last):
  File "diode_measurement\resource.py", line 56, in read
  File "pyvisa\resources\messagebased.py", line 486, in read
  File "pyvisa\resources\messagebased.py", line 442, in _read_raw
  File "pyvisa_py\highlevel.py", line 519, in read
  File "pyvisa\highlevel.py", line 251, in handle_return_value
pyvisa.errors.VisaIOError: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "diode_measurement\driver\driver.py", line 12, in handle_exception
  File "diode_measurement\driver\k2470.py", line 76, in _query
  File "diode_measurement\resource.py", line 43, in query
  File "diode_measurement\resource.py", line 60, in read
diode_measurement.resource.ResourceError: TCPIP0::localhost::11002::SOCKET: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "diode_measurement\measurement\__init__.py", line 110, in run
  File "diode_measurement\measurement\__init__.py", line 328, in measure
  File "diode_measurement\measurement\iv.py", line 54, in acquireReading
  File "diode_measurement\measurement\iv.py", line 34, in acquireReadingData
  File "diode_measurement\driver\k2470.py", line 64, in read_current
  File "diode_measurement\driver\driver.py", line 14, in handle_exception
diode_measurement.driver.driver.DriverError: K2470: TCPIP0::localhost::11002::SOCKET: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.
2022-05-09T09:50:24::diode_measurement.measurement::ERROR::K2470: TCPIP0::localhost::11002::SOCKET: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.
Traceback (most recent call last):
  File "diode_measurement\resource.py", line 56, in read
  File "pyvisa\resources\messagebased.py", line 486, in read
  File "pyvisa\resources\messagebased.py", line 442, in _read_raw
  File "pyvisa_py\highlevel.py", line 519, in read
  File "pyvisa\highlevel.py", line 251, in handle_return_value
pyvisa.errors.VisaIOError: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "diode_measurement\driver\driver.py", line 12, in handle_exception
  File "diode_measurement\driver\k2470.py", line 76, in _query
  File "diode_measurement\resource.py", line 43, in query
  File "diode_measurement\resource.py", line 60, in read
diode_measurement.resource.ResourceError: TCPIP0::localhost::11002::SOCKET: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "diode_measurement\measurement\__init__.py", line 118, in run
  File "diode_measurement\measurement\__init__.py", line 365, in finalize
  File "diode_measurement\measurement\__init__.py", line 354, in read_source_voltage
  File "diode_measurement\driver\k2470.py", line 67, in read_voltage
  File "diode_measurement\driver\driver.py", line 14, in handle_exception
diode_measurement.driver.driver.DriverError: K2470: TCPIP0::localhost::11002::SOCKET: VI_ERROR_TMO (-1073807339): Timeout expired before operation completed.

Occasional TypeError with QDateTime.fromMSecsSinceEpoch

QDateTime.fromMSecsSinceEpoch raises a TypeError one some occasions albeit the assigned float value is cast to an integer.

TypeError: arguments did not match any overloaded call:
  fromMSecsSinceEpoch(int): argument 1 has unexpected type 'float'
  fromMSecsSinceEpoch(int, Qt.TimeSpec, offsetSeconds: int = 0): argument 1 has unexpected type 'float'
  fromMSecsSinceEpoch(int, QTimeZone): argument 1 has unexpected type 'float'

This issue seems to affect only on Windows OS.

Change voltage in continuous It measurement

Make it possible to change source voltage during It measurements by applying a configurable ramp to a new target voltage level.

  • add button Change Voltage to Continuous Meas. group box in General tab.
  • create a Change Voltage dialog to configure ramp parameters end voltage, step voltage and waiting time.

Bug with continuous waiting time > 1 s

A unit conversion error due to non English locales using pint returns waiting times scales by a factor of 1000.

Quick fix: do not scale waiting time using pint.

Broken release 0.14.0

A misspelled attribute prevents starting measurements (pylint, flake8 and mypy failed to detect the issue).

unclear delay between "start" button pressed and IV ramp starts

the title says it all. The feeling is also that it lasts much longer on the first start after the software was opened. But even later it takes several seconds until something happens after the start button was pressed.

If it is intentional then it needs to be written somewhere how long this delay lasts.
If it is not intentional then we need to investigate why it takes so long.

Show error dialog before ramp down

If an error occurs during a measurement the corresponding error dialog shows up after ramping down and finishing the measurement.

The dialog should show up immediately.

Add parameters for Electrometers

For K6514 and K6517B add panel inputs for

  • current auto range
  • current range
  • average state
  • average count
  • average tcontrol
  • power line cycles (NPLC)

Additional options for LCR meters

A request for adding following options for LCR meters 4284A and 4980A:

  • Correction
    • Enable SHORT
  • AC Voltage
    • Amplitude (mV)
    • Frequency (Hz)
    • ALC (Auto Level Control)

Add SMU integration time

Add NPLC input for SMUs to set measurement integration time/aperture.

For K2410 and K2470 (0.01 to 10) configure :SENS:CURR:NPLC <n>

For K2657A (0.001 to 25) configure smuX.measure.nplc = <n>

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.