I'm trying to copy an ADO field to a CComVariant in chunks using pField->GetChunk(). I did come across this sample code here
And based some code on it.
GetValue(CComPtr<Field>& pField, CComVariant& value)
{
long nSizeInBytes = 0;
pField->get_ActualSize(&nSizeInBytes);
UCHAR chData;
SAFEARRAY FAR* psa;
SAFEARRAYBOUND rgsabound[1];
rgsabound[0].lLbound = 0;
rgsabound[0].cElements = nSizeInBytes;
long lngOffSet = 0;
_variant_t varChunk;
psa = SafeArrayCreate(VT_UI1, 1, rgsabound);
long index1 = 0;
while (lngOffSet < nSizeInBytes)
{
hr = pField->GetChunk(CHUNK_SIZE, &varChunk);
if (FAILED(hr)) RETURN_ERROR(hr, _T("Failed Getting chunk of certain size"));
for (long index = 0; index <= (CHUNK_SIZE - 1); index++)
{
hr = SafeArrayGetElement(varChunk.parray, &index, &chData);
if (SUCCEEDED(hr))
{
hr = SafeArrayPutElement(psa, &index1, &chData);
if (FAILED(hr)) RETURN_ERROR(hr, _T("Failed doing saferray put"));
index1++;
}
else
{
break;
}
}
lngOffSet = lngOffSet + CHUNK_SIZE;
}
lngOffSet = 0;
value.vt = VT_ARRAY | VT_UI1;
value.parray = psa;
}
But this only seems to apply to if the variant returned by GetChunk() is an array (VT_ARRAY | VT_UI1) to begin with.
What if It's something like a BSTR? Then there is no array in varChunk.parray and SafeArrayGetElement fails with a "Catastrophic error".
Is there any way to read the field in chunks and sew it back together in a variant? Regardless of it's type?
Why am I trying to do this? Usually in our code we get the value in one swoop with GetChunk using the full size of the field. But we have a customer in which it looks like calling GetChunk with sizes of 2 meg or more causes memory leaks and crashes. Not exactly sure if that's the case but we wanted to see if the issue goes away if instead of doing it in one swoop, we try to do so in smaller chunks.