HIDProcessLocalItem.c [plain text]
#include "HIDLib.h"
OSStatus HIDProcessLocalItem(HIDReportDescriptor *ptDescriptor,
HIDPreparsedDataPtr ptPreparsedData)
{
HIDDesignatorItem *ptDesignatorItem;
HIDStringItem *ptStringItem;
HIDP_UsageItem *ptUsageItem;
HIDItem *ptItem;
if ((ptDescriptor == NULL) || (ptPreparsedData == NULL))
return kHIDNullPointerErr;
ptItem = &ptDescriptor->item;
switch (ptItem->tag)
{
case kHIDTagUsage:
ptUsageItem = &ptPreparsedData->usageItems[ptPreparsedData->usageItemCount++];
ptUsageItem->isRange = false;
if (ptItem->byteCount == 4)
{
ptUsageItem->usagePage = ptItem->unsignedValue>>16;
ptUsageItem->usage = ptItem->unsignedValue&0xFFFFL;
}
else
{
ptUsageItem->usagePage = ptDescriptor->globals.usagePage;
ptUsageItem->usage = ptItem->unsignedValue;
}
break;
case kHIDTagUsageMinimum:
if (ptDescriptor->haveUsageMax)
{
ptUsageItem = &ptPreparsedData->usageItems[ptPreparsedData->usageItemCount++];
ptUsageItem->isRange = true;
if (ptItem->byteCount == 4)
{
ptUsageItem->usagePage = ptItem->unsignedValue>>16;
ptUsageItem->usageMinimum = ptItem->unsignedValue&0xFFFFL;
}
else
{
ptUsageItem->usagePage = ptDescriptor->globals.usagePage;
ptUsageItem->usageMinimum = ptItem->unsignedValue;
}
if (ptUsageItem->usagePage != (HIDUsage)ptDescriptor->rangeUsagePage)
return kHIDInvalidRangePageErr;
ptUsageItem->usageMaximum = ptDescriptor->usageMaximum;
if (ptUsageItem->usageMaximum < ptUsageItem->usageMinimum)
return kHIDInvertedUsageRangeErr;
ptDescriptor->haveUsageMax = false;
ptDescriptor->haveUsageMin = false;
}
else
{
if (ptItem->byteCount == 4)
{
ptDescriptor->rangeUsagePage = ptItem->unsignedValue>>16;
ptDescriptor->usageMinimum = ptItem->unsignedValue&0xFFFFL;
}
else
{
ptDescriptor->rangeUsagePage = ptDescriptor->globals.usagePage;
ptDescriptor->usageMinimum = ptItem->unsignedValue;
}
ptDescriptor->haveUsageMin = true;
}
break;
case kHIDTagUsageMaximum:
if (ptDescriptor->haveUsageMin)
{
ptUsageItem = &ptPreparsedData->usageItems[ptPreparsedData->usageItemCount++];
ptUsageItem->isRange = true;
if (ptItem->byteCount == 4)
{
ptUsageItem->usagePage = ptItem->unsignedValue>>16;
ptUsageItem->usageMaximum = ptItem->unsignedValue&0xFFFFL;
}
else
{
ptUsageItem->usagePage = ptDescriptor->globals.usagePage;
ptUsageItem->usageMaximum = ptItem->unsignedValue;
}
if (ptUsageItem->usagePage != (HIDUsage)ptDescriptor->rangeUsagePage)
return kHIDInvalidRangePageErr;
ptUsageItem->usageMinimum = ptDescriptor->usageMinimum;
if (ptUsageItem->usageMaximum < ptUsageItem->usageMinimum)
return kHIDInvertedUsageRangeErr;
ptDescriptor->haveUsageMax = false;
ptDescriptor->haveUsageMin = false;
}
else
{
if (ptItem->byteCount == 4)
{
ptDescriptor->rangeUsagePage = ptItem->unsignedValue>>16;
ptDescriptor->usageMaximum = ptItem->unsignedValue&0xFFFFL;
}
else
{
ptDescriptor->rangeUsagePage = ptDescriptor->globals.usagePage;
ptDescriptor->usageMaximum = ptItem->unsignedValue;
}
ptDescriptor->haveUsageMax = true;
}
break;
case kHIDTagDesignatorIndex:
ptDesignatorItem = &ptPreparsedData->desigItems[ptPreparsedData->desigItemCount++];
ptDesignatorItem->isRange = false;
ptDesignatorItem->index = ptItem->unsignedValue;
break;
case kHIDTagDesignatorMinimum:
if (ptDescriptor->haveDesigMax)
{
ptDesignatorItem = &ptPreparsedData->desigItems[ptPreparsedData->desigItemCount++];
ptDesignatorItem->isRange = true;
ptDesignatorItem->minimum = ptItem->unsignedValue;
ptDesignatorItem->maximum = ptDescriptor->desigMaximum;
ptDescriptor->haveDesigMin = false;
ptDescriptor->haveDesigMax = false;
}
else
{
ptDescriptor->desigMinimum = ptItem->unsignedValue;
ptDescriptor->haveDesigMin = true;
}
break;
case kHIDTagDesignatorMaximum:
if (ptDescriptor->haveDesigMin)
{
ptDesignatorItem = &ptPreparsedData->desigItems[ptPreparsedData->desigItemCount++];
ptDesignatorItem->isRange = true;
ptDesignatorItem->maximum = ptItem->unsignedValue;
ptDesignatorItem->minimum = ptDescriptor->desigMinimum;
ptDescriptor->haveDesigMin = false;
ptDescriptor->haveDesigMax = false;
}
else
{
ptDescriptor->desigMaximum = ptItem->unsignedValue;
ptDescriptor->haveDesigMax = true;
}
break;
case kHIDTagStringIndex:
ptStringItem = &ptPreparsedData->stringItems[ptPreparsedData->stringItemCount++];
ptStringItem->isRange = false;
ptStringItem->index = ptItem->unsignedValue;
break;
case kHIDTagStringMinimum:
if (ptDescriptor->haveStringMax)
{
ptStringItem = &ptPreparsedData->stringItems[ptPreparsedData->stringItemCount++];
ptStringItem->isRange = true;
ptStringItem->minimum = ptItem->unsignedValue;
ptStringItem->maximum = ptDescriptor->stringMaximum;
ptDescriptor->haveStringMin = false;
ptDescriptor->haveStringMax = false;
}
else
{
ptDescriptor->stringMinimum = ptItem->unsignedValue;
ptDescriptor->haveStringMin = true;
}
break;
case kHIDTagStringMaximum:
if (ptDescriptor->haveStringMin)
{
ptStringItem = &ptPreparsedData->stringItems[ptPreparsedData->stringItemCount++];
ptStringItem->isRange = true;
ptStringItem->maximum = ptItem->unsignedValue;
ptStringItem->minimum = ptDescriptor->stringMinimum;
ptDescriptor->haveStringMin = false;
ptDescriptor->haveStringMax = false;
}
else
{
ptDescriptor->stringMaximum = ptItem->unsignedValue;
ptDescriptor->haveStringMax = true;
}
break;
case kHIDTagSetDelimiter:
break;
}
return kHIDSuccess;
}