diff options
author | Guido Kiener <guido@kiener-muenchen.de> | 2018-07-18 10:45:39 +0200 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2018-07-21 08:22:15 +0200 |
commit | 12dcaeb77e67c1162a2604f6b589266baec2d1ef (patch) | |
tree | 8e705a16b689c9fa2b73a6c1df4d7bdc562bcbc9 /drivers/usb/class | |
parent | fbd83971f9429849dd3a105b663822d15b7b992b (diff) |
usb: usbtmc: Add ioctl for termination character
add USBTMC_IOCTL_CONFIG_TERMCHAR to control TermChar handling
for next read(). Controls field 'TermChar' and Bit 1 of field
'bmTransferAttributes' of REQUEST_DEV_DEP_MSG_IN BULK-OUT header.
Allows enabling/disabling of terminating a read on reception of
term_char individually for each read request.
Reviewed-by: Steve Bayless <steve_bayless@keysight.com>
Tested-by: Dave Penkler <dpenkler@gmail.com>
Signed-off-by: Dave Penkler <dpenkler@gmail.com>
Signed-off-by: Guido Kiener <guido.kiener@rohde-schwarz.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/usb/class')
-rw-r--r-- | drivers/usb/class/usbtmc.c | 36 |
1 files changed, 34 insertions, 2 deletions
diff --git a/drivers/usb/class/usbtmc.c b/drivers/usb/class/usbtmc.c index c77e0ac6260b..1b7b2e402adb 100644 --- a/drivers/usb/class/usbtmc.c +++ b/drivers/usb/class/usbtmc.c @@ -121,6 +121,8 @@ struct usbtmc_file_data { u8 srq_byte; atomic_t srq_asserted; u8 eom_val; + u8 term_char; + bool term_char_enabled; }; /* Forward declarations */ @@ -157,7 +159,10 @@ static int usbtmc_open(struct inode *inode, struct file *filp) mutex_lock(&data->io_mutex); file_data->data = data; + /* copy default values from device settings */ file_data->timeout = USBTMC_TIMEOUT; + file_data->term_char = data->TermChar; + file_data->term_char_enabled = data->TermCharEnabled; file_data->eom_val = 1; INIT_LIST_HEAD(&file_data->file_elem); @@ -634,9 +639,9 @@ static int send_request_dev_dep_msg_in(struct usbtmc_file_data *file_data, buffer[5] = transfer_size >> 8; buffer[6] = transfer_size >> 16; buffer[7] = transfer_size >> 24; - buffer[8] = data->TermCharEnabled * 2; + buffer[8] = file_data->term_char_enabled * 2; /* Use term character? */ - buffer[9] = data->TermChar; + buffer[9] = file_data->term_char; buffer[10] = 0; /* Reserved */ buffer[11] = 0; /* Reserved */ @@ -1298,6 +1303,28 @@ static int usbtmc_ioctl_eom_enable(struct usbtmc_file_data *file_data, return 0; } +/* + * Configure termination character for read() + */ +static int usbtmc_ioctl_config_termc(struct usbtmc_file_data *file_data, + void __user *arg) +{ + struct usbtmc_termchar termc; + + if (copy_from_user(&termc, arg, sizeof(termc))) + return -EFAULT; + + if ((termc.term_char_enabled > 1) || + (termc.term_char_enabled && + !(file_data->data->capabilities.device_capabilities & 1))) + return -EINVAL; + + file_data->term_char = termc.term_char; + file_data->term_char_enabled = termc.term_char_enabled; + + return 0; +} + static long usbtmc_ioctl(struct file *file, unsigned int cmd, unsigned long arg) { struct usbtmc_file_data *file_data; @@ -1353,6 +1380,11 @@ static long usbtmc_ioctl(struct file *file, unsigned int cmd, unsigned long arg) (void __user *)arg); break; + case USBTMC_IOCTL_CONFIG_TERMCHAR: + retval = usbtmc_ioctl_config_termc(file_data, + (void __user *)arg); + break; + case USBTMC488_IOCTL_GET_CAPS: retval = copy_to_user((void __user *)arg, &data->usb488_caps, |