Changes in uspace/srv/hid/console/console.c [8c74d15:ffa2c8ef] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/srv/hid/console/console.c
r8c74d15 rffa2c8ef 41 41 #include <ipc/ns.h> 42 42 #include <errno.h> 43 #include <str_error.h>44 43 #include <ipc/console.h> 45 44 #include <unistd.h> … … 57 56 #include <io/style.h> 58 57 #include <io/screenbuffer.h> 59 #include <inttypes.h>60 58 61 59 #include "console.h" … … 66 64 #define NAME "console" 67 65 #define NAMESPACE "term" 68 /** Interval for checking for new keyboard (1/4s). */69 #define HOTPLUG_WATCH_INTERVAL (1000 * 250)70 71 /* Kernel defines 32 but does not export it. */72 #define MAX_IPC_OUTGOING_PHONES 12873 /** To allow proper phone closing. */74 static ipc_callid_t driver_phones[MAX_IPC_OUTGOING_PHONES] = { 0 };75 66 76 67 /** Phone to the keyboard driver. */ … … 97 88 } console_t; 98 89 99 100 101 90 /** Array of data for virtual consoles */ 102 91 static console_t consoles[CONSOLE_COUNT]; … … 328 317 static void change_console(console_t *cons) 329 318 { 330 if (cons == active_console) {319 if (cons == active_console) 331 320 return; 332 }333 321 334 322 fb_pending_flush(); … … 409 397 } 410 398 411 static void close_driver_phone(ipc_callid_t hash)412 {413 int i;414 for (i = 0; i < MAX_IPC_OUTGOING_PHONES; i++) {415 if (driver_phones[i] == hash) {416 printf("Device %" PRIxn " gone.\n", hash);417 driver_phones[i] = 0;418 async_hangup(i);419 return;420 }421 }422 }423 424 399 /** Handler for keyboard */ 425 400 static void keyboard_events(ipc_callid_t iid, ipc_call_t *icall) … … 436 411 case IPC_M_PHONE_HUNGUP: 437 412 /* TODO: Handle hangup */ 438 close_driver_phone(iid);439 413 return; 440 414 case KBD_EVENT: … … 480 454 case IPC_M_PHONE_HUNGUP: 481 455 /* TODO: Handle hangup */ 482 close_driver_phone(iid);483 456 return; 484 457 case MEVENT_BUTTON: 485 458 if (IPC_GET_ARG1(call) == 1) { 486 459 int newcon = gcons_mouse_btn((bool) IPC_GET_ARG2(call)); 487 if (newcon != -1) {460 if (newcon != -1) 488 461 change_console(&consoles[newcon]); 489 }490 462 } 491 463 retval = 0; … … 738 710 } 739 711 740 static int async_connect_to_me_hack(int phone, sysarg_t arg1, sysarg_t arg2, 741 sysarg_t arg3, async_client_conn_t client_receiver, ipc_callid_t *hash) 742 { 743 sysarg_t task_hash; 744 sysarg_t phone_hash; 745 int rc = async_req_3_5(phone, IPC_M_CONNECT_TO_ME, arg1, arg2, arg3, 746 NULL, NULL, NULL, &task_hash, &phone_hash); 747 if (rc != EOK) 748 return rc; 749 750 if (client_receiver != NULL) 751 async_new_connection(task_hash, phone_hash, phone_hash, NULL, 752 client_receiver); 753 754 if (hash != NULL) { 755 *hash = phone_hash; 756 } 757 758 return EOK; 759 } 760 761 static int connect_keyboard_or_mouse(const char *devname, 762 async_client_conn_t handler, const char *path) 763 { 764 int fd = open(path, O_RDONLY); 765 if (fd < 0) { 766 return fd; 767 } 768 769 int phone = fd_phone(fd); 770 close(fd); 771 if (phone < 0) { 712 static bool console_init(char *input) 713 { 714 /* Connect to input device */ 715 int input_fd = open(input, O_RDONLY); 716 if (input_fd < 0) { 717 printf(NAME ": Failed opening %s\n", input); 718 return false; 719 } 720 721 kbd_phone = fd_phone(input_fd); 722 if (kbd_phone < 0) { 772 723 printf(NAME ": Failed to connect to input device\n"); 773 return phone;774 }775 776 ipc_callid_t hash;777 int rc = async_connect_to_me_hack(phone, SERVICE_CONSOLE, 0, phone,778 handler, &hash);779 if (rc != EOK) {780 async_hangup(phone);781 printf(NAME ": " \782 "Failed to create callback from input device: %s.\n",783 str_error(rc));784 return rc;785 }786 787 driver_phones[phone] = hash;788 789 printf(NAME ": found %s \"%s\" (%" PRIxn ").\n", devname, path, hash);790 791 return phone;792 }793 794 static int connect_keyboard(const char *path)795 {796 return connect_keyboard_or_mouse("keyboard", keyboard_events, path);797 }798 799 static int connect_mouse(const char *path)800 {801 return connect_keyboard_or_mouse("mouse", mouse_events, path);802 }803 804 struct hid_class_info {805 char *classname;806 int (*connection_func)(const char *);807 };808 809 /** Periodically check for new keyboards in /dev/class/.810 *811 * @param arg Class name.812 * @return This function should never exit.813 */814 static int check_new_device_fibril(void *arg)815 {816 struct hid_class_info *dev_info = arg;817 818 size_t index = 1;819 820 while (true) {821 async_usleep(HOTPLUG_WATCH_INTERVAL);822 char *path;823 int rc = asprintf(&path, "/dev/class/%s\\%zu",824 dev_info->classname, index);825 if (rc < 0) {826 continue;827 }828 rc = 0;829 rc = dev_info->connection_func(path);830 if (rc > 0) {831 /* We do not allow unplug. */832 index++;833 }834 835 free(path);836 }837 838 return EOK;839 }840 841 842 /** Start a fibril monitoring hot-plugged keyboards.843 */844 static void check_new_devices_in_background(int (*connection_func)(const char *),845 const char *classname)846 {847 struct hid_class_info *dev_info = malloc(sizeof(struct hid_class_info));848 if (dev_info == NULL) {849 printf(NAME ": " \850 "out of memory, will not start hot-plug-watch fibril.\n");851 return;852 }853 int rc;854 855 rc = asprintf(&dev_info->classname, "%s", classname);856 if (rc < 0) {857 printf(NAME ": failed to format classname: %s.\n",858 str_error(rc));859 return;860 }861 dev_info->connection_func = connection_func;862 863 fid_t fid = fibril_create(check_new_device_fibril, (void *)dev_info);864 if (!fid) {865 printf(NAME866 ": failed to create hot-plug-watch fibril for %s.\n",867 classname);868 return;869 }870 fibril_add_ready(fid);871 }872 873 static bool console_init(char *input)874 {875 /* Connect to input device */876 kbd_phone = connect_keyboard(input);877 if (kbd_phone < 0) {878 724 return false; 879 725 } 880 881 mouse_phone = connect_mouse("/dev/hid_in/mouse"); 726 727 /* NB: The callback connection is slotted for removal */ 728 if (async_connect_to_me(kbd_phone, SERVICE_CONSOLE, 0, 0, keyboard_events) 729 != 0) { 730 printf(NAME ": Failed to create callback from input device\n"); 731 return false; 732 } 733 734 /* Connect to mouse device */ 735 mouse_phone = -1; 736 int mouse_fd = open("/dev/hid_in/mouse", O_RDONLY); 737 738 if (mouse_fd < 0) { 739 printf(NAME ": Notice - failed opening %s\n", "/dev/hid_in/mouse"); 740 goto skip_mouse; 741 } 742 743 mouse_phone = fd_phone(mouse_fd); 882 744 if (mouse_phone < 0) { 883 printf(NAME ": Failed to connect to mouse device: %s.\n", 884 str_error(mouse_phone)); 885 } 745 printf(NAME ": Failed to connect to mouse device\n"); 746 goto skip_mouse; 747 } 748 749 if (async_connect_to_me(mouse_phone, SERVICE_CONSOLE, 0, 0, mouse_events) 750 != 0) { 751 printf(NAME ": Failed to create callback from mouse device\n"); 752 mouse_phone = -1; 753 goto skip_mouse; 754 } 755 756 skip_mouse: 886 757 887 758 /* Connect to framebuffer driver */ … … 966 837 printf(NAME ": Error registering kconsole notifications\n"); 967 838 968 /* Start fibril for checking on hot-plugged keyboards. */969 check_new_devices_in_background(connect_keyboard, "keyboard");970 check_new_devices_in_background(connect_mouse, "mouse");971 972 839 return true; 973 840 } … … 989 856 if (!console_init(argv[1])) 990 857 return -1; 991 858 992 859 printf(NAME ": Accepting connections\n"); 993 860 async_manager();
Note:
See TracChangeset
for help on using the changeset viewer.