# pyvisa-ar488

PyVISA backend for AR488 and Prologix GPIB-USB/TCP adapters.

Lets you use standard [pyvisa](https://pyvisa.readthedocs.io/) and
[pymeasure](https://pymeasure.readthedocs.io/) code to talk to IEEE-488
(GPIB) instruments through inexpensive AR488 or Prologix-compatible adapters.

## Quick Start

```bash
pip install pyvisa-ar488
```

```python
import pyvisa

# Serial adapter (e.g. Arduino Nano / ESP32 with AR488 firmware)
rm = pyvisa.ResourceManager("@ar488")
print(rm.list_resources())          # scans bus: ('GPIB0::5::INSTR', 'GPIB0::22::INSTR', ...)

instr = rm.open_resource("GPIB0::22::INSTR")
print(instr.query("*IDN?"))         # 'KEITHLEY INSTRUMENTS INC.,MODEL 2400,...'
print(instr.query("MEAS:VOLT:DC?")) # '-1.234567E-03'
```

## Transports

### Serial (default)

The adapter is auto-detected on `/dev/ttyUSB0` at 115200 baud. Override via
environment or constructor:

```python
from pyvisa_ar488 import AR488VisaLibrary

lib = AR488VisaLibrary.from_serial(port="/dev/ttyACM0", baudrate=115200)
rm = pyvisa.ResourceManager(lib)
```

### TCP (WiFi-connected ESP32)

```python
lib = AR488VisaLibrary.from_tcp(host="192.168.1.100", port=23)
rm = pyvisa.ResourceManager(lib)
```

### Bridge mode (mcgpib integration)

When used inside [mcgpib](https://github.com/rmalley/mcgpib), the backend
shares the existing async connection instead of opening a new one:

```python
lib = AR488VisaLibrary.from_bridge(bridge_connection, event_loop)
rm = pyvisa.ResourceManager(lib)
```

## CLI

Scan a bus from the command line:

```bash
# Serial
pyvisa-ar488 --port /dev/ttyUSB0

# TCP
pyvisa-ar488 --host 192.168.1.100 --tcp-port 23
```

## How it works

pyvisa discovers backends by looking for `pyvisa_<name>` packages.
`pyvisa-ar488` registers as the `@ar488` backend. When you open a resource,
the backend translates pyvisa's read/write/poll calls into AR488 `++` command
sequences:

| pyvisa call | AR488 commands |
|---|---|
| `rm.list_resources()` | `++findlstn` |
| `instr.write("*RST")` | `++addr 22` then `*RST` |
| `instr.read()` | `++read eoi` |
| `instr.query("*IDN?")` | `++addr 22`, `*IDN?`, `++read eoi` |
| `instr.read_stb()` | `++spoll 22` |
| `instr.assert_trigger()` | `++trg` |
| `rm.send_ifc()` | `++ifc` |

The init sequence configures the adapter for machine-parseable output:
`++verbose 0`, `++prompt 0`, `++auto 0`, `++mode 1`, `++eoi 1`, `++eos 0`.

## Compatible adapters

- [AR488](https://github.com/Twilight-Logic/AR488) (Arduino / ESP32)
- Prologix GPIB-USB
- Any adapter using the Prologix `++` command protocol

## Requirements

- Python 3.11+
- pyvisa >= 1.13
- pyserial >= 3.5

## License

MIT
