1 /* This file tests that the host correctly receives the keys the device sends to it. */
2
3 #include "usbx_test_common_hid.h"
4
5 #include "ux_host_class_hid_keyboard.h"
6
7 #define HOST_WAIT_TIME 1
8 #define SLAVE_WAIT_TIME (6*HOST_WAIT_TIME)
9
10 #ifndef UX_HID_KEYBOARD_PHANTOM_STATE
11 #define UX_HID_KEYBOARD_PHANTOM_STATE 0x01
12 #endif
13 #define KEY_START (UX_HID_KEYBOARD_PHANTOM_STATE+1)
14
15 static UCHAR ux_host_class_hid_keyboard_regular_array[] =
16 {
17 0,0,0,0,
18 'a','b','c','d','e','f','g','h','i','j','k','l','m','n',
19 'o','p','q','r','s','t','u','v','w','x','y','z',
20 '1','2','3','4','5','6','7','8','9','0',
21 0x0d,0x1b,0x08,0x07,0x20,'-','=','[',']',
22 '\\','#',';',0x27,'`',',','.','/',0xf0,
23 0xbb,0xbc,0xbd,0xbe,0xbf,0xc0,0xc1,0xc2,0xc3,0xc4,0xc5,0xc6,
24 0x00,0xf1,0x00,0xd2,0xc7,0xc9,0xd3,0xcf,0xd1,0xcd,0xcb,0xd0,0xc8,0xf2,
25 '/','*','-','+',
26 0x0d,'1','2','3','4','5','6','7','8','9','0','.','\\',0x00,0x00,'=',
27 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
28 };
29
30 static UCHAR ux_host_class_hid_keyboard_capslock_array[] =
31 {
32 0,0,0,0,
33 'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z',
34 '1','2','3','4','5','6','7','8','9','0',
35 0x0d,0x1b,0x08,0x07,0x20,'-','=','[',']',
36 '\\','#',';',0x27,'`',',','.','/',0xf0,
37 0xbb,0xbc,0xbd,0xbe,0xbf,0xc0,0xc1,0xc2,0xc3,0xc4,0xc5,0xc6,
38 0x00,0xf1,0x00,0xd2,0xc7,0xc9,0xd3,0xcf,0xd1,0xcd,0xcb,0xd0,0xc8,0xf2,
39 '/','*','-','+',
40 0x0d,'1','2','3','4','5','6','7','8','9','0','.','\\',0x00,0x00,'=',
41 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
42 };
43
44 static UCHAR ux_host_class_hid_keyboard_shift_array[] =
45 {
46 0,0,0,0,
47 'A','B','C','D','E','F','G','H','I','J','K','L','M','N',
48 'O','P','Q','R','S','T','U','V','W','X','Y','Z',
49 '!','@','#','$','%','^','&','*','(',')',
50 0x0d,0x1b,0x08,0x07,0x20,'_','+','{','}',
51 '|','~',':','"','~','<','>','?',0xf0,
52 0xbb,0xbc,0xbd,0xbe,0xbf,0xc0,0xc1,0xc2,0xc3,0xc4,0xc5,0xc6,
53 0x00,0xf1,0x00,0xd2,0xc7,0xc9,0xd3,0xcf,0xd1,0xcd,0xcb,0xd0,0xc8,0xf2,
54 '/','*','-','+',
55 0x0d,'1','2','3','4','5','6','7','8','9','0','.','\\',0x00,0x00,'=',
56 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
57 };
58
59 static UCHAR ux_host_class_hid_keyboard_shift_capslock_array[] =
60 {
61 0,0,0,0,
62 'a','b','c','d','e','f','g','h','i','j', 'k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z',
63 '!','@','#','$','%','^','&','*','(',')',
64 0x0d,0x1b,0x08,0x07,0x20,'_','+','{','}',
65 '|','~',':','"','~','<','>','?',0xf0,
66 0xbb,0xbc,0xbd,0xbe,0xbf,0xc0,0xc1,0xc2,0xc3,0xc4,0xc5,0xc6,
67 0x00,0xf1,0x00,0xd2,0xc7,0xc9,0xd3,0xcf,0xd1,0xcd,0xcb,0xd0,0xc8,0xf2,
68 '/','*','-','+',
69 0x0d,'1','2','3','4','5','6','7','8','9','0','.','\\',0x00,0x00,'=',
70 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
71 };
72
73 static UCHAR ux_host_class_hid_keyboard_numlock_on_array[] =
74 {
75 '/','*','-','+',
76 0x0d,'1','2','3','4','5','6','7','8','9','0','.','\\',0x00,0x00,'=',
77 };
78
79 static UCHAR ux_host_class_hid_keyboard_numlock_off_array[] =
80 {
81 '/','*','-','+',
82 0x0d,0xcf,0xd0,0xd1,0xcb,'5',0xcd,0xc7,0xc8,0xc9,0xd2,0xd3,'\\',0x00,0x00,'=',
83 };
84
85
86 #define DUMMY_USBX_MEMORY_SIZE (64*1024)
87 static UCHAR dummy_usbx_memory[DUMMY_USBX_MEMORY_SIZE];
88
89 static volatile ULONG test_host_phase = 0;
90 static volatile ULONG test_slave_phase = 0;
91
92 static UCHAR hid_report_descriptor[] = {
93
94 0x05, 0x01, // USAGE_PAGE (Generic Desktop)
95 0x09, 0x06, // USAGE (Keyboard)
96 0xa1, 0x01, // COLLECTION (Application)
97 0x05, 0x07, // USAGE_PAGE (Keyboard)
98 0x19, 0xe0, // USAGE_MINIMUM (Keyboard LeftControl)
99 0x29, 0xe7, // USAGE_MAXIMUM (Keyboard Right GUI)
100 0x15, 0x00, // LOGICAL_MINIMUM (0)
101 0x25, 0x01, // LOGICAL_MAXIMUM (1)
102 0x75, 0x01, // REPORT_SIZE (1)
103 0x95, 0x08, // REPORT_COUNT (8)
104 0x81, 0x02, // INPUT (Data,Var,Abs)
105 0x95, 0x01, // REPORT_COUNT (1)
106 0x75, 0x08, // REPORT_SIZE (8)
107 0x81, 0x03, // INPUT (Cnst,Var,Abs)
108 0x95, 0x05, // REPORT_COUNT (5)
109 0x75, 0x01, // REPORT_SIZE (1)
110 0x05, 0x08, // USAGE_PAGE (LEDs)
111 0x19, 0x01, // USAGE_MINIMUM (Num Lock)
112 0x29, 0x05, // USAGE_MAXIMUM (Kana)
113 0x91, 0x02, // OUTPUT (Data,Var,Abs)
114 0x95, 0x01, // REPORT_COUNT (1)
115 0x75, 0x03, // REPORT_SIZE (3)
116 0x91, 0x03, // OUTPUT (Cnst,Var,Abs)
117 0x95, 0x06, // REPORT_COUNT (6)
118 0x75, 0x08, // REPORT_SIZE (8)
119 0x15, 0x00, // LOGICAL_MINIMUM (0)
120 0x25, ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array) + 1, // LOGICAL_MAXIMUM ()
121 0x05, 0x07, // USAGE_PAGE (Keyboard)
122 0x19, 0x00, // USAGE_MINIMUM (Reserved (no event indicated))
123 0x29, ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array) + 1, // USAGE_MAXIMUM ()
124 0x81, 0x00, // INPUT (Data,Ary,Abs)
125 0xc0 // END_COLLECTION
126 };
127 #define HID_REPORT_LENGTH sizeof(hid_report_descriptor)/sizeof(hid_report_descriptor[0])
128
129
130 #define DEVICE_FRAMEWORK_LENGTH_FULL_SPEED 52
131 static UCHAR device_framework_full_speed[DEVICE_FRAMEWORK_LENGTH_FULL_SPEED] = {
132
133 /* Device descriptor */
134 0x12, 0x01, 0x10, 0x01, 0x00, 0x00, 0x00, 0x08,
135 0x81, 0x0A, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00,
136 0x00, 0x01,
137
138 /* Configuration descriptor */
139 0x09, 0x02, 0x22, 0x00, 0x01, 0x01, 0x00, 0xc0,
140 0x32,
141
142 /* Interface descriptor */
143 0x09, 0x04, 0x02, 0x00, 0x01, 0x03, 0x00, 0x00,
144 0x00,
145
146 /* HID descriptor */
147 0x09, 0x21, 0x10, 0x01, 0x21, 0x01, 0x22, LSB(HID_REPORT_LENGTH),
148 MSB(HID_REPORT_LENGTH),
149
150 /* Endpoint descriptor (Interrupt) */
151 0x07, 0x05, 0x82, 0x03, 0x08, 0x00, 0x08
152
153 };
154
155
156 #define DEVICE_FRAMEWORK_LENGTH_HIGH_SPEED 62
157 static UCHAR device_framework_high_speed[DEVICE_FRAMEWORK_LENGTH_HIGH_SPEED] = {
158
159 /* Device descriptor */
160 0x12, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00, 0x40,
161 0x0a, 0x07, 0x25, 0x40, 0x01, 0x00, 0x01, 0x02,
162 0x03, 0x01,
163
164 /* Device qualifier descriptor */
165 0x0a, 0x06, 0x00, 0x02, 0x00, 0x00, 0x00, 0x40,
166 0x01, 0x00,
167
168 /* Configuration descriptor */
169 0x09, 0x02, 0x22, 0x00, 0x01, 0x01, 0x00, 0xc0,
170 0x32,
171
172 /* Interface descriptor */
173 0x09, 0x04, 0x02, 0x00, 0x01, 0x03, 0x00, 0x00,
174 0x00,
175
176 /* HID descriptor */
177 0x09, 0x21, 0x10, 0x01, 0x21, 0x01, 0x22, LSB(HID_REPORT_LENGTH),
178 MSB(HID_REPORT_LENGTH),
179
180 /* Endpoint descriptor (Interrupt) */
181 0x07, 0x05, 0x82, 0x03, 0x08, 0x00, 0x08
182
183 };
184
185
186 /* String Device Framework :
187 Byte 0 and 1 : Word containing the language ID : 0x0904 for US
188 Byte 2 : Byte containing the index of the descriptor
189 Byte 3 : Byte containing the length of the descriptor string
190 */
191
192 #define STRING_FRAMEWORK_LENGTH 40
193 static UCHAR string_framework[] = {
194
195 /* Manufacturer string descriptor : Index 1 */
196 0x09, 0x04, 0x01, 0x0c,
197 0x45, 0x78, 0x70, 0x72,0x65, 0x73, 0x20, 0x4c,
198 0x6f, 0x67, 0x69, 0x63,
199
200 /* Product string descriptor : Index 2 */
201 0x09, 0x04, 0x02, 0x0c,
202 0x55, 0x53, 0x42, 0x20, 0x4b, 0x65, 0x79, 0x62,
203 0x6f, 0x61, 0x72, 0x64,
204
205 /* Serial Number string descriptor : Index 3 */
206 0x09, 0x04, 0x03, 0x04,
207 0x30, 0x30, 0x30, 0x31
208 };
209
210
211 /* Multiple languages are supported on the device, to add
212 a language besides english, the unicode language code must
213 be appended to the language_id_framework array and the length
214 adjusted accordingly. */
215 #define LANGUAGE_ID_FRAMEWORK_LENGTH 2
216 static UCHAR language_id_framework[] = {
217
218 /* English. */
219 0x09, 0x04
220 };
221
222
223 UINT _ux_hcd_sim_host_entry(UX_HCD *hcd, UINT function, VOID *parameter);
224
225
ux_system_host_change_function(ULONG a,UX_HOST_CLASS * b,VOID * c)226 static UINT ux_system_host_change_function(ULONG a, UX_HOST_CLASS *b, VOID *c)
227 {
228 return 0;
229 }
230
error_callback(UINT system_level,UINT system_context,UINT error_code)231 static VOID error_callback(UINT system_level, UINT system_context, UINT error_code)
232 {
233
234 /* @BUG_FIX_PENDING: ux_dcd_sim_slave_function.c doesn't support transfer aborts, which happen during device unregistration of a class. */
235 if (error_code != UX_FUNCTION_NOT_SUPPORTED &&
236 error_code != UX_BUFFER_OVERFLOW /* Key queue overflow! */)
237 {
238
239 /* Failed test. */
240 printf("Error on line %d, system_level: %d, system_context: %d, error code: 0x%x\n", __LINE__, system_level, system_context, error_code);
241 test_control_return(1);
242 }
243 }
244
245 /* Define what the initial system looks like. */
246
247 #ifdef CTEST
test_application_define(void * first_unused_memory)248 void test_application_define(void *first_unused_memory)
249 #else
250 void usbx_hid_keyboard_key_test_application_define(void *first_unused_memory)
251 #endif
252 {
253
254 UINT status;
255 CHAR * stack_pointer;
256 CHAR * memory_pointer;
257
258
259 /* Inform user. */
260 printf("Running HID Keyboard Key Test....................................... ");
261
262 /* Initialize the free memory pointer */
263 stack_pointer = (CHAR *) usbx_memory;
264 memory_pointer = stack_pointer + (UX_DEMO_STACK_SIZE * 2);
265
266 /* Initialize USBX. Memory */
267 status = ux_system_initialize(memory_pointer, UX_DEMO_MEMORY_SIZE, UX_NULL,0);
268
269 /* Check for error. */
270 if (status != UX_SUCCESS)
271 {
272
273 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
274 test_control_return(1);
275 }
276
277 /* Register the error callback. */
278 _ux_utility_error_callback_register(error_callback);
279
280 /* The code below is required for installing the host portion of USBX */
281 status = ux_host_stack_initialize(ux_system_host_change_function);
282 if (status != UX_SUCCESS)
283 {
284
285 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
286 test_control_return(1);
287 }
288
289 status = ux_host_stack_class_register(_ux_system_host_class_hid_name, ux_host_class_hid_entry);
290 if (status != UX_SUCCESS)
291 {
292
293 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
294 test_control_return(1);
295 }
296
297 /* Register the HID client(s). */
298 status = ux_host_class_hid_client_register(_ux_system_host_class_hid_client_keyboard_name, ux_host_class_hid_keyboard_entry);
299 if (status != UX_SUCCESS)
300 {
301
302 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
303 test_control_return(1);
304 }
305
306 /* The code below is required for installing the device portion of USBX. No call back for
307 device status change in this example. */
308 status = ux_device_stack_initialize(device_framework_high_speed, DEVICE_FRAMEWORK_LENGTH_HIGH_SPEED,
309 device_framework_full_speed, DEVICE_FRAMEWORK_LENGTH_FULL_SPEED,
310 string_framework, STRING_FRAMEWORK_LENGTH,
311 language_id_framework, LANGUAGE_ID_FRAMEWORK_LENGTH,UX_NULL);
312 if(status!=UX_SUCCESS)
313 {
314
315 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
316 test_control_return(1);
317 }
318
319 /* Initialize the hid class parameters. */
320 hid_parameter.ux_device_class_hid_parameter_report_address = hid_report_descriptor;
321 hid_parameter.ux_device_class_hid_parameter_report_length = HID_REPORT_LENGTH;
322 hid_parameter.ux_device_class_hid_parameter_callback = demo_thread_hid_callback;
323
324 /* Initialize the device hid class. The class is connected with interface 2 */
325 status = ux_device_stack_class_register(_ux_system_slave_class_hid_name, ux_device_class_hid_entry,
326 1,2, (VOID *)&hid_parameter);
327 if(status!=UX_SUCCESS)
328 {
329
330 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
331 test_control_return(1);
332 }
333
334 /* Initialize the simulated device controller. */
335 status = _ux_dcd_sim_slave_initialize();
336
337 /* Check for error. */
338 if (status != UX_SUCCESS)
339 {
340
341 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
342 test_control_return(1);
343 }
344
345 /* Register all the USB host controllers available in this system */
346 status = ux_host_stack_hcd_register(_ux_system_host_hcd_simulator_name, ux_hcd_sim_host_initialize,0,0);
347
348 /* Check for error. */
349 if (status != UX_SUCCESS)
350 {
351
352 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
353 test_control_return(1);
354 }
355
356 /* Create the main host simulation thread. */
357 status = tx_thread_create(&tx_demo_thread_host_simulation, "tx demo host simulation", tx_demo_thread_host_simulation_entry, 0,
358 stack_pointer, UX_DEMO_STACK_SIZE,
359 20, 20, 1, TX_AUTO_START);
360
361 /* Check for error. */
362 if (status != TX_SUCCESS)
363 {
364
365 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
366 test_control_return(1);
367 }
368
369 /* Create the main demo thread. */
370 status = tx_thread_create(&tx_demo_thread_slave_simulation, "tx demo slave simulation", tx_demo_thread_slave_simulation_entry, 0,
371 stack_pointer + UX_DEMO_STACK_SIZE, UX_DEMO_STACK_SIZE,
372 20, 20, 1, TX_AUTO_START);
373
374 /* Check for error. */
375 if (status != TX_SUCCESS)
376 {
377
378 printf("Running HID Keyboard Basic Functionality Test....................... ERROR #10\n");
379 test_control_return(1);
380 }
381
382 }
383
384
_wait_key(UX_HOST_CLASS_HID_KEYBOARD * keyboard,ULONG * keyboard_key,ULONG * keyboard_state)385 static UINT _wait_key(UX_HOST_CLASS_HID_KEYBOARD *keyboard, ULONG *keyboard_key, ULONG *keyboard_state)
386 {
387
388 UINT status;
389 UINT i;
390
391
392 for(i = 0; i < 200; i ++)
393 {
394 status = ux_host_class_hid_keyboard_key_get(keyboard, keyboard_key, keyboard_state);
395 if (status == UX_SUCCESS)
396 {
397 // printf("Key: %lx,%lx\n", *keyboard_key, *keyboard_state);
398
399 #if defined(UX_HOST_CLASS_HID_KEYBOARD_EVENTS_KEY_CHANGES_MODE_REPORT_LOCK_KEYS) || defined(UX_HOST_CLASS_HID_KEYBOARD_EVENTS_KEY_CHANGES_MODE_REPORT_MODIFIER_KEYS)
400 if (*keyboard_state & UX_HID_KEYBOARD_STATE_FUNCTION)
401 continue;
402 #endif
403
404 #if !defined(UX_HOST_CLASS_HID_KEYBOARD_EVENTS_KEY_CHANGES_MODE_REPORT_KEY_DOWN_ONLY)
405 if (*keyboard_state & UX_HID_KEYBOARD_STATE_KEY_UP)
406 continue;
407 #endif
408 return UX_SUCCESS;
409 }
410 _ux_utility_delay_ms(1);
411 }
412 return UX_ERROR;
413 }
414
415
tx_demo_phase_sync(ULONG in_host,ULONG nb_loop,ULONG tick_in_loop)416 static UINT tx_demo_phase_sync(ULONG in_host, ULONG nb_loop, ULONG tick_in_loop)
417 {
418
419 ULONG i;
420
421
422 for (i = 0; i < nb_loop; i ++)
423 {
424 if (in_host)
425 {
426 if (test_host_phase <= test_slave_phase)
427 return UX_SUCCESS;
428 }
429 else
430 {
431 if (test_slave_phase <= test_host_phase)
432 return UX_SUCCESS;
433 }
434 _ux_utility_thread_sleep(tick_in_loop);
435 }
436 return UX_ERROR;
437 }
438
tx_demo_thread_host_simulation_entry(ULONG arg)439 static void tx_demo_thread_host_simulation_entry(ULONG arg)
440 {
441
442 UINT status;
443 UX_HOST_CLASS_HID_KEYBOARD *keyboard;
444 ULONG keyboard_key;
445 ULONG keyboard_state;
446 ULONG expected_key;
447 ULONG num_keypad_keys;
448 ULONG i, n;
449 UCHAR *test_array[4] = {
450 ux_host_class_hid_keyboard_regular_array,
451 ux_host_class_hid_keyboard_shift_array,
452 ux_host_class_hid_keyboard_capslock_array,
453 ux_host_class_hid_keyboard_shift_capslock_array
454 };
455
456 /* Find the HID class */
457 status = demo_class_hid_get();
458 if (status != UX_SUCCESS)
459 {
460
461 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
462 test_control_return(1);
463 }
464
465 /* Get the HID client */
466 hid_client = hid -> ux_host_class_hid_client;
467
468 /* Check if the instance of the keyboard is live */
469 while (hid_client -> ux_host_class_hid_client_local_instance == UX_NULL)
470 tx_thread_sleep(10);
471
472 /* Get the keyboard instance */
473 keyboard = (UX_HOST_CLASS_HID_KEYBOARD *)hid_client -> ux_host_class_hid_client_local_instance;
474
475 /**************************************************************************/
476 /** 1. Test receiving maximum keys at once. **/
477 test_host_phase ++;
478 // printf("###### host step: %ld ######\n", test_host_phase);
479
480 for (i = 4; i < 10; i++)
481 {
482
483 status = _wait_key(keyboard, &keyboard_key, &keyboard_state);
484 if (status != UX_SUCCESS)
485 {
486 printf("ERROR #%d: code 0x%x\n", __LINE__, status);
487 test_control_return(1);
488 }
489
490 expected_key = ux_host_class_hid_keyboard_regular_array[i];
491
492 if (keyboard_key != expected_key)
493 {
494
495 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
496 test_control_return(1);
497 }
498 }
499
500 /**************************************************************************/
501 /** 2. Test keys. **/
502 test_host_phase ++;
503 // printf("###### host step: %ld ######\n", test_host_phase);
504
505 for (n = 0; n < 4; n ++)
506 {
507 for (i = KEY_START; i < ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array); i++)
508 {
509
510 /* These keys change the keyboard state and are not retrievable. */
511 if (i == UX_HID_LED_KEY_CAPS_LOCK ||
512 i == UX_HID_LED_KEY_NUM_LOCK ||
513 i == UX_HID_LED_KEY_SCROLL_LOCK)
514 continue;
515
516 status = _wait_key(keyboard, &keyboard_key, &keyboard_state);
517 if (status != UX_SUCCESS)
518 {
519 printf("ERROR #%d: code 0x%x\n", __LINE__, status);
520 test_control_return(1);
521 }
522
523 // printf("test key: %lx @ %lx\n", keyboard_key, keyboard_state);
524 expected_key = test_array[n][i];
525
526 if (keyboard_key != expected_key)
527 {
528
529 printf("Error on line %d, test %ld.%ld, state 0x%lx, key 0x%lx <> 0x%lx\n", __LINE__, n, i, keyboard_state, expected_key, keyboard_key);
530 test_control_return(1);
531 }
532 }
533 }
534
535 /**************************************************************************/
536 /** 3. Test number pad keys. **/
537 test_host_phase ++;
538 // printf("###### host step: %ld ######\n", test_host_phase);
539
540 /** Test numlock on keys. **/
541
542 num_keypad_keys = (UX_HID_KEYBOARD_KEYS_KEYPAD_UPPER_RANGE - UX_HID_KEYBOARD_KEYS_KEYPAD_LOWER_RANGE) + 1;
543
544 for (i = 0; i < ARRAY_COUNT(ux_host_class_hid_keyboard_numlock_on_array); i++)
545 {
546
547 status = _wait_key(keyboard, &keyboard_key, &keyboard_state);
548 if (status != UX_SUCCESS)
549 {
550 printf("ERROR #%d: code 0x%x\n", __LINE__, status);
551 test_control_return(1);
552 }
553
554 expected_key = ux_host_class_hid_keyboard_numlock_on_array[i];
555
556 if (keyboard_key != ux_host_class_hid_keyboard_numlock_on_array[i])
557 {
558
559 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
560 test_control_return(1);
561 }
562 }
563
564 /** Test numlock off keys. **/
565
566 for (i = 0; i < ARRAY_COUNT(ux_host_class_hid_keyboard_numlock_off_array); i++)
567 {
568
569 status = _wait_key(keyboard, &keyboard_key, &keyboard_state);
570 if (status != UX_SUCCESS)
571 {
572 printf("ERROR #%d: code 0x%x\n", __LINE__, status);
573 test_control_return(1);
574 }
575
576 // printf("test key: %lx @ %lx\n", keyboard_key, keyboard_state);
577
578 expected_key = ux_host_class_hid_keyboard_numlock_off_array[i];
579
580 if (keyboard_key != ux_host_class_hid_keyboard_numlock_off_array[i])
581 {
582
583 printf("Error on line %d, test %ld, state 0x%lx, key 0x%lx <> 0x%lx\n", __LINE__, i, keyboard_state, expected_key, keyboard_key);
584 test_control_return(1);
585 }
586 }
587
588 /**************************************************************************/
589 /** 4. Test states. **/
590 test_host_phase ++;
591 // printf("###### host step: %ld ######\n", test_host_phase);
592
593 /** Test keyboard on states. **/
594
595 status = _wait_key(keyboard, &keyboard_key, &keyboard_state);
596 if (status != UX_SUCCESS)
597 {
598 printf("ERROR #%d: code 0x%x\n", __LINE__, status);
599 test_control_return(1);
600 }
601
602 /* Ensure every bit is enabled (represented by 0xff07 (search for "Define HID Keyboard States." in ux_host_class_hid_keyboard.h)). */
603 if ((keyboard_state & 0xFFFF) != 0xff07)
604 {
605
606 printf("Error on line %d, test %ld.%ld, state 0x%lx\n", __LINE__, n, i, keyboard_state);
607 test_control_return(1);
608 }
609
610 /** Test keyboard off states. **/
611
612 status = _wait_key(keyboard, &keyboard_key, &keyboard_state);
613 if (status != UX_SUCCESS)
614 {
615 printf("ERROR #%d: code 0x%x\n", __LINE__, status);
616 test_control_return(1);
617 }
618
619 /* Ensure every bit is disabled. */
620 if ((keyboard_state & 0xFFFF) != 0x0000)
621 {
622
623 printf("Error on line %d, test %ld.%ld, state 0x%lx\n", __LINE__, n, i, keyboard_state);
624 test_control_return(1);
625 }
626
627 /**************************************************************************/
628 /** 5. Test raw key. **/
629
630 /* Disable decode. */
631 ux_host_class_hid_keyboard_ioctl(keyboard, UX_HID_KEYBOARD_IOCTL_DISABLE_KEYS_DECODE, UX_NULL);
632 test_host_phase ++;
633 // printf("###### host step: %ld ######\n", test_host_phase);
634
635 for (i = KEY_START; i < ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array); i++)
636 {
637 #if 0
638 /* These keys change the keyboard state and are not retrievable. */
639 if (i == UX_HID_LED_KEY_CAPS_LOCK ||
640 i == UX_HID_LED_KEY_NUM_LOCK ||
641 i == UX_HID_LED_KEY_SCROLL_LOCK)
642 continue;
643 #endif
644
645 status = _wait_key(keyboard, &keyboard_key, &keyboard_state);
646 if (status != UX_SUCCESS)
647 {
648 printf("ERROR #%d: code 0x%x\n", __LINE__, status);
649 test_control_return(1);
650 }
651
652 expected_key = i;
653
654 if (keyboard_key != expected_key)
655 {
656
657 printf("Error on line %d, test %ld, 0x%lx <> 0x%lx\n", __LINE__, i, expected_key, keyboard_key);
658 // test_control_return(1);
659 }
660 }
661
662 /**************************************************************************/
663 /** 6. Test invalid key. **/
664
665 /* Enable decode. */
666 ux_host_class_hid_keyboard_ioctl(keyboard, UX_HID_KEYBOARD_IOCTL_ENABLE_KEYS_DECODE, UX_NULL);
667 test_host_phase ++;
668 // printf("###### host step: %ld ######\n", test_host_phase);
669
670 /* Wait slave execute. */
671 if (tx_demo_phase_sync(UX_TRUE, 10, SLAVE_WAIT_TIME) != UX_SUCCESS)
672 {
673 printf("Error in line %d, thread phase error %ld <> %ld!\n", __LINE__, test_host_phase, test_slave_phase);
674 test_control_return(1);
675 }
676
677 /* Wait a invalid key (discarded). */
678 ux_utility_thread_sleep(HOST_WAIT_TIME * 2);
679
680 /**************************************************************************/
681 /** 7. Test key array overflow. **/
682
683 /* Flush keys. */
684 do {
685 status = ux_host_class_hid_keyboard_key_get(keyboard, &keyboard_key, &keyboard_state);
686 } while(status == UX_SUCCESS);
687
688 /* No read, test array full. */
689 ux_host_class_hid_keyboard_ioctl(keyboard, UX_HID_KEYBOARD_IOCTL_DISABLE_KEYS_DECODE, UX_NULL);
690 test_host_phase ++;
691 // printf("###### host step: %ld ######\n", test_host_phase);
692
693 /* Wait until test done. */
694 while(test_slave_phase != 0)
695 _ux_utility_delay_ms(10);
696
697 /* There are keys remain in key array. */
698 for (i = 0; i < UX_HOST_CLASS_HID_KEYBOARD_USAGE_ARRAY_LENGTH / 2 - 1; i ++)
699 {
700
701 status = ux_host_class_hid_keyboard_key_get(keyboard, &keyboard_key, &keyboard_state);
702 if(status != UX_SUCCESS)
703 {
704 printf("Error on line %d.%ld, error code 0x%x\n", __LINE__, i, status);
705 test_control_return(1);
706 }
707 if (keyboard_key != 5)
708 {
709 printf("Error on line %d, key 0x%lx,0x%lx @ %ld\n", __LINE__, keyboard_key, keyboard_state, i);
710 test_control_return(1);
711 }
712 }
713 status = ux_host_class_hid_keyboard_key_get(keyboard, &keyboard_key, &keyboard_state);
714 if(status == UX_SUCCESS)
715 {
716 printf("Error on line %d, error code 0x%x\n", __LINE__, status);
717 }
718
719 /* Now disconnect the device. */
720 _ux_device_stack_disconnect();
721
722 /* And deinitialize the class. */
723 status = ux_device_stack_class_unregister(_ux_system_slave_class_hid_name, ux_device_class_hid_entry);
724
725 /* Deinitialize the device side of usbx. */
726 _ux_device_stack_uninitialize();
727
728 /* And finally the usbx system resources. */
729 _ux_system_uninitialize();
730
731 /* Successful test. */
732 printf("SUCCESS!\n");
733 test_control_return(0);
734 }
735
demo_thread_hid_callback(UX_SLAVE_CLASS_HID * class,UX_SLAVE_CLASS_HID_EVENT * event)736 static UINT demo_thread_hid_callback(UX_SLAVE_CLASS_HID *class, UX_SLAVE_CLASS_HID_EVENT *event)
737 {
738 return(UX_SUCCESS);
739 }
740
tx_demo_thread_slave_simulation_entry(ULONG arg)741 static void tx_demo_thread_slave_simulation_entry(ULONG arg)
742 {
743
744 UINT status;
745 UX_SLAVE_DEVICE *device;
746 UX_SLAVE_INTERFACE *interface;
747 UX_SLAVE_CLASS_HID *hid;
748 UX_SLAVE_CLASS_HID_EVENT hid_event;
749 UINT i, n;
750 UCHAR state_modifier[2] = {0, (0x01 << 1)};
751
752 /* Get the pointer to the device. */
753 device = &_ux_system_slave -> ux_system_slave_device;
754
755 /* reset the HID event structure. */
756 ux_utility_memory_set(&hid_event, 0, sizeof(UX_SLAVE_CLASS_HID_EVENT));
757
758 /* Is the device configured ? */
759 while (device->ux_slave_device_state != UX_DEVICE_CONFIGURED)
760
761 /* Then wait. */
762 tx_thread_sleep(10);
763
764 /* Get the interface. We use the first interface, this is a simple device. */
765 interface = device->ux_slave_device_first_interface;
766
767 /* Form that interface, derive the HID owner. */
768 hid = interface->ux_slave_interface_class_instance;
769
770 /**************************************************************************/
771 /** 1. Test receiving maximum keys at once. **/
772 test_slave_phase ++;
773 // printf("****** slave step: %ld ******\n", test_slave_phase);
774
775 hid_event.ux_device_class_hid_event_length = 8;
776
777 /* Modification byte. */
778 hid_event.ux_device_class_hid_event_buffer[0] = 0;
779
780 /* Reserved byte. */
781 hid_event.ux_device_class_hid_event_buffer[1] = 0;
782
783 /* Set keys. */
784 for (i = 0; i < 6; i++)
785 hid_event.ux_device_class_hid_event_buffer[2 + i] = 4 + i;
786
787 ux_device_class_hid_event_set(hid, &hid_event);
788 #if 0
789 /* Release keys. */
790 for (i = 0; i < 6; i++)
791 hid_event.ux_device_class_hid_event_buffer[2 + i] = 0;
792
793 ux_device_class_hid_event_set(hid, &hid_event);
794 #endif
795 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
796
797 /* Reset for next test. */
798 ux_utility_memory_set(&hid_event, 0, sizeof(UX_SLAVE_CLASS_HID_EVENT));
799
800 /**************************************************************************/
801 /** 2. Test keys. **/
802 test_slave_phase ++;
803 // printf("****** slave step: %ld ******\n", test_slave_phase);
804
805 /** Test regular keys with/without SHIFT. Only go up to maximum value specified by report descriptor. **/
806
807 for (n = 0; n < 2; n ++)
808 {
809
810 for (i = KEY_START; i < ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array); i++)
811 {
812
813 /* These keys change the keyboard state and are not retrievable. */
814 if (i == UX_HID_LED_KEY_CAPS_LOCK ||
815 i == UX_HID_LED_KEY_NUM_LOCK ||
816 i == UX_HID_LED_KEY_SCROLL_LOCK)
817 continue;
818
819 hid_event.ux_device_class_hid_event_length = 8;
820
821 /* Modification byte. */
822 hid_event.ux_device_class_hid_event_buffer[0] = state_modifier[n];
823
824 /* Reserved byte. */
825 hid_event.ux_device_class_hid_event_buffer[1] = 0;
826
827 /* Key byte. */
828 hid_event.ux_device_class_hid_event_buffer[2] = i;
829
830 status = ux_device_class_hid_event_set(hid, &hid_event);
831 if (status != UX_SUCCESS)
832 {
833
834 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
835 test_control_return(1);
836 }
837
838 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
839 }
840
841 }
842 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
843
844 /** Test CAPS LOCK with/without SHIFT keys. Only go up to maximum value specified by report descriptor. **/
845
846 /* Turn CAPS LOCK on. */
847 hid_event.ux_device_class_hid_event_length = 8;
848 hid_event.ux_device_class_hid_event_buffer[0] = 0;
849 hid_event.ux_device_class_hid_event_buffer[1] = 0;
850 hid_event.ux_device_class_hid_event_buffer[2] = UX_HID_LED_KEY_CAPS_LOCK;
851 status = ux_device_class_hid_event_set(hid, &hid_event);
852 if (status != UX_SUCCESS)
853 {
854
855 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
856 test_control_return(1);
857 }
858
859 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
860
861 for (n = 0; n < 2; n ++)
862 {
863
864 for (i = KEY_START; i < ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array); i++)
865 {
866
867 /* These keys change the keyboard state and are not retrievable. */
868 if (i == UX_HID_LED_KEY_CAPS_LOCK ||
869 i == UX_HID_LED_KEY_NUM_LOCK ||
870 i == UX_HID_LED_KEY_SCROLL_LOCK)
871 continue;
872
873 hid_event.ux_device_class_hid_event_length = 8;
874
875 /* Modification byte. */
876 hid_event.ux_device_class_hid_event_buffer[0] = state_modifier[n];
877
878 /* Reserved byte. */
879 hid_event.ux_device_class_hid_event_buffer[1] = 0;
880
881 /* Key byte. */
882 hid_event.ux_device_class_hid_event_buffer[2] = i;
883
884 status = ux_device_class_hid_event_set(hid, &hid_event);
885 if (status != UX_SUCCESS)
886 {
887
888 /* ERROR */
889 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
890 test_control_return(1);
891 }
892
893 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
894 }
895 }
896 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
897
898 /* Turn CAPS LOCK off. */
899 hid_event.ux_device_class_hid_event_length = 8;
900 hid_event.ux_device_class_hid_event_buffer[0] = 0;
901 hid_event.ux_device_class_hid_event_buffer[1] = 0;
902 hid_event.ux_device_class_hid_event_buffer[2] = UX_HID_LED_KEY_CAPS_LOCK;
903 status = ux_device_class_hid_event_set(hid, &hid_event);
904 if (status != UX_SUCCESS)
905 {
906
907 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
908 test_control_return(1);
909 }
910
911 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
912
913 /**************************************************************************/
914 /** 3. Test num pad keys. **/
915 test_slave_phase ++;
916 // printf("****** slave step: %ld ******\n", test_slave_phase);
917
918 /** Test NUM LOCK on keys. NUM LOCK is on by default. **/
919
920 for (i = UX_HID_KEYBOARD_KEYS_KEYPAD_LOWER_RANGE; i <= UX_HID_KEYBOARD_KEYS_KEYPAD_UPPER_RANGE; i++)
921 {
922
923 hid_event.ux_device_class_hid_event_length = 8;
924
925 /* Modification byte. */
926 hid_event.ux_device_class_hid_event_buffer[0] = 0;
927
928 /* Reserved byte. */
929 hid_event.ux_device_class_hid_event_buffer[1] = 0;
930
931 /* Key byte. */
932 hid_event.ux_device_class_hid_event_buffer[2] = i;
933
934 status = ux_device_class_hid_event_set(hid, &hid_event);
935 if (status != UX_SUCCESS)
936 {
937
938 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
939 test_control_return(1);
940 }
941
942 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
943 }
944 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
945
946 /** Test NUM LOCK off keys. **/
947
948 /* Turn NUM LOCK off. */
949 hid_event.ux_device_class_hid_event_length = 8;
950 hid_event.ux_device_class_hid_event_buffer[0] = 0;
951 hid_event.ux_device_class_hid_event_buffer[1] = 0;
952 hid_event.ux_device_class_hid_event_buffer[2] = UX_HID_LED_KEY_NUM_LOCK;
953 ux_device_class_hid_event_set(hid, &hid_event);
954
955 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
956
957 for (i = UX_HID_KEYBOARD_KEYS_KEYPAD_LOWER_RANGE; i <= UX_HID_KEYBOARD_KEYS_KEYPAD_UPPER_RANGE; i++)
958 {
959
960 hid_event.ux_device_class_hid_event_length = 8;
961
962 /* Modification byte. */
963 hid_event.ux_device_class_hid_event_buffer[0] = 0;
964
965 /* Reserved byte. */
966 hid_event.ux_device_class_hid_event_buffer[1] = 0;
967
968 /* Key byte. */
969 hid_event.ux_device_class_hid_event_buffer[2] = i;
970
971 status = ux_device_class_hid_event_set(hid, &hid_event);
972 if (status != UX_SUCCESS)
973 {
974
975 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
976 test_control_return(1);
977 }
978
979 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
980 }
981 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
982
983 /* Turn NUM LOCK on. */
984 hid_event.ux_device_class_hid_event_length = 8;
985 hid_event.ux_device_class_hid_event_buffer[0] = 0;
986 hid_event.ux_device_class_hid_event_buffer[1] = 0;
987 hid_event.ux_device_class_hid_event_buffer[2] = UX_HID_LED_KEY_NUM_LOCK;
988 status = ux_device_class_hid_event_set(hid, &hid_event);
989 if (status != UX_SUCCESS)
990 {
991
992 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
993 test_control_return(1);
994 }
995
996 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
997
998 /**************************************************************************/
999 /** 4. Test states. **/
1000 test_slave_phase ++;
1001 // printf("****** slave step: %ld ******\n", test_slave_phase);
1002
1003 /** Test key states. **/
1004
1005 /* Enable every bit in key state. */
1006 hid_event.ux_device_class_hid_event_length = 8;
1007 hid_event.ux_device_class_hid_event_buffer[0] = 0xff;
1008 hid_event.ux_device_class_hid_event_buffer[1] = 0;
1009 hid_event.ux_device_class_hid_event_buffer[2] = UX_HID_LED_KEY_CAPS_LOCK;
1010 hid_event.ux_device_class_hid_event_buffer[3] = UX_HID_LED_KEY_SCROLL_LOCK;
1011 hid_event.ux_device_class_hid_event_buffer[4] = UX_HID_LED_KEY_NUM_LOCK;
1012
1013 status = ux_device_class_hid_event_set(hid, &hid_event);
1014 if (status != UX_SUCCESS)
1015 {
1016
1017 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1018 test_control_return(1);
1019 }
1020
1021 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1022
1023 /* Add a key so the host can receive it, allowing checking of key state. */
1024 hid_event.ux_device_class_hid_event_length = 8;
1025 hid_event.ux_device_class_hid_event_buffer[0] = 0xff;
1026 hid_event.ux_device_class_hid_event_buffer[1] = 0;
1027 hid_event.ux_device_class_hid_event_buffer[2] = 0;
1028 hid_event.ux_device_class_hid_event_buffer[3] = 0;
1029 hid_event.ux_device_class_hid_event_buffer[4] = 0x04;
1030
1031 status = ux_device_class_hid_event_set(hid, &hid_event);
1032 if (status != UX_SUCCESS)
1033 {
1034
1035 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1036 test_control_return(1);
1037 }
1038
1039 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1040
1041 /** Test key states. **/
1042
1043 /* Disable every bit in key state. */
1044 hid_event.ux_device_class_hid_event_length = 8;
1045 hid_event.ux_device_class_hid_event_buffer[0] = 0x00;
1046 hid_event.ux_device_class_hid_event_buffer[1] = 0;
1047 hid_event.ux_device_class_hid_event_buffer[2] = UX_HID_LED_KEY_CAPS_LOCK;
1048 hid_event.ux_device_class_hid_event_buffer[3] = UX_HID_LED_KEY_SCROLL_LOCK;
1049 hid_event.ux_device_class_hid_event_buffer[4] = UX_HID_LED_KEY_NUM_LOCK;
1050
1051 /* Add a different key so the host can receive it, allowing checking of key state. */
1052 hid_event.ux_device_class_hid_event_buffer[5] = 0x05;
1053
1054 status = ux_device_class_hid_event_set(hid, &hid_event);
1055 if (status != UX_SUCCESS)
1056 {
1057
1058 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1059 test_control_return(1);
1060 }
1061
1062 hid_event.ux_device_class_hid_event_buffer[2] = 0;
1063 hid_event.ux_device_class_hid_event_buffer[3] = 0;
1064 hid_event.ux_device_class_hid_event_buffer[4] = 0;
1065 hid_event.ux_device_class_hid_event_buffer[5] = 0;
1066
1067 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1068
1069 /**************************************************************************/
1070 /** 5. Test raw key. **/
1071 test_slave_phase ++;
1072 // printf("****** slave step: %ld ******\n", test_slave_phase);
1073
1074 /* Wait decode mode change. */
1075 if (tx_demo_phase_sync(UX_FALSE, 20, SLAVE_WAIT_TIME) != UX_SUCCESS)
1076 {
1077 printf("Error in line %d, thread phase error %ld <> %ld!\n", __LINE__, test_host_phase, test_slave_phase);
1078 test_control_return(1);
1079 }
1080
1081 /** Test raw key. **/
1082
1083 for (i = KEY_START; i < ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array); i++)
1084 {
1085
1086 hid_event.ux_device_class_hid_event_length = 8;
1087
1088 /* Modification byte. */
1089 hid_event.ux_device_class_hid_event_buffer[0] = 0;
1090
1091 /* Reserved byte. */
1092 hid_event.ux_device_class_hid_event_buffer[1] = 0;
1093
1094 /* Key byte. */
1095 hid_event.ux_device_class_hid_event_buffer[2] = i;
1096
1097 status = ux_device_class_hid_event_set(hid, &hid_event);
1098 if (status != UX_SUCCESS)
1099 {
1100
1101 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1102 test_control_return(1);
1103 }
1104
1105 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1106 }
1107 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1108
1109 /**************************************************************************/
1110 /** 6. Test invalid key. **/
1111 test_slave_phase ++;
1112 // printf("****** slave step: %ld ******\n", test_slave_phase);
1113
1114 /* Wait decode mode change. */
1115 if (tx_demo_phase_sync(UX_FALSE, 10, SLAVE_WAIT_TIME) != UX_SUCCESS)
1116 {
1117 printf("Error in line %d, thread phase error %ld <> %ld!\n", __LINE__, test_host_phase, test_slave_phase);
1118 test_control_return(1);
1119 }
1120
1121 /* Key byte. */
1122 hid_event.ux_device_class_hid_event_buffer[2] = ARRAY_COUNT(ux_host_class_hid_keyboard_regular_array);
1123
1124 status = ux_device_class_hid_event_set(hid, &hid_event);
1125 if (status != UX_SUCCESS)
1126 {
1127
1128 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1129 test_control_return(1);
1130 }
1131 /* Key byte release. */
1132 hid_event.ux_device_class_hid_event_buffer[2] = 0;
1133
1134 status = ux_device_class_hid_event_set(hid, &hid_event);
1135 if (status != UX_SUCCESS)
1136 {
1137
1138 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1139 test_control_return(1);
1140 }
1141 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1142
1143 /**************************************************************************/
1144 /** 7. Test key array overflow. **/
1145 test_slave_phase ++;
1146 // printf("****** slave step: %ld ******\n", test_slave_phase);
1147
1148 /* Wait decode mode change. */
1149 if (tx_demo_phase_sync(UX_FALSE, 10, SLAVE_WAIT_TIME) != UX_SUCCESS)
1150 {
1151 printf("Error in line %d, thread phase error %ld <> %ld!\n", __LINE__, test_host_phase, test_slave_phase);
1152 test_control_return(1);
1153 }
1154
1155 /** Test key array full. **/
1156
1157 for (i = 0; i < UX_HOST_CLASS_HID_KEYBOARD_USAGE_ARRAY_LENGTH + 1; i++)
1158 {
1159
1160 /* Press key. */
1161 hid_event.ux_device_class_hid_event_length = 8;
1162 hid_event.ux_device_class_hid_event_buffer[0] = 0;
1163 hid_event.ux_device_class_hid_event_buffer[1] = 0;
1164 hid_event.ux_device_class_hid_event_buffer[2] = 5;
1165 status = ux_device_class_hid_event_set(hid, &hid_event);
1166 if (status != UX_SUCCESS)
1167 {
1168
1169 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1170 test_control_return(1);
1171 }
1172
1173 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1174
1175 /* Release previous key. */
1176 hid_event.ux_device_class_hid_event_length = 8;
1177 hid_event.ux_device_class_hid_event_buffer[0] = 0;
1178 hid_event.ux_device_class_hid_event_buffer[1] = 0;
1179 hid_event.ux_device_class_hid_event_buffer[2] = 0;
1180 status = ux_device_class_hid_event_set(hid, &hid_event);
1181 if (status != UX_SUCCESS)
1182 {
1183
1184 printf("Error on line %d, error code: 0x%x\n", __LINE__, status);
1185 test_control_return(1);
1186 }
1187
1188 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1189 }
1190 ux_utility_thread_sleep(SLAVE_WAIT_TIME);
1191
1192 /* All done. */
1193 test_slave_phase = 0;
1194 }