📄 asyncapi.c
字号:
pLoopbackParams->AddressOffset.Off_Low;
pAsyncWrite->nBlockSize = 0;
pAsyncWrite->fulFlags = 0;
pAsyncWrite->bRawMode = FALSE;
pAsyncWrite->bGetGeneration = TRUE;
}
// read...
if (pLoopbackParams->ulLoopFlag & ASYNC_LOOPBACK_READ) {
ulReadSize = sizeof(ASYNC_READ) + pLoopbackParams->nMaxBytes;
pAsyncRead = (PASYNC_READ)LocalAlloc(LPTR, ulReadSize);
if (!pAsyncRead) {
dwRet = GetLastError();
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "Could not allocate pAsyncRead\r\n"));
goto Exit_AsyncLoopbackThread;
}
FillMemory(pAsyncRead, ulReadSize, 0);
// setup our values in the read buffer
pAsyncRead->DestinationAddress.IA_Destination_Offset.Off_High =
pLoopbackParams->AddressOffset.Off_High;
pAsyncRead->DestinationAddress.IA_Destination_Offset.Off_Low =
pLoopbackParams->AddressOffset.Off_Low;
pAsyncRead->nBlockSize = 0;
pAsyncRead->fulFlags = 0;
pAsyncRead->bRawMode = FALSE;
pAsyncRead->bGetGeneration = TRUE;
}
// lock...
if (pLoopbackParams->ulLoopFlag & ACCESS_FLAGS_TYPE_LOCK) {
// TODO: Add lock setup here
}
// loop until the thread is killed
while (TRUE) {
bFailed = FALSE;
// lets see what type of loopback this is. we'll go through and
// process and reads, writes, or locks...
// lets get our buffer size...
if (pLoopbackParams->ulLoopFlag & ASYNC_LOOPBACK_RANDOM_LENGTH) {
ulBufferSize = rand() % pLoopbackParams->nMaxBytes;
ulBufferSize++;
}
else {
ulBufferSize = pLoopbackParams->nMaxBytes;
}
// write...
if ((!pLoopbackParams->bKill) && (pLoopbackParams->ulLoopFlag & ACCESS_FLAGS_TYPE_WRITE)) {
ULONG i;
// set the size/data buffer for our write
pAsyncWrite->nNumberOfBytesToWrite = ulBufferSize;
for (i=0; i<pAsyncWrite->nNumberOfBytesToWrite/sizeof(ULONG); i++) {
CopyMemory((ULONG *)&pAsyncWrite->Data+i, (ULONG *)&i, sizeof(ULONG));
}
dwRet = DeviceIoControl( hDevice,
IOCTL_ASYNC_WRITE,
pAsyncWrite,
sizeof(ASYNC_WRITE) + ulBufferSize,
pAsyncWrite,
sizeof(ASYNC_WRITE) + ulBufferSize,
&dwBytesRet,
NULL
);
if (!dwRet) {
dwRet = GetLastError();
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "Error = 0x%x\r\n", dwRet));
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "Write Failed\r\n"));
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "pAsyncWrite = 0x%p\r\n", pAsyncWrite));
// see if this is a generation error, if so, we'll assume
// a bus reset and continue
if (dwRet != ERROR_MR_MID_NOT_FOUND) {
// we had a failure, up the fail count...
if (dwRet != ERROR_OPERATION_ABORTED)
bFailed = TRUE;
}
else {
TRACE(TL_WARNING, (pLoopbackParams->hWnd, "Write - Invalid Generation!\r\n"));
}
}
} // write
// read
if ((!bFailed) && (!pLoopbackParams->bKill) && (pLoopbackParams->ulLoopFlag & ACCESS_FLAGS_TYPE_READ)) {
// set the size/data buffer for our read
pAsyncRead->nNumberOfBytesToRead = ulBufferSize;
FillMemory(&pAsyncRead->Data, ulBufferSize, 0);
dwRet = DeviceIoControl( hDevice,
IOCTL_ASYNC_READ,
pAsyncRead,
sizeof(ASYNC_READ) + ulBufferSize,
pAsyncRead,
sizeof(ASYNC_READ) + ulBufferSize,
&dwBytesRet,
NULL
);
if (!dwRet) {
dwRet = GetLastError();
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "Error = 0x%x\r\n", dwRet));
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "Read Failed\r\n"));
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "pAsyncRead = 0x%p\r\n", pAsyncRead));
// see if this is a generation error, if so, we'll assume
// a bus reset and continue
if (dwRet != ERROR_MR_MID_NOT_FOUND) {
// we had a failure, up the fail count...
if (dwRet != ERROR_OPERATION_ABORTED)
bFailed = TRUE;
}
else {
TRACE(TL_WARNING, (pLoopbackParams->hWnd, "Read - Invalid Generation!\r\n"));
}
}
else {
if (pLoopbackParams->ulLoopFlag & ACCESS_FLAGS_TYPE_WRITE) {
ULONG ulResult;
ulResult = memcmp(pAsyncWrite->Data, pAsyncRead->Data, ulBufferSize);
if (ulResult != 0)
bFailed = TRUE;
else
bFailed = FALSE;
if (bFailed) {
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "ulResult = 0x%x\r\n", ulResult));
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "pAsyncWrite = 0x%p\r\n", pAsyncWrite));
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "pAsyncRead = 0x%p\r\n", pAsyncRead));
}
}
}
} // read
// lock
if ((!pLoopbackParams->bKill) && (pLoopbackParams->ulLoopFlag & ACCESS_FLAGS_TYPE_LOCK)) {
// TODO: Add lock testing here
} // lock
// increment our counters...
if (!pLoopbackParams->bKill) {
if (bFailed)
pLoopbackParams->ulFail++;
else
pLoopbackParams->ulPass++;
pLoopbackParams->ulIterations++;
// if we reached our iteration count, then lets exit...
if (pLoopbackParams->ulIterations == pLoopbackParams->nIterations)
pLoopbackParams->bKill = TRUE;
}
// see if we have been shut down
if (pLoopbackParams->bKill) {
// we've been shutdown
break;
}
} // while
Exit_AsyncLoopbackThread:
// free up all resources
CloseHandle(hDevice);
if (pAsyncWrite)
LocalFree(pAsyncWrite);
if (pAsyncRead)
LocalFree(pAsyncRead);
if (pAsyncLock)
LocalFree(pAsyncLock);
} // if
// that's it, shut this thread down
ExitThread(0);
return(0);
} // AsyncLoopbackThread
void
WINAPI
AsyncStartLoopbackEx(
HWND hWnd,
PSTR szDeviceName,
PASYNC_LOOPBACK_PARAMS_EX asyncLoopbackParamsEx
)
{
asyncLoopbackParamsEx->szDeviceName = szDeviceName;
asyncLoopbackParamsEx->hWnd = hWnd;
asyncLoopbackParamsEx->bKill = FALSE;
asyncLoopbackParamsEx->hThread = CreateThread( NULL,
0,
AsyncLoopbackThreadEx,
(LPVOID) asyncLoopbackParamsEx,
0,
&asyncLoopbackParamsEx->ThreadId
);
} // AsyncStartLoopbackEx
void
WINAPI
AsyncStopLoopbackEx(
PASYNC_LOOPBACK_PARAMS_EX asyncLoopbackParamsEx
)
{
// kill the thread
asyncLoopbackParamsEx->bKill = TRUE;
// wait for the thread to exit before returning
WaitForSingleObjectEx(asyncLoopbackParamsEx->hThread,
INFINITE,
FALSE);
// close the handle
CloseHandle(asyncLoopbackParamsEx->hThread);
return;
} // AsyncStopLoopbackEx
DWORD
WINAPI
AsyncLoopbackThreadEx(
LPVOID lpParameter
)
{
PASYNC_LOOPBACK_PARAMS_EX pLoopbackParams = NULL;
PASYNC_READ pAsyncRead = NULL;
PASYNC_WRITE pAsyncWrite = NULL;
PVOID pAsyncLock = NULL;
HANDLE hDevice;
DWORD dwRet, dwBytesRet;
ULONG ulReadSize;
ULONG ulWriteSize;
ULONG ulLockSize;
ULONG ulBufferSize;
BOOLEAN bFailed = FALSE;
// get pointer to our thread parameters
pLoopbackParams = (PASYNC_LOOPBACK_PARAMS_EX)lpParameter;
// reset pass/fail iteration counts
pLoopbackParams->ulPass = 0;
pLoopbackParams->ulFail = 0;
pLoopbackParams->ulIterations = 0;
// try to open the device
hDevice = OpenDevice(pLoopbackParams->hWnd, pLoopbackParams->szDeviceName, FALSE);
// device opened, so let's do loopback
if (hDevice != INVALID_HANDLE_VALUE) {
// lets get our buffers setup for whatever loopback we're doing.
// see if we want random sized buffers...
if (pLoopbackParams->ulLoopFlag & ASYNC_LOOPBACK_RANDOM_LENGTH) {
// lets get a random buffer size that's under our max bytes to read
srand((unsigned) time(NULL));
}
// write...
if (pLoopbackParams->ulLoopFlag & ASYNC_LOOPBACK_WRITE) {
ulWriteSize = sizeof(ASYNC_WRITE) + pLoopbackParams->nMaxBytes;
pAsyncWrite = (PASYNC_WRITE)LocalAlloc(LPTR, ulWriteSize);
if (!pAsyncWrite) {
dwRet = GetLastError();
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "Could not allocate pAsyncWrite\r\n"));
goto Exit_AsyncLoopbackThread;
}
FillMemory(pAsyncWrite, ulWriteSize, 0);
// setup our values in the write buffer
pAsyncWrite->DestinationAddress.IA_Destination_ID =
pLoopbackParams->Destination.IA_Destination_ID;
pAsyncWrite->DestinationAddress.IA_Destination_Offset.Off_High =
pLoopbackParams->Destination.IA_Destination_Offset.Off_High;
pAsyncWrite->DestinationAddress.IA_Destination_Offset.Off_Low =
pLoopbackParams->Destination.IA_Destination_Offset.Off_Low;
pAsyncWrite->nBlockSize = 0;
pAsyncWrite->fulFlags = 0;
pAsyncWrite->bRawMode = pLoopbackParams->bRawMode;
pAsyncWrite->bGetGeneration = TRUE;
}
// read...
if (pLoopbackParams->ulLoopFlag & ASYNC_LOOPBACK_READ) {
ulReadSize = sizeof(ASYNC_READ) + pLoopbackParams->nMaxBytes;
pAsyncRead = (PASYNC_READ)LocalAlloc(LPTR, ulReadSize);
if (!pAsyncRead) {
dwRet = GetLastError();
TRACE(TL_ERROR, (pLoopbackParams->hWnd, "Could not allocate pAsyncRead\r\n"));
goto Exit_AsyncLoopbackThread;
}
FillMemory(pAsyncRead, ulReadSize, 0);
// setup our values in the read buffer
pAsyncRead->DestinationAddress.IA_Destination_ID =
pLoopbackParams->Destination.IA_Destination_ID;
pAsyncRead->DestinationAddress.IA_Destination_Offset.Off_High =
pLoopbackParams->Destination.IA_Destination_Offset.Off_High;
pAsyncRead->DestinationAddress.IA_Destination_Offset.Off_Low =
pLoopbackParams->Destination.IA_Destination_Offset.Off_Low;
pAsyncRead->nBlockSize = 0;
pAsyncRead->fulFlags = 0;
pAsyncRead->bRawMode = pLoopbackParams->bRawMode;
pAsyncRead->bGetGeneration = TRUE;
}
// lock...
if (pLoopbackParams->ulLoopFlag & ACCESS_FLAGS_TYPE_LOCK) {
}
// loop until the thread is killed
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -