mirror of
https://github.com/kovidgoyal/calibre.git
synced 2025-07-09 03:04:10 -04:00
Use RAII for PROPVARIANT
This commit is contained in:
parent
ad3f147c56
commit
7005d6ecd0
@ -326,44 +326,36 @@ find_objects_in(CComPtr<IPortableDeviceContent> &content, CComPtr<IPortableDevic
|
|||||||
* The child ids are put into object_ids. Returns False if any errors
|
* The child ids are put into object_ids. Returns False if any errors
|
||||||
* occurred (also sets the python exception).
|
* occurred (also sets the python exception).
|
||||||
*/
|
*/
|
||||||
IEnumPortableDeviceObjectIDs *children;
|
CComPtr<IEnumPortableDeviceObjectIDs> children;
|
||||||
HRESULT hr = S_OK, hr2 = S_OK;
|
HRESULT hr = S_OK, hr2 = S_OK;
|
||||||
PWSTR child_ids[10];
|
PWSTR child_ids[10];
|
||||||
DWORD fetched, i;
|
prop_variant pv(VT_LPWSTR);
|
||||||
PROPVARIANT pv;
|
|
||||||
bool ok = true;
|
|
||||||
|
|
||||||
PropVariantInit(&pv);
|
|
||||||
pv.vt = VT_LPWSTR;
|
|
||||||
|
|
||||||
Py_BEGIN_ALLOW_THREADS;
|
Py_BEGIN_ALLOW_THREADS;
|
||||||
hr = content->EnumObjects(0, parent_id, NULL, &children);
|
hr = content->EnumObjects(0, parent_id, NULL, &children);
|
||||||
Py_END_ALLOW_THREADS;
|
Py_END_ALLOW_THREADS;
|
||||||
|
|
||||||
if (FAILED(hr)) {hresult_set_exc("Failed to get children from device", hr); ok = false; goto end;}
|
if (FAILED(hr)) {hresult_set_exc("Failed to get children from device", hr); return false;}
|
||||||
|
|
||||||
hr = S_OK;
|
hr = S_OK;
|
||||||
|
|
||||||
while (hr == S_OK) {
|
while (hr == S_OK) {
|
||||||
|
DWORD fetched;
|
||||||
Py_BEGIN_ALLOW_THREADS;
|
Py_BEGIN_ALLOW_THREADS;
|
||||||
hr = children->Next(10, child_ids, &fetched);
|
hr = children->Next(arraysz(child_ids), child_ids, &fetched);
|
||||||
Py_END_ALLOW_THREADS;
|
Py_END_ALLOW_THREADS;
|
||||||
if (SUCCEEDED(hr)) {
|
if (SUCCEEDED(hr)) {
|
||||||
for(i = 0; i < fetched; i++) {
|
com_wchar_raii cleanup[arraysz(child_ids)];
|
||||||
|
for(DWORD i = 0; i < fetched; i++) { cleanup[i].attach(child_ids[i]); }
|
||||||
|
for(DWORD i = 0; i < fetched; i++) {
|
||||||
pv.pwszVal = child_ids[i];
|
pv.pwszVal = child_ids[i];
|
||||||
hr2 = object_ids->Add(&pv);
|
hr2 = object_ids->Add(&pv);
|
||||||
pv.pwszVal = NULL;
|
pv.pwszVal = NULL;
|
||||||
if (FAILED(hr2)) { hresult_set_exc("Failed to add child ids to propvariantcollection", hr2); break; }
|
if (FAILED(hr2)) { hresult_set_exc("Failed to add child ids to propvariantcollection", hr2); return false; }
|
||||||
}
|
}
|
||||||
for (i = 0; i < fetched; i++) { CoTaskMemFree(child_ids[i]); child_ids[i] = NULL; }
|
|
||||||
if (FAILED(hr2) || !ok) { ok = false; goto end; }
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
end:
|
|
||||||
if (children != NULL) children->Release();
|
|
||||||
PropVariantClear(&pv);
|
|
||||||
return ok;
|
|
||||||
} // }}}
|
} // }}}
|
||||||
|
|
||||||
// Single get filesystem {{{
|
// Single get filesystem {{{
|
||||||
|
@ -256,12 +256,10 @@ get_device_information(CComPtr<IPortableDevice> &device, CComPtr<IPortableDevice
|
|||||||
|
|
||||||
bool has_storage = false;
|
bool has_storage = false;
|
||||||
for (i = 0; i < num_of_categories && !has_storage; i++) {
|
for (i = 0; i < num_of_categories && !has_storage; i++) {
|
||||||
PROPVARIANT pv;
|
prop_variant pv;
|
||||||
PropVariantInit(&pv);
|
|
||||||
if (SUCCEEDED(categories->GetAt(i, &pv)) && pv.puuid != NULL) {
|
if (SUCCEEDED(categories->GetAt(i, &pv)) && pv.puuid != NULL) {
|
||||||
if (IsEqualGUID(WPD_FUNCTIONAL_CATEGORY_STORAGE, *pv.puuid)) has_storage = true;
|
if (IsEqualGUID(WPD_FUNCTIONAL_CATEGORY_STORAGE, *pv.puuid)) has_storage = true;
|
||||||
}
|
}
|
||||||
PropVariantClear(&pv);
|
|
||||||
}
|
}
|
||||||
PyDict_SetItemString(ans, "has_storage", has_storage ? Py_True : Py_False);
|
PyDict_SetItemString(ans, "has_storage", has_storage ? Py_True : Py_False);
|
||||||
|
|
||||||
|
@ -27,3 +27,11 @@ set_error_from_hresult(PyObject *exc_type, const char *file, const int line, con
|
|||||||
typedef generic_raii<wchar_t*, CoTaskMemFree, NULL> com_wchar_raii;
|
typedef generic_raii<wchar_t*, CoTaskMemFree, NULL> com_wchar_raii;
|
||||||
static inline void handle_destructor(HANDLE p) { CloseHandle(p); }
|
static inline void handle_destructor(HANDLE p) { CloseHandle(p); }
|
||||||
typedef generic_raii<HANDLE, handle_destructor, INVALID_HANDLE_VALUE> handle_raii;
|
typedef generic_raii<HANDLE, handle_destructor, INVALID_HANDLE_VALUE> handle_raii;
|
||||||
|
|
||||||
|
struct prop_variant : PROPVARIANT {
|
||||||
|
prop_variant(VARTYPE vt=VT_EMPTY) noexcept : PROPVARIANT{} { PropVariantInit(this); this->vt = vt; }
|
||||||
|
|
||||||
|
~prop_variant() noexcept { clear(); }
|
||||||
|
|
||||||
|
void clear() noexcept { PropVariantClear(this); }
|
||||||
|
};
|
||||||
|
Loading…
x
Reference in New Issue
Block a user