⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pcietest.cpp

📁 基于xilinx vierex5得pci express dma设计实现。
💻 CPP
📖 第 1 页 / 共 3 页
字号:

    if (ProcessorCount == 1) {
        ThreadCount = DEFAULT_THREAD_COUNT;
    } else {
        ThreadCount = ProcessorCount;
    }

    Contexts = new THREAD_CONTEXT[ThreadCount];
    Threads = new HANDLE[ThreadCount];

    if (Contexts == NULL || Threads == NULL) {
        return FALSE;
    }

    if (hDevice == INVALID_HANDLE_VALUE) {
        status = GetDeviceHandle();
    }

    if (!Quite) {
        printf("Creating %d threads...\n", ThreadCount);
    }

    pAffinity = 1;

    for(i = 0; i < ThreadCount; i++) {

        if ((i % 2) == 0) {

            //
            //  Create Read Thread
            //
            Contexts[i].hDevice = hDevice;
            Contexts[i].BufferSize = ReadBufferSize;
            Contexts[i].Buffer = new UCHAR[ReadBufferSize];
            Contexts[i].quite  = Quite;

            hThread = CreateThread(NULL,
                                   0,
                                   ReadThreadProc,
                                   &Contexts[i],
                                   0,
                                   NULL);

            if (NULL == hThread) {
                printf( "Failed to create thread %d\n", i );
                this->Status = 1;
                break;

            } else {
                Threads[i] = hThread;
            }

        } else {

            //
            //  Create Write Thread
            //
            Contexts[i].hDevice = hDevice;
            Contexts[i].BufferSize = WriteBufferSize;
            Contexts[i].Buffer = new UCHAR[WriteBufferSize];
            Contexts[i].quite  = Quite;

            hThread = CreateThread(NULL,
                                   0,
                                   WriteThreadProc,
                                   &Contexts[i],
                                   0,
                                   NULL);

            if (NULL == hThread) {
                printf( "Failed to create thread %d\n", i );
                this->Status = 1;
                break;

            } else {
                Threads[i] = hThread;
            }
        }

        //
        //  Set Affinity
        //
        SetThreadAffinityMask(Threads[i], pAffinity);

        pAffinity = pAffinity << 1;
    }

    if (i != ThreadCount) {

        //
        // some create thread failed, bail out
        //
        printf( "Some CreateThread was failed, stop\n" );
        g_TimeUp = 1;

    } else {

        //
        // wait till either all quit or time is due
        //
        DWORD error;

        error = WaitForMultipleObjects(i, Threads, TRUE, ThreadTimer);

        if (error == WAIT_TIMEOUT) {

            //
            // Stop the threads if time is up
            //
            g_TimeUp = 2;
            error = WaitForMultipleObjects(i, Threads, TRUE, 100000) ;

            if (error) {
                printf("WaitForMultipleObjects[%d] error %d\n", i, error);
            }
        } else {
            if (error) {
                printf("WaitForMultipleObjects[%d] error %d\n", i, error);
            }
        }
    }

    if (Contexts) {
        for (i = 0; i < ThreadCount; i++) {
            if (Contexts[i].Buffer) {
                delete Contexts[i].Buffer;
            }
        }

        delete Contexts;
        Contexts = NULL;
    }

    if (hDevice != INVALID_HANDLE_VALUE) {
        CloseHandle(hDevice);
        hDevice = INVALID_HANDLE_VALUE;
    }

    return status;
}

BOOL
PCIE::DbgTest()
{
    BOOL    status = TRUE;
    ULONG   bytes = 0;
    ULONG   DataBuffer[0x20 * 1024];
    ULONG   InBuffer[256];
    ULONG   OutBuffer[256];
    ULONG   ulBytes;
    int     i;
    int     j;
    __int64 tscStart;
    __int64 tscEnd;
    int     timeInNsRead;
    int     timeInNsWrite;

    FILE    *fp_d2h = fopen("perf_d2h.txt", "w");
    FILE    *fp_h2d = fopen("perf_h2d.txt", "w");


    if ((status == TRUE) && (hDevice == INVALID_HANDLE_VALUE)) {
        status = GetDeviceHandle();
    }


    status = DeviceIoControl(hDevice, IOCTL_GET_BUFFERADDRESS, InBuffer, sizeof(ULONG), OutBuffer, sizeof(ULONG) * 4, &ulBytes, NULL);

    printf("status: %d, ulBytes: %d\n", status, ulBytes);

    if (!status)
    {
        printf("GetLastError(): %d", GetLastError());
    }

    PULONG      pDMABuffer1;
    PULONG      pDMABuffer2;

    pDMABuffer1 = (PULONG)OutBuffer[0];
    pDMABuffer2 = (PULONG)OutBuffer[2];

    printf("Buffer1: 0x%08X, Buffer2: 0x%08X\n", pDMABuffer1, pDMABuffer2);


    pDMABuffer1[0] = 0x11223344;
    pDMABuffer2[0] = 0xaabbccdd;


    if (status) {

        for(j=1; j<=16; ++j)
        {
            memset(DataBuffer, 1, sizeof(DataBuffer));

            // DEVICE WRITE. 
            // in : PVOID address, ULONG size, ULONG count, ULONG pattern 
            // out: ULONG performance
            InBuffer[0] = (ULONG)0x00000020;
            InBuffer[1] = (ULONG)j;
            InBuffer[2] = (ULONG)0x55AA55AA;

            GetCurrentTSC(tscStart);
            status = DeviceIoControl(hDevice, IOCTL_DMA_DEVICE_HOST, InBuffer, sizeof(ULONG) * 3, OutBuffer, sizeof(ULONG) * 3, &ulBytes, NULL);
            GetCurrentTSC(tscEnd);

            //timeInNsRead = (tscEnd - tscStart) * 1000 / nCPUFreq;
            timeInNsRead = (int)(tscEnd - tscStart);

            printf("DEVICE_HOST Performance: %08X\t%08X\t%08X\t%d\n", OutBuffer[0], OutBuffer[1], OutBuffer[2], timeInNsRead);
            printf("DEVICE_HOST DBG: %08X,  %08X\n", pDMABuffer1[0], pDMABuffer2[0]);
            
            fprintf(fp_d2h, "%d\t", j);
            fprintf(fp_d2h, "%d\t%d\t%d\t%d\n", OutBuffer[0], OutBuffer[1], OutBuffer[2], timeInNsRead);
            fflush(fp_d2h);


            // DEVICE READ. 
            // in : PVOID address, ULONG size, ULONG count
            // out: ULONG performance
            InBuffer[0] = (ULONG)0x00000020;
            InBuffer[1] = (ULONG)j;
            
            GetCurrentTSC(tscStart);
            status = DeviceIoControl(hDevice, IOCTL_DMA_HOST_DEVICE, InBuffer, sizeof(ULONG) * 2, OutBuffer, sizeof(ULONG) * 3, &ulBytes, NULL);
            GetCurrentTSC(tscEnd);

            //timeInNsWrite = (tscEnd - tscStart) * 1000 / nCPUFreq;
            timeInNsWrite = (int)(tscEnd - tscStart);

            printf("HOST_DEVICE Performance: %08X\t%08X\t%08X\t%d\n", OutBuffer[0], OutBuffer[1], OutBuffer[2], timeInNsWrite);
            printf("HOST_DEVICE DBG: %08X,  %08X\n", pDMABuffer1[0], pDMABuffer2[0]);
            
            fprintf(fp_h2d, "%d\t", j);
            fprintf(fp_h2d, "%d\t%d\t%d\t%d\n", OutBuffer[0], OutBuffer[1], OutBuffer[2], timeInNsWrite);
            fflush(fp_h2d);
        }
    }

    status = DeviceIoControl(hDevice, IOCTL_FREE_BUFFERADDRESS, InBuffer, sizeof(ULONG), OutBuffer, sizeof(ULONG) * 2, &ulBytes, NULL);

    printf("status: %d, ulBytes: %d\n", status, ulBytes);


    fclose(fp_d2h);
    fclose(fp_h2d);


    printf("OVER\n");

    if (hDevice != INVALID_HANDLE_VALUE) {
        CloseHandle(hDevice);
        hDevice = INVALID_HANDLE_VALUE;
    }

    return status;
}


BOOL
PCIE::FullTest()
{
    BOOL    status = TRUE;
    ULONG   bytes = 0;
    ULONG   DataBuffer[0x20 * 1024];
    ULONG   InBuffer[256];
    ULONG   OutBuffer[256];
    ULONG   ulBytes;
    int     i;
    int     j;
    __int64 tscStart;
    __int64 tscEnd;
    int     timeInNs;

    FILE    *fp = fopen("perf_full.txt", "w");

    if ((status == TRUE) && (hDevice == INVALID_HANDLE_VALUE)) {
        status = GetDeviceHandle();
    }


    if (status) {

        for(j=1; j<=16; ++j)
        {
            memset(DataBuffer, 1, sizeof(DataBuffer));

            // DEVICE WRITE. 
            // in : 
            //    for write:  PVOID dataBuffer, SIZE_T size, SIZE_T count, ULONG pattern
            //    for read :  SIZE_T  size,     SIZE_T count
            // out: 
            //    for write:  ULONG performance, ULONG tscCounter, ULONG tscCounter_Int
            //    for read :  ULONG performance, ULONG tscCounter, ULONG tscCounter_Int
            InBuffer[0] = (ULONG)0x00000020;
            InBuffer[1] = (ULONG)j;
            InBuffer[2] = (ULONG)0x55AA55AA;
            InBuffer[3] = (ULONG)0x00000020;
            InBuffer[4] = (ULONG)j;

            GetCurrentTSC(tscStart);
            status = DeviceIoControl(hDevice, IOCTL_DMA_PCI_TEST, InBuffer, sizeof(ULONG) * 5, OutBuffer, sizeof(ULONG) * 6, &ulBytes, NULL);
            GetCurrentTSC(tscEnd);

            timeInNs = (int)(tscEnd - tscStart);

            printf("PCI_TEST Performance(%03d): %08X\t%08X\t%08X\t%08X\t%08X\t%08X\t%08X\t%d\n", j, 
                DataBuffer[0],
                OutBuffer[0], OutBuffer[1], OutBuffer[2], OutBuffer[3], OutBuffer[4], OutBuffer[5], timeInNs);
            
            fprintf(fp, "%d\t", j);
            fprintf(fp, "%d\t%d\t%d\t%d\t%d\t%d\t%d\n", OutBuffer[0], OutBuffer[1], OutBuffer[2], OutBuffer[3], OutBuffer[4], OutBuffer[5], timeInNs);
        }
    }

    fclose(fp);

    printf("OVER\n");

    if (hDevice != INVALID_HANDLE_VALUE) {
        CloseHandle(hDevice);
        hDevice = INVALID_HANDLE_VALUE;
    }

    return status;
}


BOOL
PCIE::ReadTest()
{
    return DbgTest();
//    return FullTest();

    /*
    BOOL status = TRUE;
    ULONG bytes = 0;

    if (!ReadBuffer) {
        status = FALSE;
    }

    if ((status == TRUE) && (hDevice == INVALID_HANDLE_VALUE)) {
        status = GetDeviceHandle();
    }

    if (status) {
        if (ReadFile(hDevice,
                    ReadBuffer,
                    ReadBufferSize,
                    &bytes,
                    NULL)){

            EnterCriticalSection(&CriticalSection);
            if (!Quite) {
                printf("Read sucessful.\n");
            }
            LeaveCriticalSection(&CriticalSection);

        } else {

            EnterCriticalSection(&CriticalSection);
            printf("Read failed.\n");
            this->Status = 1;
            LeaveCriticalSection(&CriticalSection);
        }
    }

    if (hDevice != INVALID_HANDLE_VALUE) {
        CloseHandle(hDevice);
        hDevice = INVALID_HANDLE_VALUE;
    }

    return status;
    */
}

BOOL
PCIE::WriteTest()
{
    ULONG bytes = 0;
    BOOL status = TRUE;

    if (!WriteBuffer) {
        status = FALSE;
    }

    if ((status == TRUE) && (hDevice == INVALID_HANDLE_VALUE)) {
        status = GetDeviceHandle();
    }

    if (status) {
        FillMemory(WriteBuffer, WriteBufferSize, 0xAB);

        if (WriteFile(hDevice,
                      WriteBuffer,
                      WriteBufferSize,
                      &bytes,
                      NULL)) {

            EnterCriticalSection(&CriticalSection);
            if (!Quite) {
                printf("Write sucessful.\n");
            }
            LeaveCriticalSection(&CriticalSection);

        } else {

            EnterCriticalSection(&CriticalSection);
            printf("Write failed.\n");
            this->Status = 1;
            LeaveCriticalSection(&CriticalSection);
        }
    }

    if (hDevice != INVALID_HANDLE_VALUE) {
        CloseHandle(hDevice);
        hDevice = INVALID_HANDLE_VALUE;
    }

    return status;
}

BOOL
PCIE::ReadWriteTest()
{
    return (WriteTest() && ReadTest() && CompareReadWriteBuffers());
}

BOOL
PCIE::CompareReadWriteBuffers()
{
    BOOL status = TRUE;
    ULONG size;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -