You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
783 lines
20 KiB
783 lines
20 KiB
/*++
|
|
|
|
Copyright (C) 1999- Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
eventcb.cpp
|
|
|
|
Abstract:
|
|
|
|
This module implements CWiaPTPEventCallback class
|
|
|
|
Author:
|
|
|
|
William Hsieh (williamh) created
|
|
|
|
Revision History:
|
|
|
|
|
|
--*/
|
|
|
|
#include "pch.h"
|
|
|
|
//
|
|
// This method is the callback function for every PTP event
|
|
//
|
|
// Input:
|
|
// pEvent -- PTP event block
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::EventCallbackDispatch(
|
|
PPTP_EVENT pEvent
|
|
)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::EventCallback");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
CPtpMutex cpm(m_hPtpMutex);
|
|
|
|
if (!pEvent)
|
|
{
|
|
wiauDbgError("EventCallback", "invalid arg");
|
|
return E_INVALIDARG;
|
|
}
|
|
|
|
//
|
|
// Events are not expected when there is no open session. Just ignore the event
|
|
//
|
|
if (!m_pPTPCamera || !m_pPTPCamera->IsCameraSessionOpen())
|
|
{
|
|
wiauDbgError("EventCallback", "events not expected while there is no open session");
|
|
return E_FAIL;
|
|
}
|
|
|
|
//
|
|
// Figure out what the event is and call the appropriate function
|
|
//
|
|
switch (pEvent->EventCode)
|
|
{
|
|
case PTP_EVENTCODE_CANCELTRANSACTION:
|
|
hr = S_OK;
|
|
break;
|
|
|
|
case PTP_EVENTCODE_OBJECTADDED:
|
|
hr = AddNewObject(pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_OBJECTREMOVED:
|
|
hr = RemoveObject(pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_STOREADDED:
|
|
hr = AddNewStorage(pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_STOREREMOVED:
|
|
hr = RemoveStorage(pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_DEVICEPROPCHANGED:
|
|
hr = DevicePropChanged((WORD) pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_OBJECTINFOCHANGED:
|
|
hr = ObjectInfoChanged(pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_DEVICEINFOCHANGED:
|
|
|
|
// WIAFIX-8/29/2000-davepar Need to handle this
|
|
|
|
//hr = RebuildDrvItemTree(&DevErrVal);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_REQUESTOBJECTTRANSFER:
|
|
//
|
|
// This event is ignored, because we don't know where to put the image. Maybe
|
|
// it should cause a "button pushed" event.
|
|
//
|
|
break;
|
|
|
|
case PTP_EVENTCODE_STOREFULL:
|
|
hr = StorageFull(pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_DEVICERESET:
|
|
|
|
// WIAFIX-8/29/2000-davepar Need to handle this
|
|
|
|
//hr = RebuildDrvItemTree(&DevErrVal);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_STORAGEINFOCHANGED:
|
|
hr = StorageInfoChanged(pEvent->Params[0]);
|
|
break;
|
|
|
|
case PTP_EVENTCODE_CAPTURECOMPLETE:
|
|
hr = CaptureComplete();
|
|
break;
|
|
|
|
case PTP_EVENTCODE_UNREPORTEDSTATUS:
|
|
|
|
// WIAFIX-8/29/2000-davepar Need to handle this
|
|
|
|
//hr = RebuildDrvItemTree(&DevErrVal);
|
|
break;
|
|
|
|
|
|
default:
|
|
|
|
//
|
|
// If it is a vendor's event, post it
|
|
//
|
|
if (pEvent->EventCode & PTP_DATACODE_VENDORMASK)
|
|
{
|
|
hr = PostVendorEvent(pEvent->EventCode);
|
|
}
|
|
|
|
break;
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function adds a new object to the driver item tree. If a new driver
|
|
// item is added, a WIA_EVENT_ITEM_CREATED event will be signaled.
|
|
//
|
|
// Input:
|
|
// ObjectHandle -- the new object handle
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::AddNewObject(DWORD ObjectHandle)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::AddNewObject");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
//
|
|
// If there is a capture in progress, we need to wait until all new objects are reported, and
|
|
// only then start querying imformation about them. See a sample sequence from the spec below:
|
|
//
|
|
// -> InitiateCapture Operation ->
|
|
// <- InitiateCapture Response <-
|
|
// <- ObjectAdded Event(1) <-
|
|
// <- ObjectAdded Event(2) <-
|
|
// <- ObjectAdded Event(n) <-
|
|
// <- CaptureComplete Event <-
|
|
// -> GetObjectInfo Operation(1) ->
|
|
// <- ObjectInfo Dataset/Response(1) <-
|
|
// -> GetObjectInfo Operation(2) ->
|
|
// <- ObjectInfo Dataset/Response(2) <-
|
|
// -> GetObjectInfo Operation(n) ->
|
|
// <- ObjectInfo Dataset/Response(n) <-
|
|
//
|
|
|
|
//
|
|
// Check if there is a capture in progress
|
|
//
|
|
DWORD dwWait = WaitForSingleObject(m_TakePictureDoneEvent, 0);
|
|
|
|
//
|
|
// If there is no capture in progress, process the new object immediately
|
|
//
|
|
if (dwWait == WAIT_OBJECT_0)
|
|
{
|
|
hr = AddObject(ObjectHandle, TRUE);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("AddNewObject", "AddObject failed");
|
|
goto Cleanup;
|
|
}
|
|
}
|
|
|
|
//
|
|
// If there is a capture in progress, add the new object's handle to the list,
|
|
// all new objects will be processed once capture is finished
|
|
//
|
|
else if (dwWait == WAIT_TIMEOUT)
|
|
{
|
|
m_CapturedObjects.Add(ObjectHandle);
|
|
}
|
|
|
|
//
|
|
// WAIT_FAILED or WAIT_ABANDONED - something's wrong
|
|
//
|
|
else
|
|
{
|
|
wiauDbgError("AddNewObject", "WaitForSingle object failed");
|
|
hr = E_FAIL;
|
|
goto Cleanup;
|
|
}
|
|
|
|
Cleanup:
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function removes the given object handle from the driver item tree.
|
|
// If the object handle has a driver item associated with it and the
|
|
// driver item is removed, a WIA_EVENT_ITEM_REMOVED event will be signaled.
|
|
//
|
|
// Input:
|
|
// ObjectHandle -- the object handle to be removed
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::RemoveObject(DWORD ObjectHandle)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::RemoveObject");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
//
|
|
// Find the driver item for the object handle.
|
|
//
|
|
IWiaDrvItem *pDrvItem = m_HandleItem.Lookup(ObjectHandle);
|
|
if (!pDrvItem)
|
|
{
|
|
wiauDbgError("RemoveObject", "tried to remove object that doesn't exist");
|
|
return S_FALSE;
|
|
}
|
|
|
|
//
|
|
// Try to remove the object from the ancillary assoc array, in case it's there too. Ancillary
|
|
// association objects actually point to images in the handle/item map, so don't delete the
|
|
// actual item
|
|
//
|
|
if (m_AncAssocParent.Remove(ObjectHandle))
|
|
{
|
|
wiauDbgTrace("RemoveObject", "ancillary association object removed");
|
|
}
|
|
else
|
|
{
|
|
BSTR bstrFullName;
|
|
hr = pDrvItem->GetFullItemName(&bstrFullName);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("RemoveObject", "GetFullItemName failed");
|
|
return hr;
|
|
}
|
|
|
|
hr = pDrvItem->RemoveItemFromFolder(WiaItemTypeDisconnected);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("RemoveObject", "UnlinkItemTree failed");
|
|
return hr;
|
|
}
|
|
|
|
hr = wiasQueueEvent(m_bstrDeviceId, &WIA_EVENT_ITEM_DELETED, bstrFullName);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("RemoveObject", "wiasQueueEvent failed");
|
|
return hr;
|
|
}
|
|
|
|
SysFreeString(bstrFullName);
|
|
}
|
|
|
|
//
|
|
// Remove the object from the handle/drvItem association
|
|
//
|
|
m_HandleItem.Remove(ObjectHandle);
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function adds a new storage to the driver item tree.
|
|
// A WIA_EVENT_STORAGE_CREATED event will be singaled.
|
|
//
|
|
// Input:
|
|
// StorageId -- the new storage id to be added
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::AddNewStorage(DWORD StorageId)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::AddNewStorage");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
CArray32 StorageIdList;
|
|
|
|
//
|
|
// If several logical stores were added, the device may indicate
|
|
// to re-enumerate the stores
|
|
//
|
|
if (StorageId == PTP_STORAGEID_UNDEFINED)
|
|
{
|
|
hr = m_pPTPCamera->GetStorageIDs(&StorageIdList);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("AddNewStorage", "GetStorageIDs failed");
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// Loop through the list of new storage ids, removing the ones
|
|
// that have already been enumerated
|
|
//
|
|
int index;
|
|
for (int count = 0; count < StorageIdList.GetSize(); count++)
|
|
{
|
|
index = m_StorageIds.Find(StorageIdList[count]);
|
|
if (index >= 0)
|
|
{
|
|
StorageIdList.RemoveAt(index);
|
|
}
|
|
}
|
|
}
|
|
|
|
//
|
|
// Otherwise there is just one storage id to work on
|
|
//
|
|
else
|
|
{
|
|
StorageIdList.Add(StorageId);
|
|
}
|
|
|
|
//
|
|
// Loop through all of the new storage ids
|
|
//
|
|
CPtpStorageInfo tempSI;
|
|
for (int storageIndex = 0; storageIndex < StorageIdList.GetSize(); storageIndex++)
|
|
{
|
|
//
|
|
// Get info for the new storage
|
|
//
|
|
hr = m_pPTPCamera->GetStorageInfo(StorageIdList[storageIndex], &tempSI);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("drvInitializeWia", "GetStorageInfo failed");
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// Add the storage id to the main list
|
|
//
|
|
if (!m_StorageIds.Add(StorageIdList[storageIndex]))
|
|
{
|
|
wiauDbgError("AddNewStorage", "add storage id failed");
|
|
return E_OUTOFMEMORY;
|
|
}
|
|
|
|
//
|
|
// Add storage info to array
|
|
//
|
|
if (!m_StorageInfos.Add(tempSI))
|
|
{
|
|
wiauDbgError("drvInitializeWia", "add storage info failed");
|
|
return E_OUTOFMEMORY;
|
|
}
|
|
|
|
//
|
|
// Add an empty entry to the DCIM handle array
|
|
//
|
|
ULONG dummy = 0;
|
|
if (!m_DcimHandle.Add(dummy))
|
|
{
|
|
wiauDbgError("AddNewStorage", "add dcim handle failed");
|
|
return E_OUTOFMEMORY;
|
|
}
|
|
|
|
//
|
|
// Loop through all of the objects on the new storage, adding them one
|
|
// at a time.
|
|
//
|
|
CArray32 ObjectHandleList;
|
|
|
|
hr = m_pPTPCamera->GetObjectHandles(StorageIdList[storageIndex], PTP_FORMATCODE_ALL,
|
|
PTP_OBJECTHANDLE_ALL, &ObjectHandleList);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("AddNewStorage", "GetObjectHandles failed");
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// Iterate through the object handles, creating a WIA driver item for each
|
|
//
|
|
for (int objectindex = 0; objectindex < ObjectHandleList.GetSize(); objectindex++)
|
|
{
|
|
hr = AddObject(ObjectHandleList[objectindex], TRUE);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("AddNewStorage", "AddObject failed");
|
|
return hr;
|
|
}
|
|
}
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function removes all of the objects on a storage from the
|
|
// driver item tree, signalling WIA_EVENT_ITEM_DELETED as appropriate.
|
|
//
|
|
// Input:
|
|
// StorageId -- storage to delete
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::RemoveStorage(DWORD StorageId)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::RemoveStorage");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
//
|
|
// If the lower 16 bits of the storage id is 0xffff, an entire physical store
|
|
// was removed--match only the upper 16 bits of the storage id
|
|
//
|
|
DWORD StorageIdMask = PTP_STORAGEID_ALL;
|
|
if ((StorageId & PTP_STORAGEID_LOGICAL) == PTP_STORAGEID_LOGICAL)
|
|
{
|
|
StorageIdMask = PTP_STORAGEID_PHYSICAL;
|
|
StorageId &= StorageIdMask;
|
|
}
|
|
|
|
//
|
|
// Traverse the driver item tree depth-first looking for objects that were on
|
|
// the removed storage
|
|
//
|
|
CWiaArray<IWiaDrvItem*> ItemStack;
|
|
IWiaDrvItem *pCurrent = NULL;
|
|
IWiaDrvItem *pChild = NULL;
|
|
IWiaDrvItem *pSibling = NULL;
|
|
|
|
if (m_pDrvItemRoot)
|
|
{
|
|
hr = m_pDrvItemRoot->GetFirstChildItem(&pCurrent);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("RemoveStorage", "GetFirstChildItem failed");
|
|
return hr;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
wiauDbgWarning("RemoveStorage", "Tree is not built yet (m_pDrvItemRoot is NULL)");
|
|
pCurrent = NULL;
|
|
}
|
|
|
|
while (pCurrent)
|
|
{
|
|
hr = pCurrent->GetFirstChildItem(&pChild);
|
|
|
|
//
|
|
// GetFirstChildItem returns E_INVALIDARG if there are no child items
|
|
//
|
|
if (FAILED(hr) && hr != E_INVALIDARG)
|
|
{
|
|
wiauDbgError("RemoveStorage", "GetFirstChildItem failed");
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// Children exist, so traverse down the tree
|
|
//
|
|
if (hr != E_INVALIDARG && pChild)
|
|
{
|
|
if (!ItemStack.Push(pCurrent))
|
|
{
|
|
wiauDbgError("RemoveStorage", "memory allocation failed");
|
|
return E_OUTOFMEMORY;
|
|
}
|
|
pCurrent = pChild;
|
|
pChild = NULL;
|
|
}
|
|
|
|
//
|
|
// No children, so look for siblings and potentially delete the current driver item
|
|
//
|
|
else
|
|
{
|
|
//
|
|
// Loop through all of the siblings
|
|
//
|
|
while (TRUE)
|
|
{
|
|
hr = pCurrent->GetNextSiblingItem(&pSibling);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("RemoveStorage", "GetNextSiblingItem failed");
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// See if the item is on the storage which was removed
|
|
//
|
|
PDRVITEM_CONTEXT pDrvItemContext;
|
|
hr = pCurrent->GetDeviceSpecContext((BYTE **) &pDrvItemContext);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("RemoveStorage", "GetDeviceSpecContext failed");
|
|
return hr;
|
|
}
|
|
|
|
if ((pDrvItemContext->pObjectInfo->m_StorageId & StorageIdMask) == StorageId)
|
|
{
|
|
//
|
|
// Remove the item
|
|
//
|
|
hr = RemoveObject(pDrvItemContext->pObjectInfo->m_ObjectHandle);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("RemoveStorage", "RemoveObject failed");
|
|
return hr;
|
|
}
|
|
}
|
|
|
|
//
|
|
// Found a sibling, so go to the top and look for children
|
|
//
|
|
if (pSibling)
|
|
{
|
|
pCurrent = pSibling;
|
|
pSibling = NULL;
|
|
break;
|
|
}
|
|
|
|
//
|
|
// No sibling, so pop up a level
|
|
//
|
|
else
|
|
{
|
|
if (ItemStack.GetSize() > 0)
|
|
{
|
|
if (!ItemStack.Pop(pCurrent))
|
|
{
|
|
wiauDbgError("RemoveStorage", "Pop failed");
|
|
return E_FAIL;
|
|
}
|
|
}
|
|
|
|
//
|
|
// No more levels to pop, so the loop is done
|
|
//
|
|
else
|
|
{
|
|
pCurrent = NULL;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
//
|
|
// Remove the store from the appropriate arrays
|
|
//
|
|
for (int count = 0; count < m_StorageIds.GetSize(); count++)
|
|
{
|
|
if ((m_StorageIds[count] & StorageIdMask) == StorageId)
|
|
{
|
|
m_StorageIds.RemoveAt(count);
|
|
m_StorageInfos.RemoveAt(count);
|
|
m_DcimHandle.RemoveAt(count);
|
|
count--;
|
|
}
|
|
}
|
|
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function updates the value for a property
|
|
//
|
|
// Input:
|
|
// PropCode -- property code that was updated
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::DevicePropChanged(WORD PropCode)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::DevicePropChanged");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
int idx = m_DeviceInfo.m_SupportedProps.Find(PropCode);
|
|
if (idx < 0)
|
|
{
|
|
wiauDbgWarning("DevicePropChanged", "prop code not found %d", PropCode);
|
|
return hr;
|
|
}
|
|
|
|
hr = m_pPTPCamera->GetDevicePropValue(PropCode, &m_PropDescs[idx]);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("DevicePropChanged", "GetDevicePropValue failed");
|
|
return hr;
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function updates the object info for an object
|
|
//
|
|
// Input:
|
|
// ObjectHandle -- the object whose ObjectInfo needs updating
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::ObjectInfoChanged(DWORD ObjectHandle)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::ObjectInfoChanged");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
|
|
//
|
|
// Find the driver item for the object handle.
|
|
//
|
|
IWiaDrvItem *pDrvItem = m_HandleItem.Lookup(ObjectHandle);
|
|
if (!pDrvItem)
|
|
{
|
|
wiauDbgError("ObjectInfoChanged", "tried to update object that doesn't exist");
|
|
return S_FALSE;
|
|
}
|
|
|
|
PDRVITEM_CONTEXT pDrvItemContext;
|
|
hr = pDrvItem->GetDeviceSpecContext((BYTE **) &pDrvItemContext);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("ObjectInfoChanged", "GetDeviceSpecContext failed");
|
|
return hr;
|
|
}
|
|
|
|
hr = m_pPTPCamera->GetObjectInfo(ObjectHandle, pDrvItemContext->pObjectInfo);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("ObjectInfoChanged", "GetObjectInfo failed");
|
|
return hr;
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function marks a storage as full
|
|
//
|
|
// Input:
|
|
// StorageId -- the storage to be marked
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::StorageFull(DWORD StorageId)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::StorageFull");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
INT index = m_StorageIds.Find(StorageId);
|
|
if (index < 0)
|
|
{
|
|
wiauDbgError("StorageFull", "storage id not found");
|
|
return S_FALSE;
|
|
}
|
|
|
|
CPtpStorageInfo *pStorageInfo = &m_StorageInfos[index];
|
|
|
|
pStorageInfo->m_FreeSpaceInBytes = 0;
|
|
pStorageInfo->m_FreeSpaceInImages = 0;
|
|
|
|
//
|
|
// Signal that the TakePicture command is complete, if the driver was waiting for one
|
|
//
|
|
if (!SetEvent(m_TakePictureDoneEvent))
|
|
{
|
|
hr = HRESULT_FROM_WIN32(::GetLastError());
|
|
wiauDbgErrorHr(hr, "EventCallbackDispatch", "SetEvent failed");
|
|
return hr;
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function updates a StorageInfo
|
|
//
|
|
// Input:
|
|
// StorageId -- the storage id to be updated
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::StorageInfoChanged(DWORD StorageId)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::StorageInfoChanged");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
INT index = m_StorageIds.Find(StorageId);
|
|
if (index < 0)
|
|
{
|
|
wiauDbgError("StorageInfoChanged", "storage id not found");
|
|
return S_FALSE;
|
|
}
|
|
|
|
CPtpStorageInfo *pStorageInfo = &m_StorageInfos[index];
|
|
|
|
hr = m_pPTPCamera->GetStorageInfo(StorageId, pStorageInfo);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("StorageInfoChanged", "GetStorageInfo failed");
|
|
return hr;
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function processes the CaptureComplete event
|
|
//
|
|
// Input:
|
|
// StorageId -- the storage id to be updated
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::CaptureComplete()
|
|
{
|
|
DBG_FN("CWiaMiniDriver::CaptureComplete");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
//
|
|
// Signal that the TakePicture command is complete
|
|
//
|
|
if (!SetEvent(m_TakePictureDoneEvent))
|
|
{
|
|
hr = HRESULT_FROM_WIN32(::GetLastError());
|
|
wiauDbgErrorHr(hr, "EventCallbackDispatch", "SetEvent failed");
|
|
return hr;
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|
|
//
|
|
// This function posts a vendor defined event
|
|
//
|
|
// Input:
|
|
// EventCode -- the event code
|
|
//
|
|
HRESULT
|
|
CWiaMiniDriver::PostVendorEvent(WORD EventCode)
|
|
{
|
|
DBG_FN("CWiaMiniDriver::PostVendorEvent");
|
|
|
|
HRESULT hr = S_OK;
|
|
|
|
CVendorEventInfo *pEventInfo = NULL;
|
|
|
|
pEventInfo = m_VendorEventMap.Lookup(EventCode);
|
|
if (pEventInfo)
|
|
{
|
|
hr = wiasQueueEvent(m_bstrDeviceId, pEventInfo->pGuid, NULL);
|
|
if (FAILED(hr))
|
|
{
|
|
wiauDbgError("PostVendorEvent", "wiasQueueEvent failed");
|
|
return hr;
|
|
}
|
|
}
|
|
|
|
return hr;
|
|
}
|
|
|