1// SPDX-License-Identifier: GPL-2.0+ 2/* 3 * (C) Copyright 2001 4 * Denis Peter, MPL AG Switzerland 5 * 6 * Part of this source has been derived from the Linux USB 7 * project. 8 */ 9#include <common.h> 10#include <console.h> 11#include <dm.h> 12#include <env.h> 13#include <errno.h> 14#include <log.h> 15#include <malloc.h> 16#include <memalign.h> 17#include <stdio_dev.h> 18#include <watchdog.h> 19#include <asm/byteorder.h> 20#ifdef CONFIG_SANDBOX 21#include <asm/state.h> 22#endif 23 24#include <usb.h> 25 26/* 27 * USB vendor and product IDs used for quirks. 28 */ 29#define USB_VENDOR_ID_APPLE 0x05ac 30#define USB_DEVICE_ID_APPLE_MAGIC_KEYBOARD_2021 0x029c 31#define USB_DEVICE_ID_APPLE_MAGIC_KEYBOARD_FINGERPRINT_2021 0x029a 32#define USB_DEVICE_ID_APPLE_MAGIC_KEYBOARD_NUMPAD_2021 0x029f 33 34#define USB_VENDOR_ID_KEYCHRON 0x3434 35 36#define USB_HID_QUIRK_POLL_NO_REPORT_IDLE BIT(0) 37 38/* 39 * If overwrite_console returns 1, the stdin, stderr and stdout 40 * are switched to the serial port, else the settings in the 41 * environment are used 42 */ 43#ifdef CONFIG_SYS_CONSOLE_OVERWRITE_ROUTINE 44extern int overwrite_console(void); 45#else 46int overwrite_console(void) 47{ 48 return 0; 49} 50#endif 51 52/* Keyboard sampling rate */ 53#define REPEAT_RATE 40 /* 40msec -> 25cps */ 54#define REPEAT_DELAY 10 /* 10 x REPEAT_RATE = 400msec */ 55 56#define NUM_LOCK 0x53 57#define CAPS_LOCK 0x39 58#define SCROLL_LOCK 0x47 59 60/* Modifier bits */ 61#define LEFT_CNTR (1 << 0) 62#define LEFT_SHIFT (1 << 1) 63#define LEFT_ALT (1 << 2) 64#define LEFT_GUI (1 << 3) 65#define RIGHT_CNTR (1 << 4) 66#define RIGHT_SHIFT (1 << 5) 67#define RIGHT_ALT (1 << 6) 68#define RIGHT_GUI (1 << 7) 69 70/* Size of the keyboard buffer */ 71#define USB_KBD_BUFFER_LEN 0x20 72 73/* Device name */ 74#define DEVNAME "usbkbd" 75 76/* Keyboard maps */ 77static const unsigned char usb_kbd_numkey[] = { 78 '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', 79 '\r', 0x1b, '\b', '\t', ' ', '-', '=', '[', ']', 80 '\\', '#', ';', '\'', '`', ',', '.', '/' 81}; 82static const unsigned char usb_kbd_numkey_shifted[] = { 83 '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', 84 '\r', 0x1b, '\b', '\t', ' ', '_', '+', '{', '}', 85 '|', '~', ':', '"', '~', '<', '>', '?' 86}; 87 88static const unsigned char usb_kbd_num_keypad[] = { 89 '/', '*', '-', '+', '\r', 90 '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', 91 '.', 0, 0, 0, '=' 92}; 93 94static const u8 usb_special_keys[] = { 95#ifdef CONFIG_USB_KEYBOARD_FN_KEYS 96 '2', 'H', '5', '3', 'F', '6', 'C', 'D', 'B', 'A' 97#else 98 'C', 'D', 'B', 'A' 99#endif 100}; 101 102/* 103 * NOTE: It's important for the NUM, CAPS, SCROLL-lock bits to be in this 104 * order. See usb_kbd_setled() function! 105 */ 106#define USB_KBD_NUMLOCK (1 << 0) 107#define USB_KBD_CAPSLOCK (1 << 1) 108#define USB_KBD_SCROLLLOCK (1 << 2) 109#define USB_KBD_CTRL (1 << 3) 110 111#define USB_KBD_LEDMASK \ 112 (USB_KBD_NUMLOCK | USB_KBD_CAPSLOCK | USB_KBD_SCROLLLOCK) 113 114struct usb_kbd_pdata { 115 unsigned long intpipe; 116 int intpktsize; 117 int intinterval; 118 unsigned long last_report; 119 struct int_queue *intq; 120 121 uint32_t ifnum; 122 123 uint32_t repeat_delay; 124 125 uint32_t usb_in_pointer; 126 uint32_t usb_out_pointer; 127 uint8_t usb_kbd_buffer[USB_KBD_BUFFER_LEN]; 128 129 uint8_t *new; 130 uint8_t old[USB_KBD_BOOT_REPORT_SIZE]; 131 132 uint8_t flags; 133}; 134 135extern int __maybe_unused net_busy_flag; 136 137/* The period of time between two calls of usb_kbd_testc(). */ 138static unsigned long kbd_testc_tms; 139 140/* Puts character in the queue and sets up the in and out pointer. */ 141static void usb_kbd_put_queue(struct usb_kbd_pdata *data, u8 c) 142{ 143 if (data->usb_in_pointer == USB_KBD_BUFFER_LEN - 1) { 144 /* Check for buffer full. */ 145 if (data->usb_out_pointer == 0) 146 return; 147 148 data->usb_in_pointer = 0; 149 } else { 150 /* Check for buffer full. */ 151 if (data->usb_in_pointer == data->usb_out_pointer - 1) 152 return; 153 154 data->usb_in_pointer++; 155 } 156 157 data->usb_kbd_buffer[data->usb_in_pointer] = c; 158} 159 160/* 161 * Set the LEDs. Since this is used in the irq routine, the control job is 162 * issued with a timeout of 0. This means, that the job is queued without 163 * waiting for job completion. 164 */ 165static void usb_kbd_setled(struct usb_device *dev) 166{ 167 struct usb_kbd_pdata *data = dev->privptr; 168 struct usb_interface *iface = &dev->config.if_desc[data->ifnum]; 169 ALLOC_ALIGN_BUFFER(uint32_t, leds, 1, USB_DMA_MINALIGN); 170 171 *leds = data->flags & USB_KBD_LEDMASK; 172 usb_control_msg(dev, usb_sndctrlpipe(dev, 0), 173 USB_REQ_SET_REPORT, USB_TYPE_CLASS | USB_RECIP_INTERFACE, 174 0x200, iface->desc.bInterfaceNumber, leds, 1, 0); 175} 176 177#define CAPITAL_MASK 0x20 178/* Translate the scancode in ASCII */ 179static int usb_kbd_translate(struct usb_kbd_pdata *data, unsigned char scancode, 180 unsigned char modifier, int pressed) 181{ 182 uint8_t keycode = 0; 183 184 /* Key released */ 185 if (pressed == 0) { 186 data->repeat_delay = 0; 187 return 0; 188 } 189 190 if (pressed == 2) { 191 data->repeat_delay++; 192 if (data->repeat_delay < REPEAT_DELAY) 193 return 0; 194 195 data->repeat_delay = REPEAT_DELAY; 196 } 197 198 /* Alphanumeric values */ 199 if ((scancode > 3) && (scancode <= 0x1d)) { 200 keycode = scancode - 4 + 'a'; 201 202 if (data->flags & USB_KBD_CAPSLOCK) 203 keycode &= ~CAPITAL_MASK; 204 205 if (modifier & (LEFT_SHIFT | RIGHT_SHIFT)) { 206 /* Handle CAPSLock + Shift pressed simultaneously */ 207 if (keycode & CAPITAL_MASK) 208 keycode &= ~CAPITAL_MASK; 209 else 210 keycode |= CAPITAL_MASK; 211 } 212 } 213 214 if ((scancode > 0x1d) && (scancode < 0x39)) { 215 /* Shift pressed */ 216 if (modifier & (LEFT_SHIFT | RIGHT_SHIFT)) 217 keycode = usb_kbd_numkey_shifted[scancode - 0x1e]; 218 else 219 keycode = usb_kbd_numkey[scancode - 0x1e]; 220 } 221 222 /* Numeric keypad */ 223 if ((scancode >= 0x54) && (scancode <= 0x67)) 224 keycode = usb_kbd_num_keypad[scancode - 0x54]; 225 226 if (data->flags & USB_KBD_CTRL) 227 keycode = scancode - 0x3; 228 229 if (pressed == 1) { 230 if (scancode == NUM_LOCK) { 231 data->flags ^= USB_KBD_NUMLOCK; 232 return 1; 233 } 234 235 if (scancode == CAPS_LOCK) { 236 data->flags ^= USB_KBD_CAPSLOCK; 237 return 1; 238 } 239 if (scancode == SCROLL_LOCK) { 240 data->flags ^= USB_KBD_SCROLLLOCK; 241 return 1; 242 } 243 } 244 245 /* Report keycode if any */ 246 if (keycode) { 247 debug("%c", keycode); 248 usb_kbd_put_queue(data, keycode); 249 return 0; 250 } 251 252#ifdef CONFIG_USB_KEYBOARD_FN_KEYS 253 if (scancode < 0x3a || scancode > 0x52 || 254 scancode == 0x46 || scancode == 0x47) 255 return 1; 256 257 usb_kbd_put_queue(data, 0x1b); 258 if (scancode < 0x3e) { 259 /* F1 - F4 */ 260 usb_kbd_put_queue(data, 0x4f); 261 usb_kbd_put_queue(data, scancode - 0x3a + 'P'); 262 return 0; 263 } 264 usb_kbd_put_queue(data, '['); 265 if (scancode < 0x42) { 266 /* F5 - F8 */ 267 usb_kbd_put_queue(data, '1'); 268 if (scancode == 0x3e) 269 --scancode; 270 keycode = scancode - 0x3f + '7'; 271 } else if (scancode < 0x49) { 272 /* F9 - F12 */ 273 usb_kbd_put_queue(data, '2'); 274 if (scancode > 0x43) 275 ++scancode; 276 keycode = scancode - 0x42 + '0'; 277 } else { 278 /* 279 * INSERT, HOME, PAGE UP, DELETE, END, PAGE DOWN, 280 * RIGHT, LEFT, DOWN, UP 281 */ 282 keycode = usb_special_keys[scancode - 0x49]; 283 } 284 usb_kbd_put_queue(data, keycode); 285 if (scancode < 0x4f && scancode != 0x4a && scancode != 0x4d) 286 usb_kbd_put_queue(data, '~'); 287 return 0; 288#else 289 /* Left, Right, Up, Down */ 290 if (scancode > 0x4e && scancode < 0x53) { 291 usb_kbd_put_queue(data, 0x1b); 292 usb_kbd_put_queue(data, '['); 293 usb_kbd_put_queue(data, usb_special_keys[scancode - 0x4f]); 294 return 0; 295 } 296 return 1; 297#endif /* CONFIG_USB_KEYBOARD_FN_KEYS */ 298} 299 300static uint32_t usb_kbd_service_key(struct usb_device *dev, int i, int up) 301{ 302 uint32_t res = 0; 303 struct usb_kbd_pdata *data = dev->privptr; 304 uint8_t *new; 305 uint8_t *old; 306 307 if (up) { 308 new = data->old; 309 old = data->new; 310 } else { 311 new = data->new; 312 old = data->old; 313 } 314 315 if ((old[i] > 3) && 316 (memscan(new + 2, old[i], USB_KBD_BOOT_REPORT_SIZE - 2) == 317 new + USB_KBD_BOOT_REPORT_SIZE)) { 318 res |= usb_kbd_translate(data, old[i], data->new[0], up); 319 } 320 321 return res; 322} 323 324/* Interrupt service routine */ 325static int usb_kbd_irq_worker(struct usb_device *dev) 326{ 327 struct usb_kbd_pdata *data = dev->privptr; 328 int i, res = 0; 329 330 /* No combo key pressed */ 331 if (data->new[0] == 0x00) 332 data->flags &= ~USB_KBD_CTRL; 333 /* Left or Right Ctrl pressed */ 334 else if ((data->new[0] == LEFT_CNTR) || (data->new[0] == RIGHT_CNTR)) 335 data->flags |= USB_KBD_CTRL; 336 337 for (i = 2; i < USB_KBD_BOOT_REPORT_SIZE; i++) { 338 res |= usb_kbd_service_key(dev, i, 0); 339 res |= usb_kbd_service_key(dev, i, 1); 340 } 341 342 /* Key is still pressed */ 343 if ((data->new[2] > 3) && (data->old[2] == data->new[2])) 344 res |= usb_kbd_translate(data, data->new[2], data->new[0], 2); 345 346 if (res == 1) 347 usb_kbd_setled(dev); 348 349 memcpy(data->old, data->new, USB_KBD_BOOT_REPORT_SIZE); 350 351 return 1; 352} 353 354/* Keyboard interrupt handler */ 355static int usb_kbd_irq(struct usb_device *dev) 356{ 357 if ((dev->irq_status != 0) || 358 (dev->irq_act_len != USB_KBD_BOOT_REPORT_SIZE)) { 359 debug("USB KBD: Error %lX, len %d\n", 360 dev->irq_status, dev->irq_act_len); 361 return 1; 362 } 363 364 return usb_kbd_irq_worker(dev); 365} 366 367/* Interrupt polling */ 368static inline void usb_kbd_poll_for_event(struct usb_device *dev) 369{ 370#if defined(CONFIG_SYS_USB_EVENT_POLL) 371 struct usb_kbd_pdata *data = dev->privptr; 372 373 /* Submit an interrupt transfer request */ 374 if (usb_int_msg(dev, data->intpipe, &data->new[0], 375 data->intpktsize, data->intinterval, true) >= 0) 376 usb_kbd_irq_worker(dev); 377#elif defined(CONFIG_SYS_USB_EVENT_POLL_VIA_CONTROL_EP) || \ 378 defined(CONFIG_SYS_USB_EVENT_POLL_VIA_INT_QUEUE) 379#if defined(CONFIG_SYS_USB_EVENT_POLL_VIA_CONTROL_EP) 380 struct usb_interface *iface; 381 struct usb_kbd_pdata *data = dev->privptr; 382 iface = &dev->config.if_desc[data->ifnum]; 383 usb_get_report(dev, iface->desc.bInterfaceNumber, 384 1, 0, data->new, USB_KBD_BOOT_REPORT_SIZE); 385 if (memcmp(data->old, data->new, USB_KBD_BOOT_REPORT_SIZE)) { 386 usb_kbd_irq_worker(dev); 387#else 388 struct usb_kbd_pdata *data = dev->privptr; 389 if (poll_int_queue(dev, data->intq)) { 390 usb_kbd_irq_worker(dev); 391 /* We've consumed all queued int packets, create new */ 392 destroy_int_queue(dev, data->intq); 393 data->intq = create_int_queue(dev, data->intpipe, 1, 394 USB_KBD_BOOT_REPORT_SIZE, data->new, 395 data->intinterval); 396#endif 397 data->last_report = get_timer(0); 398 /* Repeat last usb hid report every REPEAT_RATE ms for keyrepeat */ 399 } else if (data->last_report != -1 && 400 get_timer(data->last_report) > REPEAT_RATE) { 401 usb_kbd_irq_worker(dev); 402 data->last_report = get_timer(0); 403 } 404#endif 405} 406 407/* test if a character is in the queue */ 408static int usb_kbd_testc(struct stdio_dev *sdev) 409{ 410 struct stdio_dev *dev; 411 struct usb_device *usb_kbd_dev; 412 struct usb_kbd_pdata *data; 413 414 /* 415 * Polling the keyboard for an event can take dozens of milliseconds. 416 * Add a delay between polls to avoid blocking activity which polls 417 * rapidly, like the UEFI console timer. 418 */ 419 unsigned long poll_delay = CONFIG_SYS_HZ / 50; 420 421#ifdef CONFIG_CMD_NET 422 /* 423 * If net_busy_flag is 1, NET transfer is running, 424 * then we check key-pressed every second (first check may be 425 * less than 1 second) to improve TFTP booting performance. 426 */ 427 if (net_busy_flag) 428 poll_delay = CONFIG_SYS_HZ; 429#endif 430 431#ifdef CONFIG_SANDBOX 432 /* 433 * Skip delaying polls if a test requests it. 434 */ 435 if (state_get_skip_delays()) 436 poll_delay = 0; 437#endif 438 439 dev = stdio_get_by_name(sdev->name); 440 usb_kbd_dev = (struct usb_device *)dev->priv; 441 data = usb_kbd_dev->privptr; 442 443 if (get_timer(kbd_testc_tms) >= poll_delay) { 444 usb_kbd_poll_for_event(usb_kbd_dev); 445 kbd_testc_tms = get_timer(0); 446 } 447 448 return !(data->usb_in_pointer == data->usb_out_pointer); 449} 450 451/* gets the character from the queue */ 452static int usb_kbd_getc(struct stdio_dev *sdev) 453{ 454 struct stdio_dev *dev; 455 struct usb_device *usb_kbd_dev; 456 struct usb_kbd_pdata *data; 457 458 dev = stdio_get_by_name(sdev->name); 459 usb_kbd_dev = (struct usb_device *)dev->priv; 460 data = usb_kbd_dev->privptr; 461 462 while (data->usb_in_pointer == data->usb_out_pointer) { 463 schedule(); 464 usb_kbd_poll_for_event(usb_kbd_dev); 465 } 466 467 if (data->usb_out_pointer == USB_KBD_BUFFER_LEN - 1) 468 data->usb_out_pointer = 0; 469 else 470 data->usb_out_pointer++; 471 472 return data->usb_kbd_buffer[data->usb_out_pointer]; 473} 474 475/* probes the USB device dev for keyboard type. */ 476static int usb_kbd_probe_dev(struct usb_device *dev, unsigned int ifnum) 477{ 478 struct usb_interface *iface; 479 struct usb_endpoint_descriptor *ep; 480 struct usb_kbd_pdata *data; 481 unsigned int quirks = 0; 482 int epNum; 483 484 if (dev->descriptor.bNumConfigurations != 1) 485 return 0; 486 487 iface = &dev->config.if_desc[ifnum]; 488 489 if (iface->desc.bInterfaceClass != USB_CLASS_HID) 490 return 0; 491 492 if (iface->desc.bInterfaceSubClass != USB_SUB_HID_BOOT) 493 return 0; 494 495 if (iface->desc.bInterfaceProtocol != USB_PROT_HID_KEYBOARD) 496 return 0; 497 498 for (epNum = 0; epNum < iface->desc.bNumEndpoints; epNum++) { 499 ep = &iface->ep_desc[epNum]; 500 501 /* Check if endpoint is interrupt IN endpoint */ 502 if ((ep->bmAttributes & 3) != 3) 503 continue; 504 505 if (ep->bEndpointAddress & 0x80) 506 break; 507 } 508 509 if (epNum == iface->desc.bNumEndpoints) 510 return 0; 511 512 debug("USB KBD: found interrupt EP: 0x%x\n", ep->bEndpointAddress); 513 514 switch (dev->descriptor.idVendor) { 515 case USB_VENDOR_ID_APPLE: 516 case USB_VENDOR_ID_KEYCHRON: 517 quirks |= USB_HID_QUIRK_POLL_NO_REPORT_IDLE; 518 break; 519 default: 520 break; 521 } 522 523 data = malloc(sizeof(struct usb_kbd_pdata)); 524 if (!data) { 525 printf("USB KBD: Error allocating private data\n"); 526 return 0; 527 } 528 529 /* Clear private data */ 530 memset(data, 0, sizeof(struct usb_kbd_pdata)); 531 532 /* allocate input buffer aligned and sized to USB DMA alignment */ 533 data->new = memalign(USB_DMA_MINALIGN, 534 roundup(USB_KBD_BOOT_REPORT_SIZE, USB_DMA_MINALIGN)); 535 536 data->ifnum = ifnum; 537 538 /* Insert private data into USB device structure */ 539 dev->privptr = data; 540 541 /* Set IRQ handler */ 542 dev->irq_handle = usb_kbd_irq; 543 544 data->intpipe = usb_rcvintpipe(dev, ep->bEndpointAddress); 545 data->intpktsize = min(usb_maxpacket(dev, data->intpipe), 546 USB_KBD_BOOT_REPORT_SIZE); 547 data->intinterval = ep->bInterval; 548 data->last_report = -1; 549 550 /* We found a USB Keyboard, install it. */ 551 debug("USB KBD: set boot protocol\n"); 552 usb_set_protocol(dev, iface->desc.bInterfaceNumber, 0); 553 554#if !defined(CONFIG_SYS_USB_EVENT_POLL_VIA_CONTROL_EP) && \ 555 !defined(CONFIG_SYS_USB_EVENT_POLL_VIA_INT_QUEUE) 556 debug("USB KBD: set idle interval...\n"); 557 usb_set_idle(dev, iface->desc.bInterfaceNumber, REPEAT_RATE / 4, 0); 558#else 559 debug("USB KBD: set idle interval=0...\n"); 560 usb_set_idle(dev, iface->desc.bInterfaceNumber, 0, 0); 561#endif 562 563 /* 564 * Apple and Keychron keyboards do not report the device state. Reports 565 * are only returned during key presses. 566 */ 567 if (quirks & USB_HID_QUIRK_POLL_NO_REPORT_IDLE) { 568 debug("USB KBD: quirk: skip testing device state\n"); 569 return 1; 570 } 571 debug("USB KBD: enable interrupt pipe...\n"); 572#ifdef CONFIG_SYS_USB_EVENT_POLL_VIA_INT_QUEUE 573 data->intq = create_int_queue(dev, data->intpipe, 1, 574 USB_KBD_BOOT_REPORT_SIZE, data->new, 575 data->intinterval); 576 if (!data->intq) { 577#elif defined(CONFIG_SYS_USB_EVENT_POLL_VIA_CONTROL_EP) 578 if (usb_get_report(dev, iface->desc.bInterfaceNumber, 579 1, 0, data->new, USB_KBD_BOOT_REPORT_SIZE) < 0) { 580#else 581 if (usb_int_msg(dev, data->intpipe, data->new, data->intpktsize, 582 data->intinterval, false) < 0) { 583#endif 584 printf("Failed to get keyboard state from device %04x:%04x\n", 585 dev->descriptor.idVendor, dev->descriptor.idProduct); 586 /* Abort, we don't want to use that non-functional keyboard. */ 587 return 0; 588 } 589 590 /* Success. */ 591 return 1; 592} 593 594static int probe_usb_keyboard(struct usb_device *dev) 595{ 596 char *stdinname; 597 struct stdio_dev usb_kbd_dev; 598 unsigned int ifnum; 599 unsigned int max_ifnum = min((unsigned int)USB_MAX_ACTIVE_INTERFACES, 600 (unsigned int)dev->config.no_of_if); 601 int error; 602 603 /* Try probing the keyboard */ 604 for (ifnum = 0; ifnum < max_ifnum; ifnum++) { 605 if (usb_kbd_probe_dev(dev, ifnum) == 1) 606 break; 607 } 608 if (ifnum >= max_ifnum) 609 return -ENOENT; 610 611 /* Register the keyboard */ 612 debug("USB KBD: register.\n"); 613 memset(&usb_kbd_dev, 0, sizeof(struct stdio_dev)); 614 strcpy(usb_kbd_dev.name, DEVNAME); 615 usb_kbd_dev.flags = DEV_FLAGS_INPUT; 616 usb_kbd_dev.getc = usb_kbd_getc; 617 usb_kbd_dev.tstc = usb_kbd_testc; 618 usb_kbd_dev.priv = (void *)dev; 619 error = stdio_register(&usb_kbd_dev); 620 if (error) 621 return error; 622 623 stdinname = env_get("stdin"); 624#if CONFIG_IS_ENABLED(CONSOLE_MUX) 625 if (strstr(stdinname, DEVNAME) != NULL) { 626 error = iomux_doenv(stdin, stdinname); 627 if (error) 628 return error; 629 } 630#else 631 /* Check if this is the standard input device. */ 632 if (!strcmp(stdinname, DEVNAME)) { 633 /* Reassign the console */ 634 if (overwrite_console()) 635 return 1; 636 637 error = console_assign(stdin, DEVNAME); 638 if (error) 639 return error; 640 } 641#endif 642 643 return 0; 644} 645 646#if !CONFIG_IS_ENABLED(DM_USB) 647/* Search for keyboard and register it if found. */ 648int drv_usb_kbd_init(void) 649{ 650 int error, i; 651 652 debug("%s: Probing for keyboard\n", __func__); 653 /* Scan all USB Devices */ 654 for (i = 0; i < USB_MAX_DEVICE; i++) { 655 struct usb_device *dev; 656 657 /* Get USB device. */ 658 dev = usb_get_dev_index(i); 659 if (!dev) 660 break; 661 662 if (dev->devnum == -1) 663 continue; 664 665 error = probe_usb_keyboard(dev); 666 if (!error) 667 return 1; 668 if (error && error != -ENOENT) 669 return error; 670 } 671 672 /* No USB Keyboard found */ 673 return -1; 674} 675 676/* Deregister the keyboard. */ 677int usb_kbd_deregister(int force) 678{ 679#if CONFIG_IS_ENABLED(SYS_STDIO_DEREGISTER) 680 struct stdio_dev *dev; 681 struct usb_device *usb_kbd_dev; 682 struct usb_kbd_pdata *data; 683 684 dev = stdio_get_by_name(DEVNAME); 685 if (dev) { 686 usb_kbd_dev = (struct usb_device *)dev->priv; 687 data = usb_kbd_dev->privptr; 688#if CONFIG_IS_ENABLED(CONSOLE_MUX) 689 if (iomux_replace_device(stdin, DEVNAME, force ? "nulldev" : "")) 690 return 1; 691#endif 692 if (stdio_deregister_dev(dev, force) != 0) 693 return 1; 694#ifdef CONFIG_SYS_USB_EVENT_POLL_VIA_INT_QUEUE 695 destroy_int_queue(usb_kbd_dev, data->intq); 696#endif 697 free(data->new); 698 free(data); 699 } 700 701 return 0; 702#else 703 return 1; 704#endif 705} 706 707#endif 708 709#if CONFIG_IS_ENABLED(DM_USB) 710 711static int usb_kbd_probe(struct udevice *dev) 712{ 713 struct usb_device *udev = dev_get_parent_priv(dev); 714 715 return probe_usb_keyboard(udev); 716} 717 718static int usb_kbd_remove(struct udevice *dev) 719{ 720 struct usb_device *udev = dev_get_parent_priv(dev); 721 struct usb_kbd_pdata *data; 722 struct stdio_dev *sdev; 723 int ret; 724 725 sdev = stdio_get_by_name(DEVNAME); 726 if (!sdev) { 727 ret = -ENXIO; 728 goto err; 729 } 730 data = udev->privptr; 731#if CONFIG_IS_ENABLED(CONSOLE_MUX) 732 if (iomux_replace_device(stdin, DEVNAME, "nulldev")) { 733 ret = -ENOLINK; 734 goto err; 735 } 736#endif 737 if (stdio_deregister_dev(sdev, true)) { 738 ret = -EPERM; 739 goto err; 740 } 741#ifdef CONFIG_SYS_USB_EVENT_POLL_VIA_INT_QUEUE 742 destroy_int_queue(udev, data->intq); 743#endif 744 free(data->new); 745 free(data); 746 747 return 0; 748err: 749 printf("%s: warning, ret=%d", __func__, ret); 750 return ret; 751} 752 753static const struct udevice_id usb_kbd_ids[] = { 754 { .compatible = "usb-keyboard" }, 755 { } 756}; 757 758U_BOOT_DRIVER(usb_kbd) = { 759 .name = "usb_kbd", 760 .id = UCLASS_KEYBOARD, 761 .of_match = usb_kbd_ids, 762 .probe = usb_kbd_probe, 763 .remove = usb_kbd_remove, 764}; 765 766static const struct usb_device_id kbd_id_table[] = { 767 { 768 .match_flags = USB_DEVICE_ID_MATCH_INT_CLASS | 769 USB_DEVICE_ID_MATCH_INT_SUBCLASS | 770 USB_DEVICE_ID_MATCH_INT_PROTOCOL, 771 .bInterfaceClass = USB_CLASS_HID, 772 .bInterfaceSubClass = USB_SUB_HID_BOOT, 773 .bInterfaceProtocol = USB_PROT_HID_KEYBOARD, 774 }, 775 { 776 USB_DEVICE(USB_VENDOR_ID_APPLE, 777 USB_DEVICE_ID_APPLE_MAGIC_KEYBOARD_2021), 778 }, 779 { 780 USB_DEVICE(USB_VENDOR_ID_APPLE, 781 USB_DEVICE_ID_APPLE_MAGIC_KEYBOARD_FINGERPRINT_2021), 782 }, 783 { 784 USB_DEVICE(USB_VENDOR_ID_APPLE, 785 USB_DEVICE_ID_APPLE_MAGIC_KEYBOARD_NUMPAD_2021), 786 }, 787 { } /* Terminating entry */ 788}; 789 790U_BOOT_USB_DEVICE(usb_kbd, kbd_id_table); 791 792#endif 793