--- /dev/null
+/* SPDX-License-Identifier: GPL-2.0 */
+
+/***************************************************************************
+ * copyright : (C) 2002 by Frank Mori Hess
+ ***************************************************************************/
+
+#ifndef _GPIB_IOCTL_H
+#define _GPIB_IOCTL_H
+
+#include <asm/ioctl.h>
+#include <linux/types.h>
+
+#define GPIB_CODE 160
+
+typedef struct {
+ char name[100];
+} board_type_ioctl_t;
+
+/* argument for read/write/command ioctls */
+typedef struct {
+ uint64_t buffer_ptr;
+ unsigned int requested_transfer_count;
+ unsigned int completed_transfer_count;
+ int end; /* end flag return for reads, end io suppression request for cmd*/
+ int handle;
+} read_write_ioctl_t;
+
+typedef struct {
+ unsigned int handle;
+ unsigned int pad;
+ int sad;
+ unsigned is_board : 1;
+} open_dev_ioctl_t;
+
+typedef struct {
+ unsigned int handle;
+} close_dev_ioctl_t;
+
+typedef struct {
+ unsigned int pad;
+ int sad;
+ uint8_t status_byte;
+} serial_poll_ioctl_t;
+
+typedef struct {
+ int eos;
+ int eos_flags;
+} eos_ioctl_t;
+
+typedef struct {
+ int handle;
+ int wait_mask;
+ int clear_mask;
+ int set_mask;
+ int ibsta;
+ int pad;
+ int sad;
+ unsigned int usec_timeout;
+} wait_ioctl_t;
+
+typedef struct {
+ uint64_t init_data_ptr;
+ int init_data_length;
+ int online;
+} online_ioctl_t;
+
+typedef struct {
+ unsigned int num_bytes;
+ unsigned int pad;
+ int sad;
+} spoll_bytes_ioctl_t;
+
+typedef struct {
+ unsigned int pad;
+ int sad;
+ int parallel_poll_configuration;
+ int autopolling;
+ int is_system_controller;
+ unsigned int t1_delay;
+ unsigned ist : 1;
+ unsigned no_7_bit_eos : 1;
+} board_info_ioctl_t;
+
+typedef struct {
+ int pci_bus;
+ int pci_slot;
+} select_pci_ioctl_t;
+
+typedef struct {
+ uint8_t config;
+ unsigned set_ist : 1;
+ unsigned clear_ist : 1;
+} ppoll_config_ioctl_t;
+
+typedef struct {
+ unsigned int handle;
+ unsigned int pad;
+} pad_ioctl_t;
+
+typedef struct {
+ unsigned int handle;
+ int sad;
+} sad_ioctl_t;
+
+// select a piece of hardware to attach by its sysfs device path
+typedef struct {
+ char device_path[0x1000];
+} select_device_path_ioctl_t;
+
+typedef short event_ioctl_t;
+typedef int rsc_ioctl_t;
+typedef unsigned int t1_delay_ioctl_t;
+typedef short autospoll_ioctl_t;
+typedef short local_ppoll_mode_ioctl_t;
+
+// update status byte and request service
+typedef struct {
+ uint8_t status_byte;
+ int new_reason_for_service;
+} request_service2_t;
+
+/* Standard functions. */
+enum gpib_ioctl {
+ IBRD = _IOWR(GPIB_CODE, 100, read_write_ioctl_t),
+ IBWRT = _IOWR(GPIB_CODE, 101, read_write_ioctl_t),
+ IBCMD = _IOWR(GPIB_CODE, 102, read_write_ioctl_t),
+ IBOPENDEV = _IOWR(GPIB_CODE, 3, open_dev_ioctl_t),
+ IBCLOSEDEV = _IOW(GPIB_CODE, 4, close_dev_ioctl_t),
+ IBWAIT = _IOWR(GPIB_CODE, 5, wait_ioctl_t),
+ IBRPP = _IOWR(GPIB_CODE, 6, uint8_t),
+
+ IBSIC = _IOW(GPIB_CODE, 9, unsigned int),
+ IBSRE = _IOW(GPIB_CODE, 10, int),
+ IBGTS = _IO(GPIB_CODE, 11),
+ IBCAC = _IOW(GPIB_CODE, 12, int),
+ IBLINES = _IOR(GPIB_CODE, 14, short),
+ IBPAD = _IOW(GPIB_CODE, 15, pad_ioctl_t),
+ IBSAD = _IOW(GPIB_CODE, 16, sad_ioctl_t),
+ IBTMO = _IOW(GPIB_CODE, 17, unsigned int),
+ IBRSP = _IOWR(GPIB_CODE, 18, serial_poll_ioctl_t),
+ IBEOS = _IOW(GPIB_CODE, 19, eos_ioctl_t),
+ IBRSV = _IOW(GPIB_CODE, 20, uint8_t),
+ CFCBASE = _IOW(GPIB_CODE, 21, uint64_t),
+ CFCIRQ = _IOW(GPIB_CODE, 22, unsigned int),
+ CFCDMA = _IOW(GPIB_CODE, 23, unsigned int),
+ CFCBOARDTYPE = _IOW(GPIB_CODE, 24, board_type_ioctl_t),
+
+ IBMUTEX = _IOW(GPIB_CODE, 26, int),
+ IBSPOLL_BYTES = _IOWR(GPIB_CODE, 27, spoll_bytes_ioctl_t),
+ IBPPC = _IOW(GPIB_CODE, 28, ppoll_config_ioctl_t),
+ IBBOARD_INFO = _IOR(GPIB_CODE, 29, board_info_ioctl_t),
+
+ IBQUERY_BOARD_RSV = _IOR(GPIB_CODE, 31, int),
+ IBSELECT_PCI = _IOWR(GPIB_CODE, 32, select_pci_ioctl_t),
+ IBEVENT = _IOR(GPIB_CODE, 33, event_ioctl_t),
+ IBRSC = _IOW(GPIB_CODE, 34, rsc_ioctl_t),
+ IB_T1_DELAY = _IOW(GPIB_CODE, 35, t1_delay_ioctl_t),
+ IBLOC = _IO(GPIB_CODE, 36),
+
+ IBAUTOSPOLL = _IOW(GPIB_CODE, 38, autospoll_ioctl_t),
+ IBONL = _IOW(GPIB_CODE, 39, online_ioctl_t),
+ IBPP2_SET = _IOW(GPIB_CODE, 40, local_ppoll_mode_ioctl_t),
+ IBPP2_GET = _IOR(GPIB_CODE, 41, local_ppoll_mode_ioctl_t),
+ IBSELECT_DEVICE_PATH = _IOW(GPIB_CODE, 43, select_device_path_ioctl_t),
+ // 44 was IBSELECT_SERIAL_NUMBER
+ IBRSV2 = _IOW(GPIB_CODE, 45, request_service2_t)
+};
+
+#endif /* _GPIB_IOCTL_H */
--- /dev/null
+/* SPDX-License-Identifier: GPL-2.0 */
+
+/***************************************************************************
+ * copyright : (C) 2002 by Frank Mori Hess
+ ***************************************************************************/
+
+#ifndef _GPIB_USER_H
+#define _GPIB_USER_H
+
+#define GPIB_MAX_NUM_BOARDS 16
+#define GPIB_MAX_NUM_DESCRIPTORS 0x1000
+
+enum ibsta_bit_numbers {
+ DCAS_NUM = 0,
+ DTAS_NUM = 1,
+ LACS_NUM = 2,
+ TACS_NUM = 3,
+ ATN_NUM = 4,
+ CIC_NUM = 5,
+ REM_NUM = 6,
+ LOK_NUM = 7,
+ CMPL_NUM = 8,
+ EVENT_NUM = 9,
+ SPOLL_NUM = 10,
+ RQS_NUM = 11,
+ SRQI_NUM = 12,
+ END_NUM = 13,
+ TIMO_NUM = 14,
+ ERR_NUM = 15
+};
+
+/* IBSTA status bits (returned by all functions) */
+enum ibsta_bits {
+ DCAS = (1 << DCAS_NUM), /* device clear state */
+ DTAS = (1 << DTAS_NUM), /* device trigger state */
+ LACS = (1 << LACS_NUM), /* GPIB interface is addressed as Listener */
+ TACS = (1 << TACS_NUM), /* GPIB interface is addressed as Talker */
+ ATN = (1 << ATN_NUM), /* Attention is asserted */
+ CIC = (1 << CIC_NUM), /* GPIB interface is Controller-in-Charge */
+ REM = (1 << REM_NUM), /* remote state */
+ LOK = (1 << LOK_NUM), /* lockout state */
+ CMPL = (1 << CMPL_NUM), /* I/O is complete */
+ EVENT = (1 << EVENT_NUM), /* DCAS, DTAS, or IFC has occurred */
+ SPOLL = (1 << SPOLL_NUM), /* board serial polled by busmaster */
+ RQS = (1 << RQS_NUM), /* Device requesting service */
+ SRQI = (1 << SRQI_NUM), /* SRQ is asserted */
+ END = (1 << END_NUM), /* EOI or EOS encountered */
+ TIMO = (1 << TIMO_NUM), /* Time limit on I/O or wait function exceeded */
+ ERR = (1 << ERR_NUM) /* Function call terminated on error */
+};
+
+static const int device_status_mask = ERR | TIMO | END | CMPL | RQS;
+static const int board_status_mask = ERR | TIMO | END | CMPL | SPOLL |
+ EVENT | LOK | REM | CIC | ATN | TACS | LACS | DTAS | DCAS | SRQI;
+
+/* IBERR error codes */
+enum iberr_code {
+ EDVR = 0, /* system error */
+ ECIC = 1, /* not CIC */
+ ENOL = 2, /* no listeners */
+ EADR = 3, /* CIC and not addressed before I/O */
+ EARG = 4, /* bad argument to function call */
+ ESAC = 5, /* not SAC */
+ EABO = 6, /* I/O operation was aborted */
+ ENEB = 7, /* non-existent board (GPIB interface offline) */
+ EDMA = 8, /* DMA hardware error detected */
+ EOIP = 10, /* new I/O attempted with old I/O in progress */
+ ECAP = 11, /* no capability for intended opeation */
+ EFSO = 12, /* file system operation error */
+ EBUS = 14, /* bus error */
+ ESTB = 15, /* lost serial poll bytes */
+ ESRQ = 16, /* SRQ stuck on */
+ ETAB = 20 /* Table Overflow */
+};
+
+/* Timeout values and meanings */
+enum gpib_timeout {
+ TNONE = 0, /* Infinite timeout (disabled) */
+ T10us = 1, /* Timeout of 10 usec (ideal) */
+ T30us = 2, /* Timeout of 30 usec (ideal) */
+ T100us = 3, /* Timeout of 100 usec (ideal) */
+ T300us = 4, /* Timeout of 300 usec (ideal) */
+ T1ms = 5, /* Timeout of 1 msec (ideal) */
+ T3ms = 6, /* Timeout of 3 msec (ideal) */
+ T10ms = 7, /* Timeout of 10 msec (ideal) */
+ T30ms = 8, /* Timeout of 30 msec (ideal) */
+ T100ms = 9, /* Timeout of 100 msec (ideal) */
+ T300ms = 10, /* Timeout of 300 msec (ideal) */
+ T1s = 11, /* Timeout of 1 sec (ideal) */
+ T3s = 12, /* Timeout of 3 sec (ideal) */
+ T10s = 13, /* Timeout of 10 sec (ideal) */
+ T30s = 14, /* Timeout of 30 sec (ideal) */
+ T100s = 15, /* Timeout of 100 sec (ideal) */
+ T300s = 16, /* Timeout of 300 sec (ideal) */
+ T1000s = 17 /* Timeout of 1000 sec (maximum) */
+};
+
+/* End-of-string (EOS) modes for use with ibeos */
+
+enum eos_flags {
+ EOS_MASK = 0x1c00,
+ REOS = 0x0400, /* Terminate reads on EOS */
+ XEOS = 0x800, /* assert EOI when EOS char is sent */
+ BIN = 0x1000 /* Do 8-bit compare on EOS */
+};
+
+/* GPIB Bus Control Lines bit vector */
+enum bus_control_line {
+ ValidDAV = 0x01,
+ ValidNDAC = 0x02,
+ ValidNRFD = 0x04,
+ ValidIFC = 0x08,
+ ValidREN = 0x10,
+ ValidSRQ = 0x20,
+ ValidATN = 0x40,
+ ValidEOI = 0x80,
+ ValidALL = 0xff,
+ BusDAV = 0x0100, /* DAV line status bit */
+ BusNDAC = 0x0200, /* NDAC line status bit */
+ BusNRFD = 0x0400, /* NRFD line status bit */
+ BusIFC = 0x0800, /* IFC line status bit */
+ BusREN = 0x1000, /* REN line status bit */
+ BusSRQ = 0x2000, /* SRQ line status bit */
+ BusATN = 0x4000, /* ATN line status bit */
+ BusEOI = 0x8000 /* EOI line status bit */
+};
+
+enum old_bus_control_line {
+ BUS_DAV = 0x0100, /* DAV line status bit */
+ BUS_NDAC = 0x0200, /* NDAC line status bit */
+ BUS_NRFD = 0x0400, /* NRFD line status bit */
+ BUS_IFC = 0x0800, /* IFC line status bit */
+ BUS_REN = 0x1000, /* REN line status bit */
+ BUS_SRQ = 0x2000, /* SRQ line status bit */
+ BUS_ATN = 0x4000, /* ATN line status bit */
+ BUS_EOI = 0x8000 /* EOI line status bit */
+};
+
+/* Possible GPIB command messages */
+
+enum cmd_byte {
+ GTL = 0x1, /* go to local */
+ SDC = 0x4, /* selected device clear */
+ PPConfig = 0x5,
+#ifndef PPC
+ PPC = PPConfig, /* parallel poll configure */
+#endif
+ GET = 0x8, /* group execute trigger */
+ TCT = 0x9, /* take control */
+ LLO = 0x11, /* local lockout */
+ DCL = 0x14, /* device clear */
+ PPU = 0x15, /* parallel poll unconfigure */
+ SPE = 0x18, /* serial poll enable */
+ SPD = 0x19, /* serial poll disable */
+ CFE = 0x1f, /* configure enable */
+ LAD = 0x20, /* value to be 'ored' in to obtain listen address */
+ UNL = 0x3F, /* unlisten */
+ TAD = 0x40, /* value to be 'ored' in to obtain talk address */
+ UNT = 0x5F, /* untalk */
+ SAD = 0x60, /* my secondary address (base) */
+ PPE = 0x60, /* parallel poll enable (base) */
+ PPD = 0x70 /* parallel poll disable */
+};
+
+enum ppe_bits {
+ PPC_DISABLE = 0x10,
+ PPC_SENSE = 0x8, /* parallel poll sense bit */
+ PPC_DIO_MASK = 0x7
+};
+
+/* confine address to range 0 to 30. */
+static inline unsigned int gpib_address_restrict(unsigned int addr)
+{
+ addr &= 0x1f;
+ if (addr == 0x1f)
+ addr = 0;
+ return addr;
+}
+
+static inline uint8_t MLA(unsigned int addr)
+{
+ return gpib_address_restrict(addr) | LAD;
+}
+
+static inline uint8_t MTA(unsigned int addr)
+{
+ return gpib_address_restrict(addr) | TAD;
+}
+
+static inline uint8_t MSA(unsigned int addr)
+{
+ return gpib_address_restrict(addr) | SAD;
+}
+
+static inline uint8_t PPE_byte(unsigned int dio_line, int sense)
+{
+ uint8_t cmd;
+
+ cmd = PPE;
+ if (sense)
+ cmd |= PPC_SENSE;
+ cmd |= (dio_line - 1) & 0x7;
+ return cmd;
+}
+
+static inline uint8_t CFGn(unsigned int meters)
+{
+ return 0x6 | (meters & 0xf);
+}
+
+/* mask of bits that actually matter in a command byte */
+static const uint8_t gpib_command_mask = 0x7f;
+
+static inline int is_PPE(uint8_t command)
+{
+ return (command & 0x70) == 0x60;
+}
+
+static inline int is_PPD(uint8_t command)
+{
+ return (command & 0x70) == 0x70;
+}
+
+static inline int in_addressed_command_group(uint8_t command)
+{
+ return (command & 0x70) == 0x0;
+}
+
+static inline int in_universal_command_group(uint8_t command)
+{
+ return (command & 0x70) == 0x10;
+}
+
+static inline int in_listen_address_group(uint8_t command)
+{
+ return (command & 0x60) == 0x20;
+}
+
+static inline int in_talk_address_group(uint8_t command)
+{
+ return (command & 0x60) == 0x40;
+}
+
+static inline int in_primary_command_group(uint8_t command)
+{
+ return in_addressed_command_group(command) ||
+ in_universal_command_group(command) ||
+ in_listen_address_group(command) ||
+ in_talk_address_group(command);
+}
+
+static inline int gpib_address_equal(unsigned int pad1, int sad1, unsigned int pad2, int sad2)
+{
+ if (pad1 == pad2) {
+ if (sad1 == sad2)
+ return 1;
+ if (sad1 < 0 && sad2 < 0)
+ return 1;
+ }
+
+ return 0;
+}
+
+static const int gpib_addr_max = 30; /* max address for primary/secondary gpib addresses */
+
+enum ibask_option {
+ IbaPAD = 0x1,
+ IbaSAD = 0x2,
+ IbaTMO = 0x3,
+ IbaEOT = 0x4,
+ IbaPPC = 0x5, /* board only */
+ IbaREADDR = 0x6, /* device only */
+ IbaAUTOPOLL = 0x7, /* board only */
+ IbaCICPROT = 0x8, /* board only */
+ IbaIRQ = 0x9, /* board only */
+ IbaSC = 0xa, /* board only */
+ IbaSRE = 0xb, /* board only */
+ IbaEOSrd = 0xc,
+ IbaEOSwrt = 0xd,
+ IbaEOScmp = 0xe,
+ IbaEOSchar = 0xf,
+ IbaPP2 = 0x10, /* board only */
+ IbaTIMING = 0x11, /* board only */
+ IbaDMA = 0x12, /* board only */
+ IbaReadAdjust = 0x13,
+ IbaWriteAdjust = 0x14,
+ IbaEventQueue = 0x15, /* board only */
+ IbaSPollBit = 0x16, /* board only */
+ IbaSpollBit = 0x16, /* board only */
+ IbaSendLLO = 0x17, /* board only */
+ IbaSPollTime = 0x18, /* device only */
+ IbaPPollTime = 0x19, /* board only */
+ IbaEndBitIsNormal = 0x1a,
+ IbaUnAddr = 0x1b, /* device only */
+ IbaHSCableLength = 0x1f, /* board only */
+ IbaIst = 0x20, /* board only */
+ IbaRsv = 0x21, /* board only */
+ IbaBNA = 0x200, /* device only */
+ /* linux-gpib extensions */
+ Iba7BitEOS = 0x1000 /* board only. Returns 1 if board supports 7 bit eos compares*/
+};
+
+enum ibconfig_option {
+ IbcPAD = 0x1,
+ IbcSAD = 0x2,
+ IbcTMO = 0x3,
+ IbcEOT = 0x4,
+ IbcPPC = 0x5, /* board only */
+ IbcREADDR = 0x6, /* device only */
+ IbcAUTOPOLL = 0x7, /* board only */
+ IbcCICPROT = 0x8, /* board only */
+ IbcIRQ = 0x9, /* board only */
+ IbcSC = 0xa, /* board only */
+ IbcSRE = 0xb, /* board only */
+ IbcEOSrd = 0xc,
+ IbcEOSwrt = 0xd,
+ IbcEOScmp = 0xe,
+ IbcEOSchar = 0xf,
+ IbcPP2 = 0x10, /* board only */
+ IbcTIMING = 0x11, /* board only */
+ IbcDMA = 0x12, /* board only */
+ IbcReadAdjust = 0x13,
+ IbcWriteAdjust = 0x14,
+ IbcEventQueue = 0x15, /* board only */
+ IbcSPollBit = 0x16, /* board only */
+ IbcSpollBit = 0x16, /* board only */
+ IbcSendLLO = 0x17, /* board only */
+ IbcSPollTime = 0x18, /* device only */
+ IbcPPollTime = 0x19, /* board only */
+ IbcEndBitIsNormal = 0x1a,
+ IbcUnAddr = 0x1b, /* device only */
+ IbcHSCableLength = 0x1f, /* board only */
+ IbcIst = 0x20, /* board only */
+ IbcRsv = 0x21, /* board only */
+ IbcBNA = 0x200 /* device only */
+};
+
+enum t1_delays {
+ T1_DELAY_2000ns = 1,
+ T1_DELAY_500ns = 2,
+ T1_DELAY_350ns = 3
+};
+
+static const int request_service_bit = 0x40;
+
+enum gpib_events {
+ EventNone = 0,
+ EventDevTrg = 1,
+ EventDevClr = 2,
+ EventIFC = 3
+};
+
+enum gpib_stb {
+ IbStbRQS = 0x40, /* IEEE 488.1 & 2 */
+ IbStbESB = 0x20, /* IEEE 488.2 only */
+ IbStbMAV = 0x10 /* IEEE 488.2 only */
+};
+
+#endif /* _GPIB_USER_H */
+
+/* Check for errors */