From 544629e8c366697bf859959b7a315e7291b36dd0 Mon Sep 17 00:00:00 2001 From: Hans-Christoph Steiner Date: Fri, 25 Aug 2006 01:41:49 +0000 Subject: code cleanups, replaced sprintf() for snprintf() for security's sake svn path=/trunk/externals/hcs/hid/; revision=5735 --- TODO | 6 ++ doc/hid-help.pd | 10 +- hid.c | 4 +- hid_linux.c | 277 +++++++++++++++++++++++++++----------------------------- 4 files changed, 146 insertions(+), 151 deletions(-) diff --git a/TODO b/TODO index 4a25b40..f3e32e2 100644 --- a/TODO +++ b/TODO @@ -1,3 +1,9 @@ + +______________________________________________________________________________ +- switch to snprintf + +in hid_darwin.c, replace all sprintf()s with snprintf()s. + ______________________________________________________________________________ - deal with hatswitches!! diff --git a/doc/hid-help.pd b/doc/hid-help.pd index e3eec37..fd41bf4 100644 --- a/doc/hid-help.pd +++ b/doc/hid-help.pd @@ -2,7 +2,7 @@ #X floatatom 27 439 5 0 0 0 - - -; #X floatatom 83 439 5 0 0 0 - - -; #X floatatom 63 395 6 0 0 0 - - -; -#X obj 129 77 tgl 35 0 empty empty empty 0 -6 0 8 -24198 -1 -1 25 25 +#X obj 129 77 tgl 35 0 empty empty empty 0 -6 0 8 -24198 -1 -1 0 25 ; #X floatatom 571 340 12 0 0 1 value - -; #X symbolatom 531 356 15 0 0 1 event_code - -; @@ -31,7 +31,7 @@ #X text 463 79 refresh device list; #X text 537 487 For more info:; #X text 266 557 released under the GNU GPL; -#X text 472 544 $Revision: 1.25 $$Date: 2006-06-02 21:32:53 $; +#X text 472 544 $Revision: 1.26 $$Date: 2006-08-25 01:41:49 $; #X text 473 557 $Author: eighthave $; #X msg 436 201 poll 20; #X msg 374 201 poll 2; @@ -259,7 +259,7 @@ of it could change without notice !!!; #X obj 492 321 unpack s s f; #X msg 258 110 open \$1; #X obj 258 92 hradio 15 1 0 8 empty empty empty 0 -6 0 8 -262144 -1 --1 2; +-1 0; #X floatatom 247 111 1 0 0 0 - - -; #X text 298 346 event_type event_code value; #X obj 63 374 route abs_x abs_y abs_z abs_rx abs_ry abs_rz abs_throttle @@ -358,7 +358,7 @@ type vendorID productID; #X connect 14 0 15 0; #X connect 16 0 17 0; #X restore 55 66 pd route info; -#X obj 32 97 tgl 15 0 empty empty open 0 -6 0 8 -262144 -1 -1 1 1; +#X obj 32 97 tgl 15 0 empty empty open 0 -6 0 8 -262144 -1 -1 0 1; #X obj 61 23 inlet; #X obj 74 44 print info; #X symbolatom 255 94 0 0 0 0 productID - -; @@ -449,7 +449,7 @@ IDs (it is not case sensitive):; #X floatatom 73 172 5 0 0 0 - - -; #X obj 126 175 spigot; #X obj 124 216 print test; -#X obj 167 152 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 +#X obj 167 152 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1; #X obj 270 82 spigot; #X obj 268 123 print test; diff --git a/hid.c b/hid.c index bd14f6c..4cc120f 100644 --- a/hid.c +++ b/hid.c @@ -35,8 +35,8 @@ * LOCAL DEFINES */ -#define DEBUG(x) -//#define DEBUG(x) x +//#define DEBUG(x) +#define DEBUG(x) x unsigned short global_debug_level = 0; diff --git a/hid_linux.c b/hid_linux.c index de2f52c..f69e664 100644 --- a/hid_linux.c +++ b/hid_linux.c @@ -15,8 +15,8 @@ #include "hid.h" -#define DEBUG(x) -//#define DEBUG(x) x +//#define DEBUG(x) +#define DEBUG(x) x #define LINUX_BLOCK_DEVICE "/dev/input/event" @@ -49,21 +49,21 @@ t_symbol* hid_convert_linux_buttons_to_numbers(__u16 linux_code) { - char hid_code[10]; + char hid_code[MAXPDSTRING]; if(linux_code >= 0x100) { - if(linux_code < BTN_MOUSE) - sprintf(hid_code,"btn_%d",linux_code - BTN_MISC); /* numbered buttons */ - else if(linux_code < BTN_JOYSTICK) - sprintf(hid_code,"btn_%d",linux_code - BTN_MOUSE); /* mouse buttons */ - else if(linux_code < BTN_GAMEPAD) - sprintf(hid_code,"btn_%d",linux_code - BTN_JOYSTICK); /* joystick buttons */ - else if(linux_code < BTN_DIGI) - sprintf(hid_code,"btn_%d",linux_code - BTN_GAMEPAD); /* gamepad buttons */ - else if(linux_code < BTN_WHEEL) - sprintf(hid_code,"btn_%d",linux_code - BTN_DIGI); /* tablet buttons */ - else if(linux_code < KEY_OK) - sprintf(hid_code,"btn_%d",linux_code - BTN_WHEEL); /* wheel buttons */ + if(linux_code < BTN_MOUSE) /* numbered buttons */ + snprintf(hid_code, MAXPDSTRING,"btn_%d",linux_code - BTN_MISC); + else if(linux_code < BTN_JOYSTICK) /* mouse buttons */ + snprintf(hid_code, MAXPDSTRING,"btn_%d",linux_code - BTN_MOUSE); + else if(linux_code < BTN_GAMEPAD) /* joystick buttons */ + snprintf(hid_code, MAXPDSTRING,"btn_%d",linux_code - BTN_JOYSTICK); + else if(linux_code < BTN_DIGI) /* gamepad buttons */ + snprintf(hid_code, MAXPDSTRING,"btn_%d",linux_code - BTN_GAMEPAD); + else if(linux_code < BTN_WHEEL) /* tablet buttons */ + snprintf(hid_code, MAXPDSTRING,"btn_%d",linux_code - BTN_DIGI); + else if(linux_code < KEY_OK) /* wheel buttons */ + snprintf(hid_code, MAXPDSTRING,"btn_%d",linux_code - BTN_WHEEL); else return 0; } return gensym(hid_code ? hid_code : "?"); @@ -78,10 +78,8 @@ t_symbol* hid_convert_linux_keys(__u16 linux_code) { if(linux_code > 226) return 0; - /* quick hack to get the keys */ - /* (in future this should be auto-generated) */ - static char key_names[227][20] = + static char key_names[227][32] = { "key_reserved", "key_esc", "key_1", "key_2", "key_3", "key_4", "key_5", "key_6", "key_7", "key_8", "key_9", "key_0", "key_minus", @@ -263,13 +261,13 @@ void hid_print_device_list(void) { debug_print(LOG_DEBUG,"hid_print_device_list"); int i,fd; - char device_output_string[256] = "Unknown"; - char dev_handle_name[20] = "/dev/input/event0"; + char device_output_string[MAXPDSTRING] = "Unknown"; + char dev_handle_name[MAXPDSTRING] = "/dev/input/event0"; post(""); for(i=0;i<128;++i) { - sprintf(dev_handle_name,"/dev/input/event%d",i); + snprintf(dev_handle_name, MAXPDSTRING, "/dev/input/event%d", i); if(dev_handle_name) { /* open the device read-only, non-exclusive */ @@ -292,6 +290,88 @@ void hid_print_device_list(void) post(""); } + + +static void hid_build_element_list(t_hid *x) +{ + post("hid_build_element_list"); + unsigned long element_bitmask[EV_MAX][NBITS(KEY_MAX)]; + uint8_t abs_bitmask[ABS_MAX/8 + 1]; + struct input_absinfo abs_features; + t_hid_element *new_element = NULL; + t_int i, j; + + element_count[x->x_device_number] = 0; + if( x->x_fd ) + { + new_element = getbytes(sizeof(t_hid_element)); + /* get bitmask representing supported elements (axes, keys, etc.) */ + memset(element_bitmask, 0, sizeof(element_bitmask)); + if( ioctl(x->x_fd, EVIOCGBIT(0, EV_MAX), element_bitmask[0]) < 0 ) + perror("[hid] error: evdev ioctl: element_bitmask"); + memset(abs_bitmask, 0, sizeof(abs_bitmask)); + if( ioctl(x->x_fd, EVIOCGBIT(EV_ABS, sizeof(abs_bitmask)), abs_bitmask) < 0 ) + perror("[hid] error: evdev ioctl: abs_bitmask"); + for( i = 1; i < EV_MAX; i++ ) + { + if(test_bit(i, element_bitmask[0])) + { + new_element->linux_type = i; + new_element->type = gensym(ev[i] ? ev[i] : "?"); + /* get bitmask representing supported button types */ + ioctl(x->x_fd, EVIOCGBIT(i, KEY_MAX), element_bitmask[i]); + /* cycle through all possible event codes (axes, keys, etc.) + * testing to see which are supported. + * i = i j = j + */ + for(j = 0; j < KEY_MAX; j++) + { + if( (i == EV_ABS) && (test_bit(j, abs_bitmask)) ) + { + /* this means that the bit is set in the axes list */ + if(ioctl(x->x_fd, EVIOCGABS(j), &abs_features)) + perror("evdev EVIOCGABS ioctl"); + new_element->min = abs_features.minimum; + new_element->max = abs_features.maximum; + } + else + { + new_element->min = 0; + new_element->max = 0; + } + if(test_bit(j, element_bitmask[i])) + { + new_element->linux_code = j; + if((i == EV_KEY) && (j >= BTN_MISC) && (j < KEY_OK) ) + { + new_element->name = hid_convert_linux_buttons_to_numbers(j); + } + else + { + new_element->name = gensym(event_names[i][j] ? event_names[i][j] : "?"); + } + if( i == EV_REL ) + new_element->relative = 1; + else + new_element->relative = 0; + // fill in the t_hid_element struct here + post("x->x_device_number: %d element_count[]: %d", + x->x_device_number, element_count[x->x_device_number]); + post("linux_type/linux_code: %d/%d type/name: %s/%s max: %d min: %d ", + new_element->linux_type, new_element->linux_code, + new_element->type->s_name, new_element->name->s_name, + new_element->max, new_element->min); + post("\tpolled: %d relative: %d", + new_element->polled, new_element->relative); + element[x->x_device_number][element_count[x->x_device_number]] = new_element; + ++element_count[x->x_device_number]; + } + } + } + } + } +} + /* ------------------------------------------------------------------------------ */ /* Pd [hid] FUNCTIONS */ /* ------------------------------------------------------------------------------ */ @@ -302,8 +382,8 @@ void hid_get_events(t_hid *x) /* for debugging, counts how many events are processed each time hid_read() is called */ DEBUG(t_int event_counter = 0;); - - t_symbol*hid_code=0; + unsigned short i; + t_hid_element *output_element = NULL; /* this will go into the generic read function declared in hid.h and * implemented in hid_linux.c @@ -314,37 +394,27 @@ void hid_get_events(t_hid *x) while( read (x->x_fd, &(hid_input_event), sizeof(struct input_event)) > -1 ) { - hid_code=0; - if( hid_input_event.type == EV_KEY ) - { - /* JMZ: originally both functions were called, the latter evtl. overwriting - * the former; now i only call the latter if the former does not return - * a valid result - */ - if(!(hid_code=hid_convert_linux_buttons_to_numbers(hid_input_event.code))) - hid_code=hid_convert_linux_keys(hid_input_event.code); - } - else if( hid_input_event.type == EV_SYN ) + if( hid_input_event.type != EV_SYN ) { - // filter out EV_SYN events, they are currently unused - } - else if( event_names[hid_input_event.type][hid_input_event.code] != NULL ) - { - hid_code = gensym(event_names[hid_input_event.type][hid_input_event.code]); - } - else - { - hid_code = gensym("unknown"); + for( i=0; i < element_count[x->x_device_number]; ++i ) + { + output_element = element[x->x_device_number][i]; + if( (hid_input_event.type == output_element->linux_type) && \ + (hid_input_event.code == output_element->linux_code) ) + { + output_element->value = hid_input_event.value; + post("output %d",output_element->value); + break; + } + } + if( output_element != NULL ) + hid_output_event(x, output_element); } - /* TODO: needs porting - if( hid_code && hid_input_event.type != EV_SYN ) - hid_output_event(x, gensym(ev[hid_input_event.type]), hid_code, - (t_float)hid_input_event.value);*/ DEBUG(++event_counter;); } DEBUG( - //if(event_counter > 0) - //post("output %d events",event_counter); + if(event_counter > 0) + post("output %d events",event_counter); ); return; @@ -362,14 +432,14 @@ t_int hid_open_device(t_hid *x, short device_number) { debug_print(LOG_DEBUG,"hid_open_device"); - char device_name[256] = "Unknown"; - char block_device[20] = "/dev/input/event0"; + char device_name[MAXPDSTRING] = "Unknown"; + char block_device[MAXPDSTRING] = "/dev/input/event0"; struct input_event hid_input_event; x->x_fd = -1; x->x_device_number = device_number; - sprintf(block_device,"/dev/input/event%d",x->x_device_number); + snprintf(block_device,MAXPDSTRING,"/dev/input/event%d",x->x_device_number); if(block_device) { @@ -394,6 +464,7 @@ t_int hid_open_device(t_hid *x, short device_number) post ("[hid] opened device %d (%s): %s", x->x_device_number,block_device,device_name); + post("pre hid_build_element_list"); hid_build_element_list(x); return (0); @@ -423,8 +494,8 @@ void hid_build_device_list(void) int fd; unsigned int i; unsigned int last_active_device = 0; - char device_name[256] = "Unknown"; - char block_device[20] = "/dev/input/event0"; + char device_name[MAXPDSTRING] = "Unknown"; + char block_device[MAXPDSTRING] = "/dev/input/event0"; struct input_event x_input_event; debug_print(LOG_DEBUG,"hid_build_device_list"); @@ -433,9 +504,9 @@ void hid_build_device_list(void) for(i=0; ix_device_number] = 0; - if( x->x_fd ) - { - new_element = getbytes(sizeof(t_hid_element)); - /* get bitmask representing supported elements (axes, keys, etc.) */ - memset(element_bitmask, 0, sizeof(element_bitmask)); - if( ioctl(x->x_fd, EVIOCGBIT(0, EV_MAX), element_bitmask[0]) < 0 ) - perror("[hid] error: evdev ioctl: element_bitmask"); - memset(abs_bitmask, 0, sizeof(abs_bitmask)); - if( ioctl(x->x_fd, EVIOCGBIT(EV_ABS, sizeof(abs_bitmask)), abs_bitmask) < 0 ) - perror("[hid] error: evdev ioctl: abs_bitmask"); - for( i = 1; i < EV_MAX; i++ ) - { - if(test_bit(i, element_bitmask[0])) - { - new_element->linux_type = i; - new_element->type = gensym(ev[i] ? ev[i] : "?"); - /* get bitmask representing supported button types */ - ioctl(x->x_fd, EVIOCGBIT(i, KEY_MAX), element_bitmask[i]); - /* cycle through all possible event codes (axes, keys, etc.) - * testing to see which are supported. - * i = i j = j - */ - for(j = 0; j < KEY_MAX; j++) - { - if(test_bit(j, abs_bitmask)) - { - /* this means that the bit is set in the axes list */ - if(ioctl(x->x_fd, EVIOCGABS(j), &abs_features)) - perror("evdev EVIOCGABS ioctl"); - new_element->min = abs_features.minimum; - new_element->max = abs_features.maximum; - } - else - { - new_element->min = 0; - new_element->max = 0; - } - if(test_bit(j, element_bitmask[i])) - { - new_element->linux_code = j; - if((i == EV_KEY) && (j >= BTN_MISC) && (j < KEY_OK) ) - { - new_element->name = hid_convert_linux_buttons_to_numbers(j); - } - else - { - new_element->name = gensym(event_names[i][j] ? event_names[i][j] : "?"); - } - if( i == EV_REL ) - new_element->relative = 1; - else - new_element->relative = 0; - // fill in the t_hid_element struct here -// post("x->x_device_number: %d element_count[]: %d", -// x->x_device_number, element_count[x->x_device_number]); - post("linux_type/linux_code: %d/%d type/name: %s %s max: %d min: %d ", - new_element->linux_type, new_element->linux_code, - new_element->type->s_name, new_element->name->s_name, - new_element->max, new_element->min); - post("\tpolled: %d relative: %d", - new_element->polled, new_element->relative); - element[x->x_device_number][element_count[x->x_device_number]] = new_element; - ++element_count[x->x_device_number]; - } - } - } - } - } -} - - void hid_platform_specific_free(t_hid *x) { /* nothing to be done here on GNU/Linux */ } + + + /* device info on the status outlet */ void hid_platform_specific_info(t_hid* x) { struct input_id my_id; - char device_name[256] = "Unknown"; + char device_name[MAXPDSTRING] = "Unknown"; char vendor_id_string[7]; char product_id_string[7]; - t_symbol *output_symbol; t_atom *output_atom = getbytes(sizeof(t_atom)); ioctl(x->x_fd, EVIOCGID); - sprintf(vendor_id_string,"0x%04x", my_id.vendor); + snprintf(vendor_id_string,7,"0x%04x", my_id.vendor); SETSYMBOL(output_atom, gensym(vendor_id_string)); outlet_anything( x->x_status_outlet, gensym("vendorID"), 1, output_atom); - sprintf(product_id_string,"0x%04x", my_id.product); + snprintf(product_id_string,7,"0x%04x", my_id.product); SETSYMBOL(output_atom, gensym(product_id_string)); outlet_anything( x->x_status_outlet, gensym("productID"), 1, output_atom); -- cgit v1.2.1