From dab68c33ed20488e352cd018d4653ba6c600ef81 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Stephan=20A=C3=9Fmus?= Date: Mon, 27 Oct 2008 16:52:39 +0000 Subject: [PATCH] * When a device closes, delete the transfer semaphore, so that threads blocking on it are unblocked and get an error. * Make fOpen volatile to prevent unwanted caching effects when checking it from different threads. (?) * Check IsOpen() in the KeyboardDevice class in more acquire_sem_etc() return cases, analogous to the MouseDevice class. I am still getting a problem when relaunching input_server with the input_server add-on thread that ioctl()s on a USB keyboard fd, which should have never fired because it's a fake device from a KVM. After the first input_server instance is gone, this thread keeps on busy looping in acquire_sem_etc()->switch_sem() from within the ioctl() of the KeyboardDevice usb_hid driver. Still on it. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@28350 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.cpp | 5 +++++ src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.h | 2 +- src/add-ons/kernel/drivers/input/usb_hid/KeyboardDevice.cpp | 6 +++--- 3 files changed, 9 insertions(+), 4 deletions(-) diff --git a/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.cpp b/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.cpp index 0ca2c4b74b..4fb955cfa1 100644 --- a/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.cpp +++ b/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.cpp @@ -240,6 +240,11 @@ status_t HIDDevice::Close() { fOpen = false; + // make threads waiting for a transfer bail out + if (fTransferNotifySem >= 0) { + delete_sem(fTransferNotifySem); + fTransferNotifySem = -1; + } return B_OK; } diff --git a/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.h b/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.h index 3acb560785..656b901dd4 100644 --- a/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.h +++ b/src/add-ons/kernel/drivers/input/usb_hid/HIDDevice.h @@ -78,7 +78,7 @@ static void _TransferCallback(void *cookie, char * fName; int32 fParentCookie; - bool fOpen; +volatile bool fOpen; bool fRemoved; struct ring_buffer * fRingBuffer; diff --git a/src/add-ons/kernel/drivers/input/usb_hid/KeyboardDevice.cpp b/src/add-ons/kernel/drivers/input/usb_hid/KeyboardDevice.cpp index dc24391cf4..170042c803 100644 --- a/src/add-ons/kernel/drivers/input/usb_hid/KeyboardDevice.cpp +++ b/src/add-ons/kernel/drivers/input/usb_hid/KeyboardDevice.cpp @@ -65,15 +65,15 @@ KeyboardDevice::Control(uint32 op, void *buffer, size_t length) _SetTransferProcessed(); if (result != B_OK) return result; - } else if (result == B_TIMED_OUT) { + } else if (result == B_TIMED_OUT && IsOpen()) { // this case is for handling key repeats, it means // no interrupt transfer has happened _WriteKey(fCurrentRepeatKey, true); // the next timeout is reduced to the repeat_rate fCurrentRepeatDelay = fRepeatRate; - } else if (result == B_INTERRUPTED) + } else if (result == B_INTERRUPTED && IsOpen()) { continue; - else if (result != B_OK) + } else return result; }