Changeset 41811af in mainline for uspace/srv/hid/console/console.c
- Timestamp:
- 2011-06-10T10:14:26Z (14 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- ab547063
- Parents:
- 9536e6e (diff), 390d80d (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)
links above to see all the changes relative to each parent. - File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/srv/hid/console/console.c
r9536e6e r41811af 39 39 #include <ipc/fb.h> 40 40 #include <ipc/services.h> 41 #include <ipc/ns.h> 41 #include <ns.h> 42 #include <ns_obsolete.h> 42 43 #include <errno.h> 44 #include <str_error.h> 43 45 #include <ipc/console.h> 44 46 #include <unistd.h> 45 47 #include <async.h> 48 #include <async_obsolete.h> 46 49 #include <adt/fifo.h> 47 50 #include <sys/mman.h> … … 51 54 #include <event.h> 52 55 #include <devmap.h> 56 #include <devmap_obsolete.h> 53 57 #include <fcntl.h> 54 58 #include <vfs/vfs.h> … … 56 60 #include <io/style.h> 57 61 #include <io/screenbuffer.h> 62 #include <inttypes.h> 58 63 59 64 #include "console.h" … … 61 66 #include "keybuffer.h" 62 67 68 // FIXME: remove this header 69 #include <kernel/ipc/ipc_methods.h> 63 70 64 71 #define NAME "console" 65 72 #define NAMESPACE "term" 73 74 /** Interval for checking for new keyboard (1/4s). */ 75 #define HOTPLUG_WATCH_INTERVAL (1000 * 250) 76 77 /* Kernel defines 32 but does not export it. */ 78 #define MAX_IPC_OUTGOING_PHONES 128 79 80 /** To allow proper phone closing. */ 81 static ipc_callid_t driver_phones[MAX_IPC_OUTGOING_PHONES] = { 0 }; 66 82 67 83 /** Phone to the keyboard driver. */ … … 111 127 static void curs_visibility(bool visible) 112 128 { 113 async_ msg_1(fb_info.phone, FB_CURSOR_VISIBILITY, visible);129 async_obsolete_msg_1(fb_info.phone, FB_CURSOR_VISIBILITY, visible); 114 130 } 115 131 116 132 static void curs_hide_sync(void) 117 133 { 118 async_ req_1_0(fb_info.phone, FB_CURSOR_VISIBILITY, false);134 async_obsolete_req_1_0(fb_info.phone, FB_CURSOR_VISIBILITY, false); 119 135 } 120 136 121 137 static void curs_goto(sysarg_t x, sysarg_t y) 122 138 { 123 async_ msg_2(fb_info.phone, FB_CURSOR_GOTO, x, y);139 async_obsolete_msg_2(fb_info.phone, FB_CURSOR_GOTO, x, y); 124 140 } 125 141 126 142 static void screen_clear(void) 127 143 { 128 async_ msg_0(fb_info.phone, FB_CLEAR);144 async_obsolete_msg_0(fb_info.phone, FB_CLEAR); 129 145 } 130 146 131 147 static void screen_yield(void) 132 148 { 133 async_ req_0_0(fb_info.phone, FB_SCREEN_YIELD);149 async_obsolete_req_0_0(fb_info.phone, FB_SCREEN_YIELD); 134 150 } 135 151 136 152 static void screen_reclaim(void) 137 153 { 138 async_ req_0_0(fb_info.phone, FB_SCREEN_RECLAIM);154 async_obsolete_req_0_0(fb_info.phone, FB_SCREEN_RECLAIM); 139 155 } 140 156 141 157 static void kbd_yield(void) 142 158 { 143 async_ req_0_0(kbd_phone, KBD_YIELD);159 async_obsolete_req_0_0(kbd_phone, KBD_YIELD); 144 160 } 145 161 146 162 static void kbd_reclaim(void) 147 163 { 148 async_ req_0_0(kbd_phone, KBD_RECLAIM);164 async_obsolete_req_0_0(kbd_phone, KBD_RECLAIM); 149 165 } 150 166 151 167 static void set_style(uint8_t style) 152 168 { 153 async_ msg_1(fb_info.phone, FB_SET_STYLE, style);169 async_obsolete_msg_1(fb_info.phone, FB_SET_STYLE, style); 154 170 } 155 171 156 172 static void set_color(uint8_t fgcolor, uint8_t bgcolor, uint8_t flags) 157 173 { 158 async_ msg_3(fb_info.phone, FB_SET_COLOR, fgcolor, bgcolor, flags);174 async_obsolete_msg_3(fb_info.phone, FB_SET_COLOR, fgcolor, bgcolor, flags); 159 175 } 160 176 161 177 static void set_rgb_color(uint32_t fgcolor, uint32_t bgcolor) 162 178 { 163 async_ msg_2(fb_info.phone, FB_SET_RGB_COLOR, fgcolor, bgcolor);179 async_obsolete_msg_2(fb_info.phone, FB_SET_RGB_COLOR, fgcolor, bgcolor); 164 180 } 165 181 … … 216 232 } 217 233 218 async_ req_4_0(fb_info.phone, FB_DRAW_TEXT_DATA,234 async_obsolete_req_4_0(fb_info.phone, FB_DRAW_TEXT_DATA, 219 235 x0, y0, width, height); 220 236 } … … 257 273 static void fb_putchar(wchar_t c, sysarg_t col, sysarg_t row) 258 274 { 259 async_ msg_3(fb_info.phone, FB_PUTCHAR, c, col, row);275 async_obsolete_msg_3(fb_info.phone, FB_PUTCHAR, c, col, row); 260 276 } 261 277 … … 306 322 307 323 if (cons == active_console) 308 async_ msg_1(fb_info.phone, FB_SCROLL, 1);324 async_obsolete_msg_1(fb_info.phone, FB_SCROLL, 1); 309 325 } 310 326 … … 323 339 324 340 if (cons == kernel_console) { 325 async_ serialize_start();341 async_obsolete_serialize_start(); 326 342 curs_hide_sync(); 327 343 gcons_in_kernel(); 328 344 screen_yield(); 329 345 kbd_yield(); 330 async_ serialize_end();346 async_obsolete_serialize_end(); 331 347 332 348 if (__SYSCALL0(SYS_DEBUG_ENABLE_CONSOLE)) { … … 338 354 339 355 if (cons != kernel_console) { 340 async_ serialize_start();356 async_obsolete_serialize_start(); 341 357 342 358 if (active_console == kernel_console) { … … 365 381 366 382 /* This call can preempt, but we are already at the end */ 367 rc = async_ req_4_0(fb_info.phone, FB_DRAW_TEXT_DATA,383 rc = async_obsolete_req_4_0(fb_info.phone, FB_DRAW_TEXT_DATA, 368 384 0, 0, cons->scr.size_x, 369 385 cons->scr.size_y); … … 393 409 curs_visibility(cons->scr.is_cursor_visible); 394 410 395 async_serialize_end(); 411 async_obsolete_serialize_end(); 412 } 413 } 414 415 static void close_driver_phone(ipc_callid_t hash) 416 { 417 int i; 418 for (i = 0; i < MAX_IPC_OUTGOING_PHONES; i++) { 419 if (driver_phones[i] == hash) { 420 printf("Device %" PRIxn " gone.\n", hash); 421 driver_phones[i] = 0; 422 async_obsolete_hangup(i); 423 return; 424 } 396 425 } 397 426 } … … 406 435 407 436 int retval; 408 console_event_t ev; 437 kbd_event_t ev; 438 439 if (!IPC_GET_IMETHOD(call)) { 440 /* TODO: Handle hangup */ 441 close_driver_phone(iid); 442 return; 443 } 409 444 410 445 switch (IPC_GET_IMETHOD(call)) { 411 case IPC_M_PHONE_HUNGUP:412 /* TODO: Handle hangup */413 return;414 446 case KBD_EVENT: 415 447 /* Got event from keyboard driver. */ … … 451 483 int retval; 452 484 485 if (!IPC_GET_IMETHOD(call)) { 486 /* TODO: Handle hangup */ 487 close_driver_phone(iid); 488 return; 489 } 490 453 491 switch (IPC_GET_IMETHOD(call)) { 454 case IPC_M_PHONE_HUNGUP:455 /* TODO: Handle hangup */456 return;457 492 case MEVENT_BUTTON: 458 493 if (IPC_GET_ARG1(call) == 1) { … … 487 522 } 488 523 489 async_ serialize_start();524 async_obsolete_serialize_start(); 490 525 491 526 size_t off = 0; … … 495 530 } 496 531 497 async_ serialize_end();532 async_obsolete_serialize_end(); 498 533 499 534 gcons_notify_char(cons->index); … … 521 556 522 557 size_t pos = 0; 523 console_event_t ev;558 kbd_event_t ev; 524 559 fibril_mutex_lock(&input_mutex); 525 560 … … 546 581 static void cons_get_event(console_t *cons, ipc_callid_t rid, ipc_call_t *request) 547 582 { 548 console_event_t ev;583 kbd_event_t ev; 549 584 550 585 fibril_mutex_lock(&input_mutex); … … 590 625 int rc; 591 626 592 async_ serialize_start();627 async_obsolete_serialize_start(); 593 628 if (cons->refcount == 0) 594 629 gcons_notify_connect(cons->index); … … 600 635 601 636 while (true) { 602 async_ serialize_end();637 async_obsolete_serialize_end(); 603 638 callid = async_get_call(&call); 604 async_ serialize_start();639 async_obsolete_serialize_start(); 605 640 606 641 arg1 = 0; … … 608 643 arg3 = 0; 609 644 610 switch (IPC_GET_IMETHOD(call)) { 611 case IPC_M_PHONE_HUNGUP: 645 if (!IPC_GET_IMETHOD(call)) { 612 646 cons->refcount--; 613 647 if (cons->refcount == 0) 614 648 gcons_notify_disconnect(cons->index); 615 649 return; 650 } 651 652 switch (IPC_GET_IMETHOD(call)) { 616 653 case VFS_OUT_READ: 617 async_ serialize_end();654 async_obsolete_serialize_end(); 618 655 cons_read(cons, callid, &call); 619 async_ serialize_start();656 async_obsolete_serialize_start(); 620 657 continue; 621 658 case VFS_OUT_WRITE: 622 async_ serialize_end();659 async_obsolete_serialize_end(); 623 660 cons_write(cons, callid, &call); 624 async_ serialize_start();661 async_obsolete_serialize_start(); 625 662 continue; 626 663 case VFS_OUT_SYNC: 627 664 fb_pending_flush(); 628 665 if (cons == active_console) { 629 async_ req_0_0(fb_info.phone, FB_FLUSH);666 async_obsolete_req_0_0(fb_info.phone, FB_FLUSH); 630 667 curs_goto(cons->scr.position_x, cons->scr.position_y); 631 668 } … … 634 671 /* Send message to fb */ 635 672 if (cons == active_console) 636 async_ msg_0(fb_info.phone, FB_CLEAR);673 async_obsolete_msg_0(fb_info.phone, FB_CLEAR); 637 674 638 675 screenbuffer_clear(&cons->scr); … … 693 730 break; 694 731 case CONSOLE_GET_EVENT: 695 async_ serialize_end();732 async_obsolete_serialize_end(); 696 733 cons_get_event(cons, callid, &call); 697 async_ serialize_start();734 async_obsolete_serialize_start(); 698 735 continue; 699 736 case CONSOLE_KCON_ENABLE: … … 710 747 } 711 748 712 static bool console_init(char *input) 749 static int async_connect_to_me_hack(int phone, sysarg_t arg1, sysarg_t arg2, 750 sysarg_t arg3, async_client_conn_t client_receiver, ipc_callid_t *hash) 751 { 752 sysarg_t task_hash; 753 sysarg_t phone_hash; 754 int rc = async_obsolete_req_3_5(phone, IPC_M_CONNECT_TO_ME, arg1, arg2, arg3, 755 NULL, NULL, NULL, &task_hash, &phone_hash); 756 if (rc != EOK) 757 return rc; 758 759 if (client_receiver != NULL) 760 async_new_connection(task_hash, phone_hash, phone_hash, NULL, 761 client_receiver); 762 763 if (hash != NULL) 764 *hash = phone_hash; 765 766 return EOK; 767 } 768 769 static int connect_keyboard_or_mouse(const char *devname, 770 async_client_conn_t handler, const char *dev) 771 { 772 int phone; 773 devmap_handle_t handle; 774 775 int rc = devmap_device_get_handle(dev, &handle, 0); 776 if (rc == EOK) { 777 phone = devmap_obsolete_device_connect(handle, 0); 778 if (phone < 0) { 779 printf("%s: Failed to connect to input device\n", NAME); 780 return phone; 781 } 782 } else 783 return rc; 784 785 /* NB: The callback connection is slotted for removal */ 786 ipc_callid_t hash; 787 rc = async_connect_to_me_hack(phone, SERVICE_CONSOLE, 0, phone, 788 handler, &hash); 789 if (rc != EOK) { 790 async_obsolete_hangup(phone); 791 printf("%s: Failed to create callback from input device (%s).\n", 792 NAME, str_error(rc)); 793 return rc; 794 } 795 796 driver_phones[phone] = hash; 797 printf("%s: found %s \"%s\" (%" PRIxn ").\n", NAME, devname, dev, hash); 798 return phone; 799 } 800 801 static int connect_keyboard(const char *dev) 802 { 803 return connect_keyboard_or_mouse("keyboard", keyboard_events, dev); 804 } 805 806 static int connect_mouse(const char *dev) 807 { 808 return connect_keyboard_or_mouse("mouse", mouse_events, dev); 809 } 810 811 struct hid_class_info { 812 char *classname; 813 int (*connection_func)(const char *); 814 }; 815 816 /** Periodically check for new keyboards in /dev/class/. 817 * 818 * @param arg Class name. 819 * 820 * @return This function should never exit. 821 * 822 */ 823 static int check_new_device_fibril(void *arg) 824 { 825 struct hid_class_info *dev_info = (struct hid_class_info *) arg; 826 827 size_t index = 1; 828 829 while (true) { 830 async_usleep(HOTPLUG_WATCH_INTERVAL); 831 832 char *dev; 833 int rc = asprintf(&dev, "class/%s\\%zu", 834 dev_info->classname, index); 835 if (rc < 0) 836 continue; 837 838 rc = dev_info->connection_func(dev); 839 if (rc > 0) { 840 /* We do not allow unplug. */ 841 index++; 842 } 843 844 free(dev); 845 } 846 847 return EOK; 848 } 849 850 /** Start a fibril monitoring hot-plugged keyboards. 851 */ 852 static void check_new_devices_in_background(int (*connection_func)(const char *), 853 const char *classname) 854 { 855 struct hid_class_info *dev_info = malloc(sizeof(struct hid_class_info)); 856 if (dev_info == NULL) { 857 printf("%s: Out of memory, no hot-plug support.\n", NAME); 858 return; 859 } 860 861 int rc = asprintf(&dev_info->classname, "%s", classname); 862 if (rc < 0) { 863 printf("%s: Failed to format classname: %s.\n", NAME, 864 str_error(rc)); 865 return; 866 } 867 868 dev_info->connection_func = connection_func; 869 870 fid_t fid = fibril_create(check_new_device_fibril, (void *) dev_info); 871 if (!fid) { 872 printf("%s: Failed to create hot-plug fibril for %s.\n", NAME, 873 classname); 874 return; 875 } 876 877 fibril_add_ready(fid); 878 } 879 880 static bool console_srv_init(char *kdev) 713 881 { 714 882 /* 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); 883 kbd_phone = connect_keyboard(kdev); 884 if (kbd_phone < 0) 718 885 return false; 719 } 720 721 kbd_phone = fd_phone(input_fd); 722 if (kbd_phone < 0) { 723 printf(NAME ": Failed to connect to input device\n"); 886 887 mouse_phone = connect_mouse("hid_in/mouse"); 888 if (mouse_phone < 0) { 889 printf("%s: Failed to connect to mouse device %s\n", NAME, 890 str_error(mouse_phone)); 891 } 892 893 /* Connect to framebuffer driver */ 894 fb_info.phone = service_obsolete_connect_blocking(SERVICE_VIDEO, 0, 0); 895 if (fb_info.phone < 0) { 896 printf("%s: Failed to connect to video service\n", NAME); 724 897 return false; 725 }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);744 if (mouse_phone < 0) {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:757 758 /* Connect to framebuffer driver */759 fb_info.phone = service_connect_blocking(SERVICE_VIDEO, 0, 0);760 if (fb_info.phone < 0) {761 printf(NAME ": Failed to connect to video service\n");762 return -1;763 898 } 764 899 … … 766 901 int rc = devmap_driver_register(NAME, client_connection); 767 902 if (rc < 0) { 768 printf( NAME ": Unable to register driver (%d)\n", rc);903 printf("%s: Unable to register driver (%d)\n", NAME, rc); 769 904 return false; 770 905 } … … 774 909 775 910 /* Synchronize, the gcons could put something in queue */ 776 async_ req_0_0(fb_info.phone, FB_FLUSH);777 async_ req_0_2(fb_info.phone, FB_GET_CSIZE, &fb_info.cols, &fb_info.rows);778 async_ req_0_1(fb_info.phone, FB_GET_COLOR_CAP, &fb_info.color_cap);911 async_obsolete_req_0_0(fb_info.phone, FB_FLUSH); 912 async_obsolete_req_0_2(fb_info.phone, FB_GET_CSIZE, &fb_info.cols, &fb_info.rows); 913 async_obsolete_req_0_1(fb_info.phone, FB_GET_COLOR_CAP, &fb_info.color_cap); 779 914 780 915 /* Set up shared memory buffer. */ … … 787 922 788 923 if (interbuffer) { 789 if (async_ share_out_start(fb_info.phone, interbuffer,924 if (async_obsolete_share_out_start(fb_info.phone, interbuffer, 790 925 AS_AREA_READ) != EOK) { 791 926 as_area_destroy(interbuffer); … … 802 937 if (screenbuffer_init(&consoles[i].scr, 803 938 fb_info.cols, fb_info.rows) == NULL) { 804 printf( NAME ": Unable to allocate screen buffer %zu\n", i);939 printf("%s: Unable to allocate screen buffer %zu\n", NAME, i); 805 940 return false; 806 941 } … … 814 949 815 950 if (devmap_device_register(vc, &consoles[i].devmap_handle) != EOK) { 816 printf( NAME ": Unable to register device %s\n", vc);951 printf("%s: Unable to register device %s\n", NAME, vc); 817 952 return false; 818 953 } … … 824 959 825 960 /* Initialize the screen */ 826 async_ serialize_start();961 async_obsolete_serialize_start(); 827 962 gcons_redraw_console(); 828 963 set_style(STYLE_NORMAL); … … 830 965 curs_goto(0, 0); 831 966 curs_visibility(active_console->scr.is_cursor_visible); 832 async_ serialize_end();967 async_obsolete_serialize_end(); 833 968 834 969 /* Receive kernel notifications */ 835 970 async_set_interrupt_received(interrupt_received); 836 971 if (event_subscribe(EVENT_KCONSOLE, 0) != EOK) 837 printf(NAME ": Error registering kconsole notifications\n"); 972 printf("%s: Error registering kconsole notifications\n", NAME); 973 974 /* Start fibril for checking on hot-plugged keyboards. */ 975 check_new_devices_in_background(connect_keyboard, "keyboard"); 976 check_new_devices_in_background(connect_mouse, "mouse"); 838 977 839 978 return true; … … 854 993 printf(NAME ": HelenOS Console service\n"); 855 994 856 if (!console_ init(argv[1]))995 if (!console_srv_init(argv[1])) 857 996 return -1; 858 997
Note:
See TracChangeset
for help on using the changeset viewer.