Search code examples
c++visual-c++mfccode-analysis

How to resolve this C6385 code analysis warning: Reading invalid data


I am trying to address a code analysis warning that appears in the following method:

CStringArray* CCreateReportDlg::BuildCustomAssignArray(ROW_DATA_S &rsRowData)
{
    INT_PTR         iAssign, iNumAssigns, iUsedAssign;
    CStringArray    *pAryStrCustom = nullptr;
    CUSTOM_ASSIGN_S *psAssign = nullptr;

    if (rsRowData.uNumCustomToFill > 0)
    {
        pAryStrCustom = new CStringArray[rsRowData.uNumCustomToFill];
        iNumAssigns = m_aryPtrAssign.GetSize();
        for (iAssign = 0, iUsedAssign = 0; iAssign < iNumAssigns; iAssign++)
        {
            psAssign = (CUSTOM_ASSIGN_S*)m_aryPtrAssign.GetAt(iAssign);
            if (psAssign != nullptr)
            {
                if (!psAssign->bExcluded)
                {
                    pAryStrCustom[iUsedAssign].Copy(psAssign->aryStrBrothersAll);
                    iUsedAssign++;
                }
            }
        }
    }

    return pAryStrCustom;
}

The offending line of code is:

pAryStrCustom[iUsedAssign].Copy(psAssign->aryStrBrothersAll);

I compile this code for both 32 bit and 64 bit. The warning being raised is:

Warning (C6385) Reading invalid data from pAryStrCustom: the readable size is (size_t)*40+8 bytes, but 80 bytes may be read.

I don't know if it is relevant, but the CUSTOM_ASSIGN_S structure is defined as:

typedef struct tagCustomAssignment
{
    int             iIndex;
    CString         strDescription;
    CString         strHeading;
    BOOL            bExcluded;
    CStringArray    aryStrBrothersAll;
    CStringArray    aryStrBrothersWT;
    CStringArray    aryStrBrothersSM;
    BOOL            bIncludeWT;
    BOOL            bIncludeTMS;
    BOOL            bFixed;
    int             iFixedType;
} CUSTOM_ASSIGN_S;

My code is functional (for years) but is there a coding improvement I can make to address this issue? I have read the linked article and it is not clear to me. I have also seen this question (Reading Invalid Data c6385) along similar lines. But in my code I can't see how that applies.


Solution

  • Warning... the readable size is (size_t)*40+8 bytes, but 80 bytes may be read.

    The wording for this warning is not accurate, because size_t is not a number, it's a data type. (size_t)*40+8 doesn't make sense. It's probably meant to be:

    Warning... the readable size is '40+8 bytes', but '80 bytes' may be read.

    This warning can be roughly reproduced with the following example:

    //don't run this code, it's just for viewing the warning
    size_t my_size = 1;
    char* buf = new char[my_size];
    
    buf[1];
    //warning C6385: Reading invalid data from 'buf':  
    //the readable size is 'my_size*1' bytes, but '2' bytes may be read
    

    The warning is correct and obvious. buf[1] is out of bound. The compiler sees allocation size for buf is my_size*1, and index 1 is accessing byte '2'. I think in other place the compiler prints it incorrectly, but the actual warning is valid.

    In any case, just make sure iUsedAssign is within range

    if (!psAssign->bExcluded && iUsedAssign < rsRowData.uNumCustomToFill)
    {
        ...
    }