Move the lock into the request.

git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@30100 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Michael Lotz
2009-04-10 08:05:17 +00:00
parent 2ecebae14f
commit da4c99002d
4 changed files with 45 additions and 34 deletions
@@ -22,7 +22,6 @@ ATAChannel::ATAChannel(device_node *node)
fUseDMA(true),
fRequest(NULL)
{
mutex_init(&fExecutionLock, "ata io execution");
B_INITIALIZE_SPINLOCK(&fInterruptLock);
fInterruptCondition.Init(this, "ata dma transfer");
@@ -57,7 +56,7 @@ ATAChannel::ATAChannel(device_node *node)
}
}
fRequest = new(std::nothrow) ATARequest();
fRequest = new(std::nothrow) ATARequest(true);
if (fRequest == NULL) {
fStatus = B_NO_MEMORY;
return;
@@ -90,8 +89,6 @@ ATAChannel::ATAChannel(device_node *node)
ATAChannel::~ATAChannel()
{
mutex_lock(&fExecutionLock);
if (fDevices) {
for (uint8 i = 0; i < fDeviceCount; i++)
delete fDevices[i];
@@ -99,7 +96,6 @@ ATAChannel::~ATAChannel()
}
delete fRequest;
mutex_destroy(&fExecutionLock);
}
@@ -222,16 +218,14 @@ status_t
ATAChannel::ExecuteIO(scsi_ccb *ccb)
{
TRACE_FUNCTION("%p\n", ccb);
if (mutex_trylock(&fExecutionLock) != B_OK) {
TRACE("channel is busy\n");
return B_BUSY;
}
status_t result = fRequest->Start(ccb);
if (result != B_OK)
return result;
fRequest->SetCCB(ccb);
if (ccb->cdb[0] == SCSI_OP_REQUEST_SENSE) {
TRACE("request sense\n");
fRequest->RequestSense();
fRequest->Finish(false, &fExecutionLock);
fRequest->Finish(false);
return B_OK;
}
@@ -241,7 +235,7 @@ ATAChannel::ExecuteIO(scsi_ccb *ccb)
if (ccb->target_id >= fDeviceCount) {
TRACE_ERROR("invalid target device\n");
fRequest->SetStatus(SCSI_SEL_TIMEOUT);
fRequest->Finish(false, &fExecutionLock);
fRequest->Finish(false);
return B_BAD_INDEX;
}
@@ -249,15 +243,15 @@ ATAChannel::ExecuteIO(scsi_ccb *ccb)
if (device == NULL) {
TRACE_ERROR("target device not present\n");
fRequest->SetStatus(SCSI_SEL_TIMEOUT);
fRequest->Finish(false, &fExecutionLock);
fRequest->Finish(false);
return B_BAD_INDEX;
}
fRequest->SetTimeout(ccb->timeout > 0 ? ccb->timeout * 1000 * 1000
: ATA_STANDARD_TIMEOUT);
status_t result = device->ExecuteIO(fRequest);
fRequest->Finish(false, &fExecutionLock);
result = device->ExecuteIO(fRequest);
fRequest->Finish(false);
return result;
}
@@ -299,7 +299,7 @@ ATADevice::SetFeature(int feature)
{
TRACE("device_set_feature: feature %d\n", feature);
ATARequest request;
ATARequest request(false);
request.SetDevice(this);
request.SetTimeout(1 * 1000 * 1000);
@@ -464,7 +464,7 @@ ATADevice::Identify()
snprintf(fDebugContext, sizeof(fDebugContext), "%s %lu-%u",
IsATAPI() ? "pi " : "", fChannel->ChannelID(), fIndex);
ATARequest request;
ATARequest request(false);
request.SetDevice(this);
request.SetTimeout(20 * 1000 * 1000);
@@ -138,7 +138,6 @@ private:
ata_controller_interface * fController;
void * fCookie;
mutex fExecutionLock;
spinlock fInterruptLock;
ConditionVariable fInterruptCondition;
ConditionVariableEntry fInterruptConditionEntry;
@@ -240,7 +239,8 @@ private:
class ATARequest {
public:
ATARequest();
ATARequest(bool hasLock);
~ATARequest();
void SetStatus(uint8 status);
uint8 Status() { return fStatus; };
@@ -266,11 +266,10 @@ public:
void SetBlocksLeft(uint32 blocksLeft);
uint32 * BlocksLeft() { return &fBlocksLeft; };
status_t Finish(bool resubmit,
mutex *mutexToUnlock);
status_t Finish(bool resubmit);
// SCSI stuff
void SetCCB(scsi_ccb *ccb);
status_t Start(scsi_ccb *ccb);
scsi_ccb * CCB() { return fCCB; };
void PrepareSGInfo();
@@ -293,6 +292,9 @@ private:
const char * _DebugContext() { return " request"; };
mutex fLock;
bool fHasLock;
uint8 fStatus;
uint8 fSenseKey;
uint8 fSenseCode;
@@ -5,18 +5,29 @@
#include "ATAPrivate.h"
ATARequest::ATARequest()
: fDevice(NULL),
ATARequest::ATARequest(bool hasLock)
: fHasLock(hasLock),
fDevice(NULL),
fTimeout(0),
fBlocksLeft(0),
fIsWrite(false),
fUseDMA(false),
fCCB(NULL)
{
if (hasLock)
mutex_init(&fLock, "ata request");
ClearSense();
}
ATARequest::~ATARequest()
{
if (fHasLock)
mutex_destroy(&fLock);
}
void
ATARequest::SetStatus(uint8 status)
{
@@ -76,7 +87,19 @@ ATARequest::SetBlocksLeft(uint32 blocksLeft)
status_t
ATARequest::Finish(bool resubmit, mutex *mutexToUnlock)
ATARequest::Start(scsi_ccb *ccb)
{
if (mutex_trylock(&fLock) != B_OK)
return B_BUSY;
fCCB = ccb;
fStatus = SCSI_REQ_CMP;
return B_OK;
}
status_t
ATARequest::Finish(bool resubmit)
{
// when the request completed and has set sense
// data, report this to the scsi stack by setting
@@ -102,7 +125,7 @@ ATARequest::Finish(bool resubmit, mutex *mutexToUnlock)
} else
fCCB->subsys_status = fStatus;
mutex_unlock(mutexToUnlock);
mutex_unlock(&fLock);
if (resubmit)
gSCSIModule->resubmit(fCCB);
@@ -113,14 +136,6 @@ ATARequest::Finish(bool resubmit, mutex *mutexToUnlock)
}
void
ATARequest::SetCCB(scsi_ccb *ccb)
{
fCCB = ccb;
fStatus = SCSI_REQ_CMP;
}
void
ATARequest::RequestSense()
{