* For multi function devices it is not so unlikely to try to do multiple

concurent SendRequest() calls. Therefore it's probably a good idea to
  protect that, now that the request data is not dynamically allocated anymore.
* Fix warning about not returning a result in the compatibility version of
  init_mutex_etc() (which wouldn't make a difference as the Haiku version
  does not return anything).

git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@25707 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Michael Lotz
2008-05-29 17:48:41 +00:00
parent cfccb35af6
commit c7d757a074
3 changed files with 18 additions and 5 deletions
@@ -55,7 +55,7 @@ mutex_init(mutex *ben, const char *name)
inline status_t inline status_t
mutex_init_etc(mutex *ben, const char *name, int32 flags) mutex_init_etc(mutex *ben, const char *name, int32 flags)
{ {
mutex_init(ben, name); return mutex_init(ben, name);
} }
+16 -4
View File
@@ -293,6 +293,7 @@ ControlPipe::ControlPipe(Object *parent)
: Pipe(parent), : Pipe(parent),
fNotifySem(-1) fNotifySem(-1)
{ {
mutex_init(&fSendRequestLock, "control pipe send request");
} }
@@ -300,6 +301,7 @@ ControlPipe::~ControlPipe()
{ {
if (fNotifySem >= 0) if (fNotifySem >= 0)
delete_sem(fNotifySem); delete_sem(fNotifySem);
mutex_destroy(&fSendRequestLock);
} }
@@ -308,16 +310,24 @@ ControlPipe::SendRequest(uint8 requestType, uint8 request, uint16 value,
uint16 index, uint16 length, void *data, size_t dataLength, uint16 index, uint16 length, void *data, size_t dataLength,
size_t *actualLength) size_t *actualLength)
{ {
status_t result = mutex_lock(&fSendRequestLock);
if (result != B_OK)
return result;
if (fNotifySem < 0) { if (fNotifySem < 0) {
fNotifySem = create_sem(0, "usb send request notify"); fNotifySem = create_sem(0, "usb send request notify");
if (fNotifySem < 0) if (fNotifySem < 0) {
mutex_unlock(&fSendRequestLock);
return B_NO_MORE_SEMS; return B_NO_MORE_SEMS;
}
} }
status_t result = QueueRequest(requestType, request, value, index, length, result = QueueRequest(requestType, request, value, index, length, data,
data, dataLength, SendRequestCallback, this); dataLength, SendRequestCallback, this);
if (result < B_OK) if (result < B_OK) {
mutex_unlock(&fSendRequestLock);
return result; return result;
}
// The sem will be released unconditionally in the callback after the // The sem will be released unconditionally in the callback after the
// result data was filled in. Use a 1 second timeout for control transfers. // result data was filled in. Use a 1 second timeout for control transfers.
@@ -334,12 +344,14 @@ ControlPipe::SendRequest(uint8 requestType, uint8 request, uint16 value,
if (actualLength) if (actualLength)
*actualLength = 0; *actualLength = 0;
mutex_unlock(&fSendRequestLock);
return B_TIMED_OUT; return B_TIMED_OUT;
} }
if (actualLength) if (actualLength)
*actualLength = fActualLength; *actualLength = fActualLength;
mutex_unlock(&fSendRequestLock);
return fTransferStatus; return fTransferStatus;
} }
@@ -334,6 +334,7 @@ static void SendRequestCallback(void *cookie,
void *callbackCookie); void *callbackCookie);
private: private:
mutex fSendRequestLock;
sem_id fNotifySem; sem_id fNotifySem;
status_t fTransferStatus; status_t fTransferStatus;
size_t fActualLength; size_t fActualLength;