From: <gregkh@linuxfoundation.org>
To: dpenkler@gmail.com,gregkh@linuxfoundation.org,stable@kernel.org
Cc: <stable@vger.kernel.org>
Subject: FAILED: patch "[PATCH] staging: gpib: Fix Oops after disconnect in ni_usb" failed to apply to 6.14-stable tree
Date: Thu, 03 Apr 2025 15:34:09 +0100 [thread overview]
Message-ID: <2025040309-kabob-graph-ed91@gregkh> (raw)
The patch below does not apply to the 6.14-stable tree.
If someone wants it applied there, or to any other stable or longterm
tree, then please email the backport, including the original git commit
id to <stable@vger.kernel.org>.
To reproduce the conflict and resubmit, you may use the following commands:
git fetch https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/ linux-6.14.y
git checkout FETCH_HEAD
git cherry-pick -x a239c6e91b665f1837cf57b97fe638ef1baf2e78
# <resolve conflicts, build, test, etc.>
git commit -s
git send-email --to '<stable@vger.kernel.org>' --in-reply-to '2025040309-kabob-graph-ed91@gregkh' --subject-prefix 'PATCH 6.14.y' HEAD^..
Possible dependencies:
thanks,
greg k-h
------------------ original commit in Linus's tree ------------------
From a239c6e91b665f1837cf57b97fe638ef1baf2e78 Mon Sep 17 00:00:00 2001
From: Dave Penkler <dpenkler@gmail.com>
Date: Sat, 22 Feb 2025 17:58:17 +0100
Subject: [PATCH] staging: gpib: Fix Oops after disconnect in ni_usb
If the usb dongle is disconnected subsequent calls to the
driver cause a NULL dereference Oops as the bus_interface
is set to NULL on disconnect.
This problem was introduced by setting usb_dev from the bus_interface
for dev_xxx messages.
Previously bus_interface was checked for NULL only in the the functions
directly calling usb_fill_bulk_urb or usb_control_msg.
Check for valid bus_interface on all interface entry points
and return -ENODEV if it is NULL.
Fixes: 4934b98bb243 ("staging: gpib: Update messaging and usb_device refs in ni_usb")
Cc: stable <stable@kernel.org>
Signed-off-by: Dave Penkler <dpenkler@gmail.com>
Link: https://lore.kernel.org/r/20250222165817.12856-1-dpenkler@gmail.com
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
diff --git a/drivers/staging/gpib/ni_usb/ni_usb_gpib.c b/drivers/staging/gpib/ni_usb/ni_usb_gpib.c
index 61b15b19e134..62fbc78204ce 100644
--- a/drivers/staging/gpib/ni_usb/ni_usb_gpib.c
+++ b/drivers/staging/gpib/ni_usb/ni_usb_gpib.c
@@ -591,7 +591,7 @@ static int ni_usb_read(gpib_board_t *board, uint8_t *buffer, size_t length,
{
int retval, parse_retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
static const int out_data_length = 0x20;
int in_data_length;
@@ -604,8 +604,11 @@ static int ni_usb_read(gpib_board_t *board, uint8_t *buffer, size_t length,
struct ni_usb_register reg;
*bytes_read = 0;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
if (length > max_read_length)
return -EINVAL;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
out_data = kmalloc(out_data_length, GFP_KERNEL);
if (!out_data)
return -ENOMEM;
@@ -718,7 +721,7 @@ static int ni_usb_write(gpib_board_t *board, uint8_t *buffer, size_t length,
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
int out_data_length;
static const int in_data_length = 0x10;
@@ -728,9 +731,11 @@ static int ni_usb_write(gpib_board_t *board, uint8_t *buffer, size_t length,
struct ni_usb_status_block status;
static const int max_write_length = 0xffff;
- *bytes_written = 0;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
if (length > max_write_length)
return -EINVAL;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
out_data_length = length + 0x10;
out_data = kmalloc(out_data_length, GFP_KERNEL);
if (!out_data)
@@ -819,7 +824,7 @@ static int ni_usb_command_chunk(gpib_board_t *board, uint8_t *buffer, size_t len
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
int out_data_length;
static const int in_data_length = 0x10;
@@ -831,8 +836,11 @@ static int ni_usb_command_chunk(gpib_board_t *board, uint8_t *buffer, size_t len
static const int max_command_length = 0x10;
*command_bytes_written = 0;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
if (length > max_command_length)
length = max_command_length;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
out_data_length = length + 0x10;
out_data = kmalloc(out_data_length, GFP_KERNEL);
if (!out_data)
@@ -925,7 +933,7 @@ static int ni_usb_take_control(gpib_board_t *board, int synchronous)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
static const int out_data_length = 0x10;
static const int in_data_length = 0x10;
@@ -933,6 +941,9 @@ static int ni_usb_take_control(gpib_board_t *board, int synchronous)
int i = 0;
struct ni_usb_status_block status;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
out_data = kmalloc(out_data_length, GFP_KERNEL);
if (!out_data)
return -ENOMEM;
@@ -983,7 +994,7 @@ static int ni_usb_go_to_standby(gpib_board_t *board)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
static const int out_data_length = 0x10;
static const int in_data_length = 0x20;
@@ -991,6 +1002,9 @@ static int ni_usb_go_to_standby(gpib_board_t *board)
int i = 0;
struct ni_usb_status_block status;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
out_data = kmalloc(out_data_length, GFP_KERNEL);
if (!out_data)
return -ENOMEM;
@@ -1039,11 +1053,14 @@ static void ni_usb_request_system_control(gpib_board_t *board, int request_contr
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
int i = 0;
struct ni_usb_register writes[4];
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return; // -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
if (request_control) {
writes[i].device = NIUSB_SUBDEV_TNT4882;
writes[i].address = CMDR;
@@ -1087,7 +1104,7 @@ static void ni_usb_interface_clear(gpib_board_t *board, int assert)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
static const int out_data_length = 0x10;
static const int in_data_length = 0x10;
@@ -1095,7 +1112,10 @@ static void ni_usb_interface_clear(gpib_board_t *board, int assert)
int i = 0;
struct ni_usb_status_block status;
- // FIXME: we are going to pulse when assert is true, and ignore otherwise
+ if (!ni_priv->bus_interface)
+ return; // -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+// FIXME: we are going to pulse when assert is true, and ignore otherwise
if (assert == 0)
return;
out_data = kmalloc(out_data_length, GFP_KERNEL);
@@ -1133,10 +1153,13 @@ static void ni_usb_remote_enable(gpib_board_t *board, int enable)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
struct ni_usb_register reg;
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return; // -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
reg.device = NIUSB_SUBDEV_TNT4882;
reg.address = nec7210_to_tnt4882_offset(AUXMR);
if (enable)
@@ -1180,11 +1203,14 @@ static unsigned int ni_usb_update_status(gpib_board_t *board, unsigned int clear
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
static const int buffer_length = 8;
u8 *buffer;
struct ni_usb_status_block status;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
buffer = kmalloc(buffer_length, GFP_KERNEL);
if (!buffer)
return board->status;
@@ -1232,11 +1258,14 @@ static int ni_usb_primary_address(gpib_board_t *board, unsigned int address)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
int i = 0;
struct ni_usb_register writes[2];
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
writes[i].device = NIUSB_SUBDEV_TNT4882;
writes[i].address = nec7210_to_tnt4882_offset(ADR);
writes[i].value = address;
@@ -1287,11 +1316,14 @@ static int ni_usb_secondary_address(gpib_board_t *board, unsigned int address, i
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
int i = 0;
struct ni_usb_register writes[3];
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
i += ni_usb_write_sad(writes, address, enable);
retval = ni_usb_write_registers(ni_priv, writes, i, &ibsta);
if (retval < 0) {
@@ -1306,7 +1338,7 @@ static int ni_usb_parallel_poll(gpib_board_t *board, uint8_t *result)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
static const int out_data_length = 0x10;
static const int in_data_length = 0x20;
@@ -1315,6 +1347,9 @@ static int ni_usb_parallel_poll(gpib_board_t *board, uint8_t *result)
int j = 0;
struct ni_usb_status_block status;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
out_data = kmalloc(out_data_length, GFP_KERNEL);
if (!out_data)
return -ENOMEM;
@@ -1358,11 +1393,14 @@ static void ni_usb_parallel_poll_configure(gpib_board_t *board, uint8_t config)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
int i = 0;
struct ni_usb_register writes[1];
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return; // -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
writes[i].device = NIUSB_SUBDEV_TNT4882;
writes[i].address = nec7210_to_tnt4882_offset(AUXMR);
writes[i].value = PPR | config;
@@ -1380,11 +1418,14 @@ static void ni_usb_parallel_poll_response(gpib_board_t *board, int ist)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
int i = 0;
struct ni_usb_register writes[1];
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return; // -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
writes[i].device = NIUSB_SUBDEV_TNT4882;
writes[i].address = nec7210_to_tnt4882_offset(AUXMR);
if (ist)
@@ -1405,11 +1446,14 @@ static void ni_usb_serial_poll_response(gpib_board_t *board, u8 status)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
int i = 0;
struct ni_usb_register writes[1];
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return; // -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
writes[i].device = NIUSB_SUBDEV_TNT4882;
writes[i].address = nec7210_to_tnt4882_offset(SPMR);
writes[i].value = status;
@@ -1432,11 +1476,14 @@ static void ni_usb_return_to_local(gpib_board_t *board)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
int i = 0;
struct ni_usb_register writes[1];
unsigned int ibsta;
+ if (!ni_priv->bus_interface)
+ return; // -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
writes[i].device = NIUSB_SUBDEV_TNT4882;
writes[i].address = nec7210_to_tnt4882_offset(AUXMR);
writes[i].value = AUX_RTL;
@@ -1454,7 +1501,7 @@ static int ni_usb_line_status(const gpib_board_t *board)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
u8 *out_data, *in_data;
static const int out_data_length = 0x20;
static const int in_data_length = 0x20;
@@ -1464,6 +1511,9 @@ static int ni_usb_line_status(const gpib_board_t *board)
int line_status = ValidALL;
// NI windows driver reads 0xd(HSSEL), 0xc (ARD0), 0x1f (BSR)
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
out_data = kmalloc(out_data_length, GFP_KERNEL);
if (!out_data)
return -ENOMEM;
@@ -1570,12 +1620,15 @@ static unsigned int ni_usb_t1_delay(gpib_board_t *board, unsigned int nano_sec)
{
int retval;
struct ni_usb_priv *ni_priv = board->private_data;
- struct usb_device *usb_dev = interface_to_usbdev(ni_priv->bus_interface);
+ struct usb_device *usb_dev;
struct ni_usb_register writes[3];
unsigned int ibsta;
unsigned int actual_ns;
int i;
+ if (!ni_priv->bus_interface)
+ return -ENODEV;
+ usb_dev = interface_to_usbdev(ni_priv->bus_interface);
i = ni_usb_setup_t1_delay(writes, nano_sec, &actual_ns);
retval = ni_usb_write_registers(ni_priv, writes, i, &ibsta);
if (retval < 0) {
reply other threads:[~2025-04-03 14:35 UTC|newest]
Thread overview: [no followups] expand[flat|nested] mbox.gz Atom feed
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=2025040309-kabob-graph-ed91@gregkh \
--to=gregkh@linuxfoundation.org \
--cc=dpenkler@gmail.com \
--cc=stable@kernel.org \
--cc=stable@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.