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

📄 hci_bcsp.cpp

📁 CSR蓝牙HCI层驱动源码
💻 CPP
📖 第 1 页 / 共 5 页
字号:
                        sniffCrc = ((sniffCrc & 0x3333) << 2) | ((sniffCrc & 0xcccc) >> 2);
                        sniffCrc = ((sniffCrc & 0x5555) << 1) | ((sniffCrc & 0xaaaa) >> 1);

                        tempBufferSniff[index++] = (sniffCrc >> 8) & 0xFF;
                        tempBufferSniff[index++] = sniffCrc & 0xFF;
                    }

                    HCIFileWritePacket(0, tempBufferSniff, totalLength);

                    LocalFree(tempBufferSniff);
                }
            }


            IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> State: %u"), name, state));

            IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> PACKET OUT (TIME: %u, TYPE: %u, CHL: %u, SEQ: %u, ACK: %u, SIZE: %u, WINDOW: %u, TIP: %u, TP: %u, IN QUEUE: %u)"), 
                            name, GetTickCount(), bcspHeader->protocolType, bcspHeader->protocolID, bcspHeader->seq, bcspHeader->ack, 
                            bcspHeader->payloadLength, transmitWindow, transmitInsertPosition, transmitPosition, 
                            (8 + transmitInsertPosition - transmitPosition) & 0x07));

            outBuffer[outPacketSize++] = 0xC0;

            for (index = 0; index < totalLength; index++)
            {
                unsigned char c;

#ifdef BCSP_TEST_MODE
                if (enableTestMode)
                {
                    if (rand() < properbility.packetSizeErrorProperbility)
                    {
                        break;
                    }
                }
#endif

                if (index < 4)
                {
                    c = bchsPacket[index];
                    if (useCrc)
                    {
                        crc = (crc >> 8) ^ crc_table[(crc & 255) ^ c];
                    }
                }
                else if (index < (4 + (DWORD) bcspHeader->payloadLength))
                {
                    c = bchsPayload[index - 4];
                    if (useCrc)
                    {
                        crc = (crc >> 8) ^ crc_table[(crc & 255) ^ c];
                    }
                }
                else if (index == (4 + (DWORD) bcspHeader->payloadLength))
                {
                    crc = ((crc & 0x00ff) << 8) | (crc >> 8);
                    crc = ((crc & 0x0f0f) << 4) | ((crc & 0xf0f0) >> 4);
                    crc = ((crc & 0x3333) << 2) | ((crc & 0xcccc) >> 2);
                    crc = ((crc & 0x5555) << 1) | ((crc & 0xaaaa) >> 1);

                    c = (crc >> 8) & 0xFF;
                }
                else
                {
                    c = crc & 0xFF;
#ifdef BCSP_TEST_MODE
                    if (enableTestMode)
                    {
                        if (rand() < properbility.packetCrcErrorProperbility)
                        {
                            c += 10;
                        }
                    }
#endif
                }

#ifdef BCSP_TEST_MODE
                if (enableTestMode)
                {
                    int r;

                    if (c == 0xC0)
                    {
                        if ((r = rand()) < properbility.markerErrorProperbility)
                        {
                            if (rand() < (RAND_MAX >> 1))
                            {
                            outBuffer[outPacketSize++] = 0xDA;
                            outBuffer[outPacketSize++] = 0xDC;
                            }
                            else
                            {
                            outBuffer[outPacketSize++] = 0xDB;
                            outBuffer[outPacketSize++] = 0xDF;
                            }
                        }
                        else
                        {
                            outBuffer[outPacketSize++] = 0xDB;
                            outBuffer[outPacketSize++] = 0xDC;
                        }
                    }
                    else if (c == 0xDB)
                    {
                        if ((r = rand()) < properbility.markerErrorProperbility)
                        {
                            if (rand() < (RAND_MAX >> 1))
                            {
                            outBuffer[outPacketSize++] = 0xDA;
                            outBuffer[outPacketSize++] = 0xDD;
                            }
                            else
                            {
                            outBuffer[outPacketSize++] = 0xDB;
                            outBuffer[outPacketSize++] = 0xDF;
                            }
                        }
                        else
                        {
                            outBuffer[outPacketSize++] = 0xDB;
                            outBuffer[outPacketSize++] = 0xDD;
                        }
                    }
                    else
                    {
                        outBuffer[outPacketSize++] = c;
                    }
                }
            else
#endif
                if (c == 0xC0)
                {
                    outBuffer[outPacketSize++] = 0xDB;
                    outBuffer[outPacketSize++] = 0xDC;
                }
                else if (c == 0xDB)
                {
                    outBuffer[outPacketSize++] = 0xDB;
                    outBuffer[outPacketSize++] = 0xDD;
                }
                else
                {
                    outBuffer[outPacketSize++] = c;
                }
            }

            outBuffer[outPacketSize++] = 0xC0;

            LeaveCriticalSection(&lock);

            while (totalWritten < outPacketSize)
            {
                written = 0;
#ifndef UNDER_CE
                if (!WriteFile(serialPortHandle, &outBuffer[totalWritten], outPacketSize - totalWritten, &written, &overlapped))
                {
                    if (GetLastError() != ERROR_IO_PENDING || !GetOverlappedResult(serialPortHandle, &overlapped, &written, TRUE))
                    {
                        IFDBG(DebugOut(DEBUG_BCSP_ERROR, TEXT("<BcspCommunication::WriteExecute@%s> GetOverlappedResult returned: %u"), name, GetLastError()));
                        serialPortError = TRUE;
                        break;
                    }
                }
#else
                if (!WriteFile(serialPortHandle, &outBuffer[totalWritten], outPacketSize - totalWritten, &written, 0))
                {
                    IFDBG(DebugOut(DEBUG_BCSP_ERROR, TEXT("<BcspCommunication::WriteExecute@%s> WriteFile returned: %u"), name, GetLastError()));
                    serialPortError = TRUE;
                    break;
                }
#endif
                totalWritten += written;
            }
            
            EnterCriticalSection(&lock);

            if (totalWritten < outPacketSize || serialPortError)
            {
                serialPortError = TRUE;
                LinkLost();    
                break;
            }

            IFSTAT(outBytes += totalWritten);
            IFSTAT(outPackets++);
        }

        if (state == BCSP_STATE_RUNNING && transmitPositionUnacknowledged != transmitPosition)
        {
            DWORD currentTime = GetTickCount();

            if ((currentTime - transmitQueue[transmitPositionUnacknowledged].transmittedTime) < transmitTimeout)
            {
                currentTimeout = (transmitTimeout + transmitQueue[transmitPositionUnacknowledged].transmittedTime - currentTime);
            }
            else
            {
                currentTimeout = 0;
            }
        }
        else
        {
            IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> STOPPED???"), name));
        }

        IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> PACKET SEND INFO (TransmitWindow: %u, CurrentTimeout: %u, Packet Sent: %s)"), name, transmitWindow, currentTimeout, bcspHeader ? TEXT("true") : TEXT("false")));

        LeaveCriticalSection(&lock);

        result = WaitForSingleObject(writePacketEvent, currentTimeout);

        EnterCriticalSection(&lock);

        IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> WAIT RETURNED"), name));

        if (transmitWindow > 4)
        {
            IFDBG(DebugOut(DEBUG_BCSP_ERROR, TEXT("<BcspCommunication::WriteExecute@%s> TRANSMITWINDOW: %u"), name, transmitWindow));
        }

        if (result == WAIT_TIMEOUT)
        {
            if (transmitWindow < 4)
            {
                unsigned int index;

                IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> RETRY (TransmitWindow: %u, TransmitPosition: %u, TransmitPositionUnacknowledged: %u)"), name, transmitWindow, transmitPosition, transmitPositionUnacknowledged));

                for (index = 0; index < 8; index++)
                {
                    if (transmitQueue[index].sent)
                    {
                    IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> %u MARKED SENT"), name, index));
                    IFSTAT(retransmissionsTimeout++);
                    }

                    transmitQueue[index].sent = FALSE;
                }

                transmitWindow = 4;
                transmitPosition = transmitPositionUnacknowledged;
                if (++transmitQueue[transmitPosition].retries == 20)
                {
                    LinkLost();    
                }
                IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WriteExecute@%s> RETRY COMPLETE (TransmitWindow: %u, TransmitPosition: %u, TransmitPositionUnacknowledged: %u)"), name, transmitWindow, transmitPosition, transmitPositionUnacknowledged));
            }
        }
        else if (result != WAIT_OBJECT_0)
        {
            serialPortError = TRUE;
            LinkLost();    
            break;
        }
    }

    IFDBG(DebugOut(DEBUG_BCSP_CTRL, TEXT("<BcspCommunication::WriteExecute@%s> TERMINATED"), name));

    LeaveCriticalSection(&lock);

    return serialPortError ? ERROR_INVALID_PARAMETER : ERROR_SUCCESS;
}

DWORD BcspCommunication::WritePacket(BcspChannelT channel, unsigned char* buffer, DWORD size)
{
    DWORD result = ERROR_NOT_ENOUGH_MEMORY;

    if (shuttingDown || serialPortError)
    {
        CloseConnection();
        return ERROR_SERVICE_NOT_ACTIVE;
    }

    if (channel == BCSP_CHANNEL_SCO)
    {
        EnterCriticalSection(&lock);

        free(outgoingSCOData.buffer);
        outgoingSCOData.buffer = malloc(size);
        if (outgoingSCOData.buffer)
        {
            outgoingSCOData.present = TRUE;
            outgoingSCOData.size    = (unsigned short) size;
            memcpy(outgoingSCOData.buffer, buffer, size);
            SetEvent(writePacketEvent);
            result = ERROR_SUCCESS;
        }
    }
    else
    {
        HANDLE handles[] = { transmitHandle, terminateEvent };

        if (sniffMode == 2)
        {
            if (channel == BCSP_CHANNEL_HCI)
            {
                HCIFileWritePacket(2, buffer, size);
            }
            else if (channel == BCSP_CHANNEL_ACL)
            {
                HCIFileWritePacket(0, buffer, size);
            }
        }

        switch (WaitForMultipleObjects(2, handles, FALSE, INFINITE))
        {
            case WAIT_OBJECT_0 + 0:
            {
                break;
            }
            case WAIT_OBJECT_0 + 1:
            {
                IFDBG(DebugOut(DEBUG_BCSP_CTRL, TEXT("<BcspCommunication::WritePacket@%s> SHUTTING DOWN"), name));

                return ERROR_SERVICE_NOT_ACTIVE;
            }
            default:
            {
                IFDBG(DebugOut(DEBUG_BCSP_CTRL, TEXT("<BcspCommunication::WritePacket@%s> UNKNOWN ERROR"), name));

                return GetLastError();
            }
        }

        if (shuttingDown || serialPortError)
        {
            IFDBG(DebugOut(DEBUG_BCSP_CTRL, TEXT("<BcspCommunication::WritePacket@%s> SHUTTING DOWN"), name));
            return ERROR_SERVICE_NOT_ACTIVE;
        }

        EnterCriticalSection(&lock);

        IFDBG(DebugOut(DEBUG_BCSP_RUN, TEXT("<BcspCommunication::WritePacket@%s> PACKET WRITE INFO (WritePossible: %u, TransmitInsertPosition: %u, Present: %u)"), name, writePossible, transmitInsertPosition, transmitQueue[transmitInsertPosition].present));

        if (!writePossible)
        {
            writePossible = TRUE;
            result = ERROR_SERVICE_DISABLED;
        }
        else if (!transmitQueue[transmitInsertPosition].present)
        {
            ZeroMemory(&transmitQueue[transmitInsertPosition], sizeof(BcspQueueElementT));

            transmitQueue[transmitInsertPosition].buffer = malloc(size);
            if (transmitQueue[transmitInsertPosition].buffer)
            {
                transmitQueue[transmitInsertPosition].present   = TRUE;
                transmitQueue[transmitInsertPosition].sent      = FALSE;
                transmitQueue[transmitInsertPosition].channel   = channel;
                transmitQueue[transmitInsertPosition].size      = (unsigned short) size;
                memcpy(transmitQueue[transmitInsertPosition].buffer, buffer, size);
                SetEvent(writePacketEvent);
                transmitInsertPosition = (++transmitInsertPosition) & 0x07;
                result = ERROR_SUCCESS;
            }        
        }

   

⌨️ 快捷键说明

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