mirror of
https://github.com/reactos/reactos.git
synced 2025-08-05 22:13:06 +00:00
[SHELL32][SHELLEXT] IEnumIDList::Next must handle pceltFetched and memory errors correctly (#5820)
- pceltFetched can be NULL if the caller is not requesting multiple items. - All entries returned in rgelt must be valid, they cannot be NULL.
This commit is contained in:
parent
b4b1c5b9aa
commit
f283a3f9ae
4 changed files with 42 additions and 17 deletions
|
@ -36,9 +36,10 @@ public:
|
||||||
// *** IEnumIDList methods ***
|
// *** IEnumIDList methods ***
|
||||||
STDMETHODIMP Next(ULONG celt, LPITEMIDLIST *rgelt, ULONG *pceltFetched)
|
STDMETHODIMP Next(ULONG celt, LPITEMIDLIST *rgelt, ULONG *pceltFetched)
|
||||||
{
|
{
|
||||||
if (!pceltFetched || !rgelt)
|
if (!rgelt || (!pceltFetched && celt != 1))
|
||||||
return E_POINTER;
|
return E_POINTER;
|
||||||
|
|
||||||
|
HRESULT hr = S_OK;
|
||||||
ULONG Fetched = 0;
|
ULONG Fetched = 0;
|
||||||
|
|
||||||
while (celt)
|
while (celt)
|
||||||
|
@ -48,15 +49,25 @@ public:
|
||||||
if (m_Index < g_FontCache->Size())
|
if (m_Index < g_FontCache->Size())
|
||||||
{
|
{
|
||||||
CStringW Name = g_FontCache->Name(m_Index);
|
CStringW Name = g_FontCache->Name(m_Index);
|
||||||
rgelt[Fetched] = _ILCreate(Name, m_Index);
|
LPITEMIDLIST item = _ILCreate(Name, m_Index);
|
||||||
|
if (!item)
|
||||||
|
{
|
||||||
|
hr = Fetched ? S_FALSE : E_OUTOFMEMORY;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
rgelt[Fetched] = item;
|
||||||
m_Index++;
|
m_Index++;
|
||||||
Fetched++;
|
Fetched++;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
hr = S_FALSE;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
*pceltFetched = Fetched;
|
if (pceltFetched)
|
||||||
return Fetched ? S_OK : S_FALSE;
|
*pceltFetched = Fetched;
|
||||||
|
return hr;
|
||||||
}
|
}
|
||||||
STDMETHODIMP Skip(ULONG celt)
|
STDMETHODIMP Skip(ULONG celt)
|
||||||
{
|
{
|
||||||
|
|
|
@ -277,9 +277,17 @@ CEnumIDList::Next(
|
||||||
for (i = 0; i < celt; i++)
|
for (i = 0; i < celt; i++)
|
||||||
{
|
{
|
||||||
if (!m_pCurrent)
|
if (!m_pCurrent)
|
||||||
|
{
|
||||||
|
hr = S_FALSE;
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
temp = ILClone(m_pCurrent->pidl);
|
temp = ILClone(m_pCurrent->pidl);
|
||||||
|
if (!temp)
|
||||||
|
{
|
||||||
|
hr = i ? S_FALSE : E_OUTOFMEMORY;
|
||||||
|
break;
|
||||||
|
}
|
||||||
rgelt[i] = temp;
|
rgelt[i] = temp;
|
||||||
m_pCurrent = m_pCurrent->pNext;
|
m_pCurrent = m_pCurrent->pNext;
|
||||||
}
|
}
|
||||||
|
|
|
@ -34,25 +34,25 @@ public:
|
||||||
// *** IEnumIDList methods ***
|
// *** IEnumIDList methods ***
|
||||||
STDMETHODIMP Next(ULONG celt, LPITEMIDLIST *rgelt, ULONG *pceltFetched)
|
STDMETHODIMP Next(ULONG celt, LPITEMIDLIST *rgelt, ULONG *pceltFetched)
|
||||||
{
|
{
|
||||||
if (!pceltFetched || !rgelt)
|
if (!rgelt || (!pceltFetched && celt != 1))
|
||||||
return E_POINTER;
|
return E_POINTER;
|
||||||
|
|
||||||
*pceltFetched = 0;
|
LPITEMIDLIST item;
|
||||||
|
|
||||||
if (celt != 1)
|
|
||||||
return E_FAIL;
|
|
||||||
|
|
||||||
CStringW name;
|
CStringW name;
|
||||||
bool dir;
|
bool dir;
|
||||||
unz_file_info64 info;
|
unz_file_info64 info;
|
||||||
if (mEnumerator.next_unique(m_Prefix, name, dir, info))
|
for (ULONG i = 0; i < celt; ++i)
|
||||||
{
|
{
|
||||||
*pceltFetched = 1;
|
if (pceltFetched)
|
||||||
*rgelt = _ILCreate(dir ? ZIP_PIDL_DIRECTORY : ZIP_PIDL_FILE, name, info);
|
*pceltFetched = i;
|
||||||
return S_OK;
|
if (!mEnumerator.next_unique(m_Prefix, name, dir, info))
|
||||||
|
return S_FALSE;
|
||||||
|
item = _ILCreate(dir ? ZIP_PIDL_DIRECTORY : ZIP_PIDL_FILE, name, info);
|
||||||
|
if (!item)
|
||||||
|
return i ? S_FALSE : E_OUTOFMEMORY;
|
||||||
|
rgelt[i] = item;
|
||||||
}
|
}
|
||||||
|
return S_OK;
|
||||||
return S_FALSE;
|
|
||||||
}
|
}
|
||||||
STDMETHODIMP Skip(ULONG celt)
|
STDMETHODIMP Skip(ULONG celt)
|
||||||
{
|
{
|
||||||
|
|
|
@ -172,9 +172,15 @@ HRESULT WINAPI CEnumIDListBase::Next(
|
||||||
|
|
||||||
for(i = 0; i < celt; i++)
|
for(i = 0; i < celt; i++)
|
||||||
{ if(!mpCurrent)
|
{ if(!mpCurrent)
|
||||||
|
{ hr = S_FALSE;
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
temp = ILClone(mpCurrent->pidl);
|
temp = ILClone(mpCurrent->pidl);
|
||||||
|
if (!temp)
|
||||||
|
{ hr = i ? S_FALSE : E_OUTOFMEMORY;
|
||||||
|
break;
|
||||||
|
}
|
||||||
rgelt[i] = temp;
|
rgelt[i] = temp;
|
||||||
mpCurrent = mpCurrent->pNext;
|
mpCurrent = mpCurrent->pNext;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue