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

📄 pckunpck.cpp

📁 著名的 helix realplayer 基于手机 symbian 系统的 播放器全套源代码
💻 CPP
📖 第 1 页 / 共 4 页
字号:
        // Save the beginning of the string
        const char* pszName = (const char*) rpBuf;
        // Search until we find either a NULL or 
        // the end of the buffer
        while (rpBuf < pLimit && *rpBuf != 0) ++rpBuf;
        // Did we get a NULL terminator?
        if (rpBuf < pLimit && *rpBuf == 0)
        {
            // We know now that pszName is a valid string
            //
            // Skip the NULL terminator
            ++rpBuf;
            // Save the beginning of the value string
            const char* pszValue = (const char*) rpBuf;
            // Search until we find either a NULL or 
            // the end of the buffer
            while (rpBuf < pLimit && *rpBuf != 0) ++rpBuf;
            // Did we get a NULL terminator?
            if (rpBuf < pLimit && *rpBuf == 0)
            {
                // Skip the NULL terminator
                ++rpBuf;
                // We know now that pszValue is a valid string, so
                // make an IHXBuffer out of it
                IHXBuffer* pValue = NULL;
                retVal = CreateStringBuffer(pValue, pszValue, pContext);
                if (SUCCEEDED(retVal))
                {
                    // Set the property
                    retVal = pValues->SetPropertyCString(pszName, pValue);
                }
                HX_RELEASE(pValue);
            }
        }
    }

    return retVal;
}

HX_RESULT UnpackPropertyBuffer(IHXValues* pValues,
                               REF(BYTE*)  rpBuf,
                               BYTE*       pLimit,
                               IUnknown*   pContext)
{
    HX_RESULT retVal = HXR_FAIL;

    if (pValues && rpBuf && pLimit &&
        rpBuf < pLimit && rpBuf[0] == 'b')
    {
        // Skip the 'b' type character
        rpBuf++;
        // Save the beginning of the string
        const char* pszName = (const char*) rpBuf;
        // Search until we find either a NULL or 
        // the end of the buffer
        while (rpBuf < pLimit && *rpBuf != 0) ++rpBuf;
        // Did we get a NULL terminator?
        if (rpBuf < pLimit && *rpBuf == 0)
        {
            // We know now that pszName is a valid string
            //
            // Skip the NULL terminator
            ++rpBuf;
            // Do we have enough bytes to get the buffer length?
            if (rpBuf + 4 <= pLimit)
            {
                // Unpack the buffer length in big-endian form
                UINT32 ulLen = ((rpBuf[0] << 24) & 0xFF000000) |
                               ((rpBuf[1] << 16) & 0x00FF0000) |
                               ((rpBuf[2] <<  8) & 0x0000FF00) |
                               ( rpBuf[3]        & 0x000000FF);
                // Skip the buffer length
                rpBuf += 4;
                // Do we have enough bytes to get the buffer?
                if (rpBuf + ulLen <= pLimit)
                {
                    // Create a buffer
                    IHXBuffer* pValue = NULL;
                    retVal = CreateBuffer(pValue, pContext);
                    if (SUCCEEDED(retVal))
                    {
                        // Set the buffer
                        retVal = pValue->Set(rpBuf, ulLen);
                        if (SUCCEEDED(retVal))
                        {
                            // Skip the buffer bytes
                            rpBuf += ulLen;
                            // Set the property
                            retVal = pValues->SetPropertyBuffer(pszName,
                                                                pValue);
                        }
                    }
                    HX_RELEASE(pValue);
                }
            }
        }
    }

    return retVal;
}

HX_RESULT UnpackValuesBinary(IHXValues* pValues,
                             IHXBuffer* pBuffer,
                             IUnknown*   pContext)
{
    HX_RESULT retVal = HXR_FAIL;

    if (pValues && pBuffer)
    {
        retVal = UnpackValuesBinary(pValues,
                                    pBuffer->GetBuffer(),
                                    pBuffer->GetSize(),
                                    pContext);
    }

    return retVal;
}

HX_RESULT UnpackValuesBinary(IHXValues* pValues,
                             BYTE*       pBuf,
                             UINT32      ulLen,
                             IUnknown*   pContext)
{
    HX_RESULT retVal = HXR_FAIL;

    if (pBuf && ulLen)
    {
        // Get the pointer limit
        BYTE* pLimit = pBuf + ulLen;
        // Make sure this is not string format
        if (pBuf[0] != '[')
        {
            // Clear the return value
            retVal = HXR_OK;
            // Loop through the buffer, unpacking name/value pairs
            while (pBuf < pLimit && SUCCEEDED(retVal))
            {
                // Get a property type code
                char c = (char) pBuf[0];
                // Save the buffer pointer
                BYTE* pCur = pBuf;
                // Switch based on type
                switch (c)
                {
                    case 'u':
                        retVal = UnpackPropertyULONG32(pValues, pBuf,
                                                       pLimit, pContext);
                        break;
                    case 'c':
                        retVal = UnpackPropertyCString(pValues, pBuf,
                                                       pLimit, pContext);
                        break;
                    case 'b':
                        retVal = UnpackPropertyBuffer(pValues, pBuf,
                                                      pLimit, pContext);
                        break;
                    default:
                        retVal = HXR_FAIL;
                        break;
                }
                // Do a sanity check: if we succeeded,
                // then we must have advanced the pointer.
                // This will prevent an infinite loop.
                if (SUCCEEDED(retVal) && pCur == pBuf)
                {
                    retVal = HXR_FAIL;
                }
            }
        }
    }

    return retVal;
}

HX_RESULT PackValues(REF(IHXBuffer*) rpBuffer,
                     IHXValues*      pValues,
                     BOOL             bPackBinary,
                     IUnknown*        pContext)
{
    HX_RESULT retVal = HXR_FAIL;

    if (pValues)
    {
        // Create an output IHXBuffer
        IHXBuffer* pBuffer = NULL;
        retVal = CreateBuffer(pBuffer, pContext);
        if (SUCCEEDED(retVal))
        {
            // Are we supposed to pack this in binary form?
            if (bPackBinary)
            {
                // Pack in binary form
                //
                // First get the size necessary to pack it in binary form
                UINT32 ulBinPackSize = GetBinaryPackedSize(pValues);
                if (ulBinPackSize)
                {
                    // Make the buffer this size
                    retVal = pBuffer->SetSize(ulBinPackSize);
                    if (SUCCEEDED(retVal))
                    {
                        // Binary pack the buffer
                        retVal = PackValuesBinary(pBuffer, pValues);
                        if (SUCCEEDED(retVal))
                        {
                            // Copy the out parameter
                            HX_RELEASE(rpBuffer);
                            rpBuffer = pBuffer;
                            rpBuffer->AddRef();
                        }
                    }
                }
                else
                {
                    retVal = HXR_FAIL;
                }
            }
            else
            {
                // Pack in a string
                CHXString cTmp;
                retVal = PackValues(cTmp, pValues);
                if (SUCCEEDED(retVal))
                {
                    // Now just copy the string into the IHXBuffer
                    retVal = pBuffer->Set((const UCHAR*) (const char*) cTmp,
                                          cTmp.GetLength() + 1);
                    if (SUCCEEDED(retVal))
                    {
                        // Set the out parameter
                        HX_RELEASE(rpBuffer);
                        rpBuffer = pBuffer;
                        rpBuffer->AddRef();
                    }
                }
            }
        }
        HX_RELEASE(pBuffer);
    }

    return retVal;
}

HX_RESULT UnpackValues(REF(IHXValues*) rpValues,
                       IHXBuffer*      pBuffer,
                       IUnknown*        pContext)
{
    HX_RESULT retVal = HXR_FAIL;

    if (pBuffer)
    {
        retVal = UnpackValues(rpValues,
                              pBuffer->GetBuffer(),
                              pBuffer->GetSize(),
                              pContext);
    }

    return retVal;
}

HX_RESULT UnpackValues(REF(IHXValues*) rpValues,
                       BYTE*            pBuf,
                       UINT32           ulLen,
                       IUnknown*        pContext)
{
    HX_RESULT retVal = HXR_FAIL;

    if (pBuf && ulLen)
    {
        // Create an output IHXValues
        IHXValues* pValues = NULL;
        retVal = CreateValues(pValues, pContext);
        if (SUCCEEDED(retVal))
        {
            // Get the string
            const char* pszBuffer = (const char*) pBuf;
            // Is this packed in binary or text? If it's in text
            // form, then it will have a '[' as the first character
            if (pszBuffer[0] != '[')
            {
                // The buffer is binary packed
                retVal = UnpackValuesBinary(pValues, pBuf, ulLen, pContext);
            }
            else
            {
                // The buffer is text packed
                retVal = UnpackValues(pszBuffer, pValues, FALSE);
            }
            if (SUCCEEDED(retVal))
            {
                // Assign the out parameter
                HX_RELEASE(rpValues);
                rpValues = pValues;
                rpValues->AddRef();
            }
        }
        HX_RELEASE(pValues);
    }

    return retVal;
}

// This method checks to see if all the properties
// in pValues1 are in pValues2 and that the value
// of these properties is indentical. pValues2,
// however, could still have properties that pValues1
// doesn't have. AreValuesIdentical() calls
// AreValuesInclusiveIdentical() in both directions,
// which establishes absolute equality if both
// are true.
BOOL AreValuesInclusiveIdentical(IHXValues* pValues1,
                                 IHXValues* pValues2)
{
    BOOL bRet = FALSE;

    if (pValues1 && pValues2)
    {
        // Assume that they are equal, and breakout
        // at the first inequality
        bRet = TRUE;
        // Check the ULONG32 properties
        const char* pszName  = NULL;
        UINT32      ulValue1 = 0;
        HX_RESULT rv = pValues1->GetFirstPropertyULONG32(pszName, ulValue1);
        while (SUCCEEDED(rv) && bRet)
        {
            // Lookup this property in pValues2
            UINT32 ulValue2 = 0;
            HX_RESULT rv2 = pValues2->GetPropertyULONG32(pszName, ulValue2);
            // Check for a match
            if (FAILED(rv2) || ulValue1 != ulValue2)
            {
                bRet = FALSE;
            }
            // Get next ULONG32 property
            rv = pValues1->GetNextPropertyULONG32(pszName, ulValue1);
        }
        if (bRet)
        {
            // Check the CString properties
            IHXBuffer* pValue1 = NULL;
            rv = pValues1->GetFirstPropertyCString(pszName, pValue1);
            while (SUCCEEDED(rv) && bRet)
            {
                // Lookup this property in pValues2
                IHXBuffer* pValue2 = NULL;
                HX_RESULT rv2 = pValues2->GetPropertyCString(pszName, pValue2);
                if (FAILED(rv2) ||
                    strcmp((const char*) pValue1->GetBuffer(),
                           (const char*) pValue2->GetBuffer()) != 0)
                {
                    bRet = FALSE;
                }
                HX_RELEASE(pValue2);
                // Get next CString prop
                HX_RELEASE(pValue1);
                rv = pValues1->GetNextPropertyCString(pszName, pValue1);
            }
            if (bRet)
            {
                // Check the buffer properties
                rv = pValues1->GetFirstPropertyBuffer(pszName, pValue1);
                while (SUCCEEDED(rv) && bRet)
                {
                    // Lookup this property in pValues2
                    IHXBuffer* pValue2 = NULL;
                    HX_RESULT rv2 = pValues2->GetPropertyBuffer(pszName, pValue2);
                    if (FAILED(rv2)                              ||
                        pValue1->GetSize() != pValue2->GetSize() ||
                        memcmp((const void*) pValue1->GetBuffer(),
                               (const void*) pValue2->GetBuffer(),
                               pValue1->GetSize()) != 0)
                    {
                        bRet = FALSE;
                    }
                    HX_RELEASE(pValue2);
                    // Get next Buffer prop
                    HX_RELEASE(pValue1);
                    rv = pValues1->GetNextPropertyBuffer(pszName, pValue1);
                }
            }
        }
    }

    return bRet;
}

BOOL AreValuesIdentical(IHXValues* pValues1,
                        IHXValues* pValues2)
{
    BOOL bRet = FALSE;

    // Check if all the properties in pValues1 are
    // in pValues2 and are identical
    bRet = AreValuesInclusiveIdentical(pValues1, pValues2);
    if (bRet)
    {
        // Check if all the properties in pValues2 are
        // in pValues1 and are identical
        bRet = AreValuesInclusiveIdentical(pValues2, pValues1);
    }

    return bRet;
}

#ifdef _DEBUG

HX_RESULT TestValuesPacking(IUnknown* pContext)
{
    HX_RESULT retVal = HXR_OK;

    // Create an IHXValues
    IHXValues* pValues = NULL;
    retVal = CreateValues(pValues, pContext);
    if (SUCCEEDED(retVal))
    {
        // Populate this IHXValues
        pValues->SetPropertyULONG32("ulong1", 42);
        pValues->SetPropertyULONG32("ulong2", 0xbaadf00d);
        SetCStringProperty(pValues, "cstring1",
                           "Rock the Casbah", pContext);
        SetCStringProperty(pValues, "cstring2",
                           "Sandinista", pContext);
        UINT32 ulBuf1Len = 128;
        BYTE*  pBuf1     = new BYTE [ulBuf1Len];
        if (pBuf1)
        {
            // Fill the buffer with random byte values
            srand(time(NULL));
            for (UINT32 i = 0; i < ulBuf1Len; i++)
            {
                UINT32 ulVal = (UINT32) rand();
                pBuf1[i]     = (BYTE) (ulVal & 0x000000FF);
            }
            SetBufferProperty(pValues, "buffer1", pBuf1, ulBuf1Len, pContext);
            // Pack it as text
            IHXBuffer* pBufferText = NULL;
            retVal = PackValues(pBufferText, pValues, FALSE, pContext);
            if (SUCCEEDED(retVal))
            {
                // Now unpack it
                IHXValues* pValuesTextOut = NULL;
                retVal = UnpackValues(pValuesTextOut, pBufferText, pContext);
                if (SUCCEEDED(retVal))
                {
                    // Compare them
                    if (AreValuesIdentical(pValues, pValuesTextOut))
                    {
                        // Now pack as binary
                        IHXBuffer* pBufferBinary = NULL;
                        retVal = PackValues(pBufferBinary, pValues,
                                            TRUE, pContext);
                        if (SUCCEEDED(retVal))
                        {
                            // Now unpack it
                            IHXValues* pValuesBinaryOut = NULL;
                            retVal = UnpackValues(pValuesBinaryOut,
                                                  pBufferBinary, pContext);
                            if (SUCCEEDED(retVal))
                            {
                                // Compare them
                                if (!AreValuesIdentical(pValues,
                                                        pValuesBinaryOut))
                                {
                                    // Oops - they are not the same
                                    retVal = HXR_FAIL;
                                }
                            }
                            HX_RELEASE(pValuesBinaryOut);
                        }
                        HX_RELEASE(pBufferBinary);
                    }
                    else
                    {
                        // Oops - they are not the same
                        retVal = HXR_FAIL;
                    }
                }
                HX_RELEASE(pValuesTextOut);
            }
            HX_RELEASE(pBufferText);
        }
        HX_VECTOR_DELETE(pBuf1);
    }
    HX_RELEASE(pValues);

    return retVal;
}

#endif

⌨️ 快捷键说明

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