Commit ad03df12 authored by Rémi Bernon's avatar Rémi Bernon Committed by Alexandre Julliard

hid: Introduce new enum_value_caps helper for HidP_GetSpecificButtonCaps.

parent 04bd7c9d
...@@ -66,6 +66,49 @@ static NTSTATUS get_value_caps_range( WINE_HIDP_PREPARSED_DATA *preparsed, HIDP_ ...@@ -66,6 +66,49 @@ static NTSTATUS get_value_caps_range( WINE_HIDP_PREPARSED_DATA *preparsed, HIDP_
return HIDP_STATUS_SUCCESS; return HIDP_STATUS_SUCCESS;
} }
struct caps_filter
{
BOOLEAN buttons;
USAGE usage_page;
USHORT collection;
USAGE usage;
};
static BOOL match_value_caps( const struct hid_value_caps *caps, const struct caps_filter *filter )
{
if (!caps->usage_min && !caps->usage_max) return FALSE;
if (filter->buttons && !HID_VALUE_CAPS_IS_BUTTON( caps )) return FALSE;
if (filter->usage_page && filter->usage_page != caps->usage_page) return FALSE;
if (filter->collection && filter->collection != caps->link_collection) return FALSE;
if (!filter->usage) return TRUE;
return caps->usage_min <= filter->usage && caps->usage_max >= filter->usage;
}
typedef NTSTATUS (*enum_value_caps_callback)( const struct hid_value_caps *caps, void *user );
static NTSTATUS enum_value_caps( WINE_HIDP_PREPARSED_DATA *preparsed, HIDP_REPORT_TYPE report_type,
const struct caps_filter *filter, enum_value_caps_callback callback,
void *user, USHORT *count )
{
const struct hid_value_caps *caps, *caps_end;
NTSTATUS status;
LONG remaining = *count;
for (status = get_value_caps_range( preparsed, report_type, 0, &caps, &caps_end );
status == HIDP_STATUS_SUCCESS && caps != caps_end; caps++)
{
if (!match_value_caps( caps, filter )) continue;
if (remaining-- > 0) status = callback( caps, user );
}
if (status != HIDP_STATUS_SUCCESS) return status;
*count -= remaining;
if (*count == 0) return HIDP_STATUS_USAGE_NOT_FOUND;
if (remaining < 0) return HIDP_STATUS_BUFFER_TOO_SMALL;
return HIDP_STATUS_SUCCESS;
}
static NTSTATUS get_report_data(BYTE *report, INT reportLength, INT startBit, INT valueSize, PULONG value) static NTSTATUS get_report_data(BYTE *report, INT reportLength, INT startBit, INT valueSize, PULONG value)
{ {
...@@ -192,17 +235,18 @@ NTSTATUS WINAPI HidP_GetButtonCaps( HIDP_REPORT_TYPE report_type, HIDP_BUTTON_CA ...@@ -192,17 +235,18 @@ NTSTATUS WINAPI HidP_GetButtonCaps( HIDP_REPORT_TYPE report_type, HIDP_BUTTON_CA
return HidP_GetSpecificButtonCaps( report_type, 0, 0, 0, caps, caps_count, preparsed_data ); return HidP_GetSpecificButtonCaps( report_type, 0, 0, 0, caps, caps_count, preparsed_data );
} }
NTSTATUS WINAPI HidP_GetCaps(PHIDP_PREPARSED_DATA PreparsedData, NTSTATUS WINAPI HidP_GetCaps( PHIDP_PREPARSED_DATA preparsed_data, HIDP_CAPS *caps )
PHIDP_CAPS Capabilities)
{ {
PWINE_HIDP_PREPARSED_DATA data = (PWINE_HIDP_PREPARSED_DATA)PreparsedData; WINE_HIDP_PREPARSED_DATA *preparsed = (WINE_HIDP_PREPARSED_DATA *)preparsed_data;
TRACE("(%p, %p)\n",PreparsedData, Capabilities); TRACE( "preparsed_data %p, caps %p.\n", preparsed_data, caps );
if (data->magic != HID_MAGIC) if (preparsed->magic != HID_MAGIC) return HIDP_STATUS_INVALID_PREPARSED_DATA;
return HIDP_STATUS_INVALID_PREPARSED_DATA;
*Capabilities = data->caps; *caps = preparsed->caps;
caps->NumberInputButtonCaps = preparsed->new_caps.NumberInputButtonCaps;
caps->NumberOutputButtonCaps = preparsed->new_caps.NumberOutputButtonCaps;
caps->NumberFeatureButtonCaps = preparsed->new_caps.NumberFeatureButtonCaps;
return HIDP_STATUS_SUCCESS; return HIDP_STATUS_SUCCESS;
} }
...@@ -603,75 +647,59 @@ NTSTATUS WINAPI HidP_TranslateUsagesToI8042ScanCodes(USAGE *ChangedUsageList, ...@@ -603,75 +647,59 @@ NTSTATUS WINAPI HidP_TranslateUsagesToI8042ScanCodes(USAGE *ChangedUsageList,
return STATUS_NOT_IMPLEMENTED; return STATUS_NOT_IMPLEMENTED;
} }
NTSTATUS WINAPI HidP_GetSpecificButtonCaps(HIDP_REPORT_TYPE ReportType, static NTSTATUS get_button_caps( const struct hid_value_caps *caps, void *user )
USAGE UsagePage, USHORT LinkCollection, USAGE Usage,
HIDP_BUTTON_CAPS *ButtonCaps, USHORT *ButtonCapsLength, PHIDP_PREPARSED_DATA PreparsedData)
{ {
WINE_HIDP_PREPARSED_DATA *data = (WINE_HIDP_PREPARSED_DATA*)PreparsedData; HIDP_BUTTON_CAPS **iter = user, *dst = *iter;
WINE_HID_ELEMENT *elems = HID_ELEMS(data); dst->UsagePage = caps->usage_page;
WINE_HID_REPORT *report = NULL; dst->ReportID = caps->report_id;
USHORT b_count = 0, r_count = 0; dst->LinkCollection = caps->link_collection;
int i,j,u; dst->LinkUsagePage = caps->link_usage_page;
dst->LinkUsage = caps->link_usage;
TRACE("(%i, 0x%x, %i, 0x%x, %p %p %p)\n", ReportType, UsagePage, LinkCollection, dst->BitField = caps->bit_field;
Usage, ButtonCaps, ButtonCapsLength, PreparsedData); dst->IsAlias = FALSE;
dst->IsAbsolute = HID_VALUE_CAPS_IS_ABSOLUTE( caps );
if (data->magic != HID_MAGIC) if (!(dst->IsRange = caps->is_range))
return HIDP_STATUS_INVALID_PREPARSED_DATA; {
dst->NotRange.Usage = caps->usage_min;
switch(ReportType) dst->NotRange.DataIndex = caps->data_index_min;
{
case HidP_Input:
b_count = data->caps.NumberInputButtonCaps;
report = HID_INPUT_REPORTS(data);
break;
case HidP_Output:
b_count = data->caps.NumberOutputButtonCaps;
report = HID_OUTPUT_REPORTS(data);
break;
case HidP_Feature:
b_count = data->caps.NumberFeatureButtonCaps;
report = HID_FEATURE_REPORTS(data);
break;
default:
return HIDP_STATUS_INVALID_REPORT_TYPE;
} }
r_count = data->reportCount[ReportType]; else
if (!r_count || !b_count)
{ {
*ButtonCapsLength = 0; dst->Range.UsageMin = caps->usage_min;
return HIDP_STATUS_SUCCESS; dst->Range.UsageMax = caps->usage_max;
dst->Range.DataIndexMin = caps->data_index_min;
dst->Range.DataIndexMax = caps->data_index_max;
} }
if (!(dst->IsStringRange = caps->is_string_range))
b_count = min(b_count, *ButtonCapsLength); dst->NotRange.StringIndex = caps->string_min;
else
u = 0;
for (j = 0; j < r_count && u < b_count; j++)
{
for (i = 0; i < report[j].elementCount && u < b_count; i++)
{
if (elems[report[j].elementIdx + i].caps.BitSize == 1 &&
(UsagePage == 0 || UsagePage == elems[report[j].elementIdx + i].caps.UsagePage) &&
(LinkCollection == 0 || LinkCollection == elems[report[j].elementIdx + i].caps.LinkCollection) &&
(Usage == 0 || (
(!elems[report[j].elementIdx + i].caps.IsRange &&
Usage == elems[report[j].elementIdx + i].caps.NotRange.Usage)) ||
(elems[report[j].elementIdx + i].caps.IsRange &&
Usage >= elems[report[j].elementIdx + i].caps.Range.UsageMin &&
Usage <= elems[report[j].elementIdx + i].caps.Range.UsageMax)))
{ {
ButtonCaps[u++] = *(HIDP_BUTTON_CAPS *)&elems[report[j].elementIdx + i].caps; dst->Range.StringMin = caps->string_min;
} dst->Range.StringMax = caps->string_max;
} }
if ((dst->IsDesignatorRange = caps->is_designator_range))
dst->NotRange.DesignatorIndex = caps->designator_min;
else
{
dst->Range.DesignatorMin = caps->designator_min;
dst->Range.DesignatorMax = caps->designator_max;
} }
TRACE("Matched %i usages\n", u); *iter += 1;
*ButtonCapsLength = u;
return HIDP_STATUS_SUCCESS; return HIDP_STATUS_SUCCESS;
} }
NTSTATUS WINAPI HidP_GetSpecificButtonCaps( HIDP_REPORT_TYPE report_type, USAGE usage_page, USHORT collection,
USAGE usage, HIDP_BUTTON_CAPS *caps, USHORT *caps_count,
PHIDP_PREPARSED_DATA preparsed_data )
{
WINE_HIDP_PREPARSED_DATA *preparsed = (WINE_HIDP_PREPARSED_DATA *)preparsed_data;
const struct caps_filter filter = {.buttons = TRUE, .usage_page = usage_page, .collection = collection, .usage = usage};
TRACE( "report_type %d, usage_page %x, collection %d, usage %x, caps %p, caps_count %p, preparsed_data %p.\n",
report_type, usage_page, collection, usage, caps, caps_count, preparsed_data );
return enum_value_caps( preparsed, report_type, &filter, get_button_caps, &caps, caps_count );
}
NTSTATUS WINAPI HidP_GetSpecificValueCaps(HIDP_REPORT_TYPE ReportType, NTSTATUS WINAPI HidP_GetSpecificValueCaps(HIDP_REPORT_TYPE ReportType,
USAGE UsagePage, USHORT LinkCollection, USAGE Usage, USAGE UsagePage, USHORT LinkCollection, USAGE Usage,
......
...@@ -1833,7 +1833,6 @@ static void test_hidp(HANDLE file, int report_id) ...@@ -1833,7 +1833,6 @@ static void test_hidp(HANDLE file, int report_id)
check_member(caps, expect_hidp_caps[report_id], "%d", OutputReportByteLength); check_member(caps, expect_hidp_caps[report_id], "%d", OutputReportByteLength);
check_member(caps, expect_hidp_caps[report_id], "%d", FeatureReportByteLength); check_member(caps, expect_hidp_caps[report_id], "%d", FeatureReportByteLength);
check_member(caps, expect_hidp_caps[report_id], "%d", NumberLinkCollectionNodes); check_member(caps, expect_hidp_caps[report_id], "%d", NumberLinkCollectionNodes);
todo_wine
check_member(caps, expect_hidp_caps[report_id], "%d", NumberInputButtonCaps); check_member(caps, expect_hidp_caps[report_id], "%d", NumberInputButtonCaps);
todo_wine todo_wine
check_member(caps, expect_hidp_caps[report_id], "%d", NumberInputValueCaps); check_member(caps, expect_hidp_caps[report_id], "%d", NumberInputValueCaps);
...@@ -1870,15 +1869,12 @@ static void test_hidp(HANDLE file, int report_id) ...@@ -1870,15 +1869,12 @@ static void test_hidp(HANDLE file, int report_id)
count = ARRAY_SIZE(button_caps); count = ARRAY_SIZE(button_caps);
status = HidP_GetButtonCaps(HidP_Output, button_caps, &count, preparsed_data); status = HidP_GetButtonCaps(HidP_Output, button_caps, &count, preparsed_data);
todo_wine
ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetButtonCaps returned %#x\n", status);
status = HidP_GetButtonCaps(HidP_Feature + 1, button_caps, &count, preparsed_data); status = HidP_GetButtonCaps(HidP_Feature + 1, button_caps, &count, preparsed_data);
ok(status == HIDP_STATUS_INVALID_REPORT_TYPE, "HidP_GetButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_INVALID_REPORT_TYPE, "HidP_GetButtonCaps returned %#x\n", status);
count = 0; count = 0;
status = HidP_GetButtonCaps(HidP_Input, button_caps, &count, preparsed_data); status = HidP_GetButtonCaps(HidP_Input, button_caps, &count, preparsed_data);
todo_wine
ok(status == HIDP_STATUS_BUFFER_TOO_SMALL, "HidP_GetButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_BUFFER_TOO_SMALL, "HidP_GetButtonCaps returned %#x\n", status);
todo_wine
ok(count == caps.NumberInputButtonCaps, "HidP_GetButtonCaps returned count %d, expected %d\n", ok(count == caps.NumberInputButtonCaps, "HidP_GetButtonCaps returned count %d, expected %d\n",
count, caps.NumberInputButtonCaps); count, caps.NumberInputButtonCaps);
count = ARRAY_SIZE(button_caps); count = ARRAY_SIZE(button_caps);
...@@ -1893,50 +1889,18 @@ static void test_hidp(HANDLE file, int report_id) ...@@ -1893,50 +1889,18 @@ static void test_hidp(HANDLE file, int report_id)
for (i = 0; i < ARRAY_SIZE(expect_button_caps); ++i) for (i = 0; i < ARRAY_SIZE(expect_button_caps); ++i)
{ {
winetest_push_context("button_caps[%d]", i); winetest_push_context("button_caps[%d]", i);
todo_wine_if(i >= 2) check_hidp_button_caps(&button_caps[i], &expect_button_caps[i]);
check_member(button_caps[i], expect_button_caps[i], "%04x", UsagePage);
check_member(button_caps[i], expect_button_caps[i], "%d", ReportID);
check_member(button_caps[i], expect_button_caps[i], "%d", IsAlias);
todo_wine_if(i == 1 || i == 2)
check_member(button_caps[i], expect_button_caps[i], "%d", BitField);
todo_wine_if(i >= 2)
check_member(button_caps[i], expect_button_caps[i], "%d", LinkCollection);
todo_wine_if(i >= (report_id ? 2 : 3))
check_member(button_caps[i], expect_button_caps[i], "%04x", LinkUsage);
todo_wine_if(i >= (report_id ? 2 : 3))
check_member(button_caps[i], expect_button_caps[i], "%04x", LinkUsagePage);
todo_wine_if(i >= 1 && i <= (report_id ? 2 : 1))
check_member(button_caps[i], expect_button_caps[i], "%d", IsRange);
check_member(button_caps[i], expect_button_caps[i], "%d", IsStringRange);
check_member(button_caps[i], expect_button_caps[i], "%d", IsDesignatorRange);
todo_wine_if(i == 2)
check_member(button_caps[i], expect_button_caps[i], "%d", IsAbsolute);
todo_wine_if(i >= 1)
check_member(button_caps[i], expect_button_caps[i], "%04x", Range.UsageMin);
todo_wine_if(i >= 1)
check_member(button_caps[i], expect_button_caps[i], "%04x", Range.UsageMax);
check_member(button_caps[i], expect_button_caps[i], "%d", Range.StringMin);
check_member(button_caps[i], expect_button_caps[i], "%d", Range.StringMax);
check_member(button_caps[i], expect_button_caps[i], "%d", Range.DesignatorMin);
check_member(button_caps[i], expect_button_caps[i], "%d", Range.DesignatorMax);
todo_wine_if(i >= 1)
check_member(button_caps[i], expect_button_caps[i], "%d", Range.DataIndexMin);
todo_wine_if(i >= 1)
check_member(button_caps[i], expect_button_caps[i], "%d", Range.DataIndexMax);
winetest_pop_context(); winetest_pop_context();
} }
count = ARRAY_SIZE(button_caps) - 1; count = ARRAY_SIZE(button_caps) - 1;
status = HidP_GetSpecificButtonCaps(HidP_Output, 0, 0, 0, button_caps, &count, preparsed_data); status = HidP_GetSpecificButtonCaps(HidP_Output, 0, 0, 0, button_caps, &count, preparsed_data);
todo_wine
ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status);
status = HidP_GetSpecificButtonCaps(HidP_Feature + 1, 0, 0, 0, button_caps, &count, preparsed_data); status = HidP_GetSpecificButtonCaps(HidP_Feature + 1, 0, 0, 0, button_caps, &count, preparsed_data);
ok(status == HIDP_STATUS_INVALID_REPORT_TYPE, "HidP_GetSpecificButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_INVALID_REPORT_TYPE, "HidP_GetSpecificButtonCaps returned %#x\n", status);
count = 0; count = 0;
status = HidP_GetSpecificButtonCaps(HidP_Input, 0, 0, 0, button_caps, &count, preparsed_data); status = HidP_GetSpecificButtonCaps(HidP_Input, 0, 0, 0, button_caps, &count, preparsed_data);
todo_wine
ok(status == HIDP_STATUS_BUFFER_TOO_SMALL, "HidP_GetSpecificButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_BUFFER_TOO_SMALL, "HidP_GetSpecificButtonCaps returned %#x\n", status);
todo_wine
ok(count == caps.NumberInputButtonCaps, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n", ok(count == caps.NumberInputButtonCaps, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n",
count, caps.NumberInputButtonCaps); count, caps.NumberInputButtonCaps);
count = ARRAY_SIZE(button_caps) - 1; count = ARRAY_SIZE(button_caps) - 1;
...@@ -1957,17 +1921,14 @@ static void test_hidp(HANDLE file, int report_id) ...@@ -1957,17 +1921,14 @@ static void test_hidp(HANDLE file, int report_id)
count = 0xbeef; count = 0xbeef;
status = HidP_GetSpecificButtonCaps(HidP_Input, 0xfffe, 0, 0, button_caps, &count, preparsed_data); status = HidP_GetSpecificButtonCaps(HidP_Input, 0xfffe, 0, 0, button_caps, &count, preparsed_data);
todo_wine
ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status);
ok(count == 0, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n", count, 0); ok(count == 0, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n", count, 0);
count = 0xbeef; count = 0xbeef;
status = HidP_GetSpecificButtonCaps(HidP_Input, 0, 0xfffe, 0, button_caps, &count, preparsed_data); status = HidP_GetSpecificButtonCaps(HidP_Input, 0, 0xfffe, 0, button_caps, &count, preparsed_data);
todo_wine
ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status);
ok(count == 0, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n", count, 0); ok(count == 0, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n", count, 0);
count = 0xbeef; count = 0xbeef;
status = HidP_GetSpecificButtonCaps(HidP_Input, 0, 0, 0xfffe, button_caps, &count, preparsed_data); status = HidP_GetSpecificButtonCaps(HidP_Input, 0, 0, 0xfffe, button_caps, &count, preparsed_data);
todo_wine
ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status); ok(status == HIDP_STATUS_USAGE_NOT_FOUND, "HidP_GetSpecificButtonCaps returned %#x\n", status);
ok(count == 0, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n", count, 0); ok(count == 0, "HidP_GetSpecificButtonCaps returned count %d, expected %d\n", count, 0);
......
...@@ -38,36 +38,6 @@ typedef struct __WINE_ELEMENT ...@@ -38,36 +38,6 @@ typedef struct __WINE_ELEMENT
HIDP_VALUE_CAPS caps; HIDP_VALUE_CAPS caps;
} WINE_HID_ELEMENT; } WINE_HID_ELEMENT;
/* make sure HIDP_BUTTON_CAPS is a subset of HIDP_VALUE_CAPS */
C_ASSERT( sizeof(HIDP_BUTTON_CAPS) == sizeof(HIDP_VALUE_CAPS) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, UsagePage) == offsetof(HIDP_VALUE_CAPS, UsagePage) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, ReportID) == offsetof(HIDP_VALUE_CAPS, ReportID) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, IsAlias) == offsetof(HIDP_VALUE_CAPS, IsAlias) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, BitField) == offsetof(HIDP_VALUE_CAPS, BitField) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, LinkCollection) == offsetof(HIDP_VALUE_CAPS, LinkCollection) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, LinkUsage) == offsetof(HIDP_VALUE_CAPS, LinkUsage) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, LinkUsagePage) == offsetof(HIDP_VALUE_CAPS, LinkUsagePage) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, IsRange) == offsetof(HIDP_VALUE_CAPS, IsRange) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, IsStringRange) == offsetof(HIDP_VALUE_CAPS, IsStringRange) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, IsDesignatorRange) == offsetof(HIDP_VALUE_CAPS, IsDesignatorRange) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, IsAbsolute) == offsetof(HIDP_VALUE_CAPS, IsAbsolute) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.UsageMin) == offsetof(HIDP_VALUE_CAPS, Range.UsageMin) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.UsageMax) == offsetof(HIDP_VALUE_CAPS, Range.UsageMax) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.StringMin) == offsetof(HIDP_VALUE_CAPS, Range.StringMin) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.StringMax) == offsetof(HIDP_VALUE_CAPS, Range.StringMax) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.DesignatorMin) == offsetof(HIDP_VALUE_CAPS, Range.DesignatorMin) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.DesignatorMax) == offsetof(HIDP_VALUE_CAPS, Range.DesignatorMax) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.DataIndexMin) == offsetof(HIDP_VALUE_CAPS, Range.DataIndexMin) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, Range.DataIndexMax) == offsetof(HIDP_VALUE_CAPS, Range.DataIndexMax) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, NotRange.Usage) == offsetof(HIDP_VALUE_CAPS, NotRange.Usage) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, NotRange.StringIndex) == offsetof(HIDP_VALUE_CAPS, NotRange.StringIndex) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, NotRange.DesignatorIndex) == offsetof(HIDP_VALUE_CAPS, NotRange.DesignatorIndex) );
C_ASSERT( offsetof(HIDP_BUTTON_CAPS, NotRange.DataIndex) == offsetof(HIDP_VALUE_CAPS, NotRange.DataIndex) );
struct hid_value_caps struct hid_value_caps
{ {
USAGE usage_page; USAGE usage_page;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment