[PD-cvs] externals/hcs usbhid.c,1.3,1.4 usbhid-help.pd,1.3,1.4

Hans-Christoph Steiner eighthave at users.sourceforge.net
Thu May 25 14:33:35 CEST 2006


Update of /cvsroot/pure-data/externals/hcs
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv3435

Modified Files:
	usbhid.c usbhid-help.pd 
Log Message:
message naming makes more sense now, and there is more status info; don't know if writing works yet, probably needs some work

Index: usbhid-help.pd
===================================================================
RCS file: /cvsroot/pure-data/externals/hcs/usbhid-help.pd,v
retrieving revision 1.3
retrieving revision 1.4
diff -C2 -d -r1.3 -r1.4
*** usbhid-help.pd	24 May 2006 13:02:37 -0000	1.3
--- usbhid-help.pd	25 May 2006 12:33:33 -0000	1.4
***************
*** 1,29 ****
! #N canvas 338 93 633 511 10;
! #X obj 111 373 usbhid;
! #X msg 184 111 close;
! #X msg 184 137 reset;
! #X obj 6 408 print left;
! #X obj 175 410 print right;
! #X text 195 174 [read page# usage# ...(;
! #X text 208 223 [write page# usage# ...(;
! #X msg 217 244 set write 1 30 1 31 1 38;
! #X text 233 288 GARBAGE FOR TESTING;
! #X msg 250 322 set read 1 30 word 1 31 1 38;
  #X msg 197 155 print;
! #X msg 176 91 open 1149 16392;
! #X text 297 91 Gravis/Destroyer Tiltpad;
! #X text 261 63 Microsoft 5-button Mouse;
! #X msg 171 63 open 1118 57;
! #X msg 159 42 open 1452 517;
! #X text 258 42 Mitsumi Electric Apple Extended USB Keyboard;
! #X msg 258 350 open 1118 57 \, get read;
! #X msg 204 195 set read 1 2 1 48;
! #X msg 221 267 get read;
! #N canvas 0 22 454 304 buttons 0;
  #X obj 99 36 inlet;
  #X obj 63 108 & 1;
  #X obj 63 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1
  ;
! #X obj 93 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1
  ;
  #X obj 123 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
--- 1,16 ----
! #N canvas 254 84 629 549 10;
! #X obj 132 376 usbhid;
! #X msg 184 91 close;
! #X msg 184 117 reset;
! #X text 240 307 GARBAGE FOR TESTING;
  #X msg 197 155 print;
! #X text 317 72 Gravis/Destroyer Tiltpad;
! #X text 311 43 Microsoft 5-button Mouse;
! #N canvas 0 22 462 312 buttons 0;
  #X obj 99 36 inlet;
  #X obj 63 108 & 1;
  #X obj 63 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1
  ;
! #X obj 93 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 2
  ;
  #X obj 123 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
***************
*** 34,42 ****
  16;
  #X obj 223 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
! 1;
  #X obj 263 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
  1;
  #X obj 303 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
! 1;
  #X obj 93 108 & 2;
  #X obj 123 108 & 4;
--- 21,29 ----
  16;
  #X obj 223 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
! 32;
  #X obj 263 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
  1;
  #X obj 303 130 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0
! 128;
  #X obj 93 108 & 2;
  #X obj 123 108 & 4;
***************
*** 62,94 ****
  #X connect 15 0 8 0;
  #X connect 16 0 9 0;
! #X restore 44 482 pd buttons test;
! #X obj 106 429 unpack float float float float;
  #X obj 44 83 metro 400;
  #X obj 46 57 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1
  ;
! #X floatatom 165 466 5 0 0 0 - - -;
! #X floatatom 235 467 5 0 0 0 - - -;
! #X floatatom 315 462 5 0 0 0 - - -;
! #X msg 44 104 read 4;
! #X msg 50 11 open vendorId productId;
! #X text 220 11 these are in decimal \, rather than the usual hex;
! #X connect 0 0 21 0;
! #X connect 0 1 4 0;
  #X connect 1 0 0 0;
  #X connect 2 0 0 0;
! #X connect 7 0 0 0;
! #X connect 9 0 0 0;
! #X connect 10 0 0 0;
! #X connect 11 0 0 0;
  #X connect 14 0 0 0;
! #X connect 15 0 0 0;
! #X connect 17 0 0 0;
  #X connect 18 0 0 0;
! #X connect 19 0 0 0;
! #X connect 21 0 20 0;
! #X connect 21 1 24 0;
! #X connect 21 2 25 0;
! #X connect 21 3 26 0;
! #X connect 22 0 27 0;
! #X connect 23 0 22 0;
! #X connect 27 0 0 0;
--- 49,139 ----
  #X connect 15 0 8 0;
  #X connect 16 0 9 0;
! #X restore 65 515 pd buttons test;
! #X obj 127 462 unpack float float float float;
  #X obj 44 83 metro 400;
  #X obj 46 57 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1
  ;
! #X floatatom 186 499 5 0 0 0 - - -;
! #X floatatom 256 500 5 0 0 0 - - -;
! #X floatatom 336 495 5 0 0 0 - - -;
! #X msg 171 43 open 0x045e 0x0039;
! #X msg 157 13 open vendorId productId;
! #X msg 176 71 open 0x047D 0x4008;
! #X floatatom 125 496 5 0 0 0 - - -;
! #X msg 239 273 debug \$1;
! #X obj 239 251 hradio 15 1 0 10 empty empty empty 0 -6 0 8 -262144
! -1 -1 0;
! #X obj 27 441 print data;
! #N canvas 458 151 454 485 parsing 0;
! #X obj 77 6 inlet;
! #X obj 80 101 route float symbol;
! #X obj 80 190 mapping/tolist;
! #X obj 139 137 trigger symbol bang;
! #X msg 22 139 bang;
! #X obj 81 226 list trim;
! #X obj 241 312 print;
! #X obj 80 272 route path;
! #X obj 34 328 print path-------------;
! #X obj 78 31 list-abs/list-drip;
! #X obj 198 51 trigger bang bang;
! #X obj 247 89 print end---------;
! #X connect 0 0 9 0;
! #X connect 1 0 2 0;
! #X connect 1 1 3 0;
! #X connect 2 0 5 0;
! #X connect 3 0 2 0;
! #X connect 3 1 2 1;
! #X connect 4 0 2 0;
! #X connect 5 0 7 0;
! #X connect 7 0 8 0;
! #X connect 7 1 6 0;
! #X connect 9 0 1 0;
! #X connect 9 1 10 0;
! #X connect 10 0 2 1;
! #X connect 10 1 11 0;
! #X restore 226 418 pd parsing;
! #X text 8 122 how many bytes to read;
! #X msg 194 136 refresh;
! #X text 259 137 reinit and refresh device list;
! #X text 233 117 resets device (don't really know what that does tho)
! ;
! #X obj 171 419 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1
! 1;
! #X obj 171 397 route open device;
! #X msg 44 104 get 4;
! #X msg 82 137 get 2;
! #X msg 212 179 descriptor;
! #X text 291 179 get descriptor;
! #X msg 219 213 descriptor 1 30 1 31 1 38;
! #X text 398 212 [descriptor page# usage# ...(;
! #X text 218 197 for writing to the device:;
! #X msg 25 208 set 2;
! #X msg 237 323 close \, open 0x045e 0x0039 \, descriptor;
! #X text 183 382 <- status outlet;
! #X text 21 383 data outlet ->;
! #X connect 0 0 8 0;
! #X connect 0 0 20 0;
! #X connect 0 1 27 0;
  #X connect 1 0 0 0;
  #X connect 2 0 0 0;
! #X connect 4 0 0 0;
! #X connect 8 0 7 0;
! #X connect 8 0 17 0;
! #X connect 8 1 11 0;
! #X connect 8 2 12 0;
! #X connect 8 3 13 0;
! #X connect 9 0 28 0;
! #X connect 10 0 9 0;
  #X connect 14 0 0 0;
! #X connect 16 0 0 0;
  #X connect 18 0 0 0;
! #X connect 19 0 18 0;
! #X connect 23 0 0 0;
! #X connect 27 0 26 0;
! #X connect 27 1 21 0;
! #X connect 28 0 0 0;
! #X connect 29 0 0 0;
! #X connect 30 0 0 0;
! #X connect 32 0 0 0;
! #X connect 35 0 0 0;
! #X connect 36 0 0 0;

Index: usbhid.c
===================================================================
RCS file: /cvsroot/pure-data/externals/hcs/usbhid.c,v
retrieving revision 1.3
retrieving revision 1.4
diff -C2 -d -r1.3 -r1.4
*** usbhid.c	24 May 2006 13:02:37 -0000	1.3
--- usbhid.c	25 May 2006 12:33:33 -0000	1.4
***************
*** 28,36 ****
  #include <stdio.h>
  #include <string.h>
  #include "m_pd.h"
  
  
  /*------------------------------------------------------------------------------
!  *  INCLUDE HACK
   */
  
--- 28,46 ----
  #include <stdio.h>
  #include <string.h>
+ #include <float.h>
  #include "m_pd.h"
  
+ /* 
+  * TODO: rename read, get, set messages so they make sense
+  * TODO: make size output work well
+  */
+ 
+ /* 
+  * BUG: for some reason it skips one of the button bits
+  */
+ 
  
  /*------------------------------------------------------------------------------
!  *  INCLUDE KLUDGE
   */
  
***************
*** 39,49 ****
   */
  struct usb_dev_handle {
!   int fd;
!   struct usb_bus *bus;
!   struct usb_device *device;
!   int config;
!   int interface;
!   int altsetting;
!   void *impl_info;
  };
  
--- 49,59 ----
   */
  struct usb_dev_handle {
! 	int fd;
! 	struct usb_bus *bus;
! 	struct usb_device *device;
! 	int config;
! 	int interface;
! 	int altsetting;
! 	void *impl_info;
  };
  
***************
*** 53,60 ****
   */
  
! /*
!  * count the number of instances of this object so that certain free()
!  * functions can be called only after the final instance is detroyed.
!  */
  t_int usbhid_instance_count;
  
--- 63,68 ----
   */
  
! /* count the number of instances of this object so that certain free()
!  * functions can be called only after the final instance is detroyed. */
  t_int usbhid_instance_count;
  
***************
*** 63,66 ****
--- 71,78 ----
  t_int hid_id_count;
  
+ /* this array is for keeping track of whether each device has been read in
+  * each cycle */
+ char usbhid_device_read_status[HID_ID_MAX];
+ 
  /*------------------------------------------------------------------------------
   *  CLASS DEF
***************
*** 72,78 ****
  /* usbhid types */
  	HIDInterface        *x_hidinterface;
- 	u_int8_t            x_iSerialNumber;
  	hid_return          x_hid_return;
  /* internal state */
  	t_int               x_device_number;
  	t_int               x_read_element_count;
--- 84,92 ----
  /* usbhid types */
  	HIDInterface        *x_hidinterface;
  	hid_return          x_hid_return;
  /* internal state */
+ 	unsigned short      vendor_id;    // idVendor for current device
+ 	unsigned short      product_id;   // idProduct for current device
+ 	unsigned short      debug_level;  // control debug messages to the console
  	t_int               x_device_number;
  	t_int               x_read_element_count;
***************
*** 80,92 ****
  	t_int               x_write_element_count;
  	t_int               *x_write_elements;
! /* clock support */
! 	t_clock             *x_clock;
! 	t_int               x_delay;
! 	t_int               x_started;
! /* outlets */
! 	t_atom              *output;
! 	t_int               output_count;
  	t_outlet            *x_data_outlet;
! 	t_outlet            *x_control_outlet;
  } t_usbhid;
  
--- 94,103 ----
  	t_int               x_write_element_count;
  	t_int               *x_write_elements;
! 	t_int               report_size;  // size in bytes of the HID report
! /* output */
! 	t_atom              *output; // holder for a list of atoms to be outputted
! 	t_int               output_count;  // number of atoms in in x->output 
  	t_outlet            *x_data_outlet;
! 	t_outlet            *x_status_outlet;
  } t_usbhid;
  
***************
*** 99,105 ****
  #define USBHID_MINOR_VERSION 0
  
- //#define DEBUG(x)
- #define DEBUG(x) x 
- 
  static t_class *usbhid_class;
  
--- 110,113 ----
***************
*** 129,132 ****
--- 137,156 ----
  }
  
+ static void add_symbol_to_output(t_usbhid *x, t_symbol *s)
+ {
+ 	t_atom *temp_atom = getbytes(sizeof(t_atom));
+ 	SETSYMBOL(temp_atom, s); 
+ 	add_atom_to_output(x,temp_atom);
+ 	freebytes(temp_atom,sizeof(t_atom));
+ }
+ 		
+ static void add_float_to_output(t_usbhid *x, t_float f)
+ {
+ 	t_atom *temp_atom = getbytes(sizeof(t_atom));
+ 	SETFLOAT(temp_atom, f);
+ 	add_atom_to_output(x,temp_atom);
+ 	freebytes(temp_atom,sizeof(t_atom));
+ }
+ 
  static void reset_output(t_usbhid *x)
  {
***************
*** 140,143 ****
--- 164,182 ----
  
  
+ static t_int init_libhid(t_usbhid *x)
+ {
+ 	if (! hid_is_initialised() )
+ 	{
+ 		x->x_hid_return = hid_init();
+ 		if(x->x_hid_return != HID_RET_SUCCESS)
+ 		{
+ 			error("[usbhid] hid_init failed with return code %d\n", 
+ 				  x->x_hid_return);
+ 		}
+ 	}
+ 	return(x->x_hid_return);
+ }
+ 
+ 
  /* 
   * This function is used in a HIDInterfaceMatcher to iterate thru all of the
***************
*** 145,149 ****
   */
  static bool device_iterator (struct usb_dev_handle const* usbdev, void* custom, 
! 					  unsigned int length)
  {
  	bool ret = false;
--- 184,188 ----
   */
  static bool device_iterator (struct usb_dev_handle const* usbdev, void* custom, 
! 							 unsigned int length)
  {
  	bool ret = false;
***************
*** 230,234 ****
  static t_int* make_hid_path(t_int element_count, t_int argc, t_atom *argv)
  {
- 	DEBUG(post("make_hid_path"););
  	t_int i;
  	t_int *return_array = NULL;
--- 269,272 ----
***************
*** 255,259 ****
  	t_int ret = 0;
  	char buffer[STRING_BUFFER_LENGTH];
! 	
  	if ( !hid_is_opened(hidif) ) 
  		return(0);
--- 293,297 ----
  	t_int ret = 0;
  	char buffer[STRING_BUFFER_LENGTH];
! 
  	if ( !hid_is_opened(hidif) ) 
  		return(0);
***************
*** 261,267 ****
  	if (hidif->device->descriptor.iManufacturer) {
  		length = usb_get_string_simple(hidif->dev_handle,
! 									hidif->device->descriptor.iManufacturer, 
! 									buffer, 
! 									STRING_BUFFER_LENGTH);
  		if (length > 0)
  		{
--- 299,305 ----
  	if (hidif->device->descriptor.iManufacturer) {
  		length = usb_get_string_simple(hidif->dev_handle,
! 									   hidif->device->descriptor.iManufacturer, 
! 									   buffer, 
! 									   STRING_BUFFER_LENGTH);
  		if (length > 0)
  		{
***************
*** 278,284 ****
  	if (hidif->device->descriptor.iProduct) {
  		length = usb_get_string_simple(hidif->dev_handle,
! 									hidif->device->descriptor.iProduct, 
! 									buffer, 
! 									STRING_BUFFER_LENGTH);
  		if (length > 0)
  		{
--- 316,322 ----
  	if (hidif->device->descriptor.iProduct) {
  		length = usb_get_string_simple(hidif->dev_handle,
! 									   hidif->device->descriptor.iProduct, 
! 									   buffer, 
! 									   STRING_BUFFER_LENGTH);
  		if (length > 0)
  		{
***************
*** 295,301 ****
  	if (hidif->device->descriptor.iSerialNumber) {
  		length = usb_get_string_simple(hidif->dev_handle,
! 									hidif->device->descriptor.iSerialNumber, 
! 									buffer, 
! 									STRING_BUFFER_LENGTH);
  		if (length > 0)
  			strncat(device_string, buffer, STRING_BUFFER_LENGTH - strlen(device_string));
--- 333,339 ----
  	if (hidif->device->descriptor.iSerialNumber) {
  		length = usb_get_string_simple(hidif->dev_handle,
! 									   hidif->device->descriptor.iSerialNumber, 
! 									   buffer, 
! 									   STRING_BUFFER_LENGTH);
  		if (length > 0)
  			strncat(device_string, buffer, STRING_BUFFER_LENGTH - strlen(device_string));
***************
*** 312,329 ****
   */
  
  /* -------------------------------------------------------------------------- */
! static void usbhid_open(t_usbhid *x, t_float vendor_id, t_float product_id)
  {
! 	DEBUG(post("usbhid_open"););
  	char string_buffer[STRING_BUFFER_LENGTH];
- 	
- 	HIDInterfaceMatcher matcher = { (unsigned short)vendor_id, 
- 									(unsigned short)product_id, 
- 									NULL, 
- 									NULL, 
- 									0 };
  
!  	if ( !hid_is_opened(x->x_hidinterface) ) 
  	{
  		x->x_hid_return = hid_force_open(x->x_hidinterface, 0, &matcher, 3);
  		if (x->x_hid_return == HID_RET_SUCCESS) 
--- 350,416 ----
   */
  
+ 
  /* -------------------------------------------------------------------------- */
! static void usbhid_close(t_usbhid *x) 
  {
! 	if(x->debug_level) post("usbhid_close");
! 	t_int ret;
  	char string_buffer[STRING_BUFFER_LENGTH];
  
! 	if ( hid_is_opened(x->x_hidinterface) ) 
! 	{
! 		ret = get_device_string(x->x_hidinterface,string_buffer);
! 		x->x_hid_return = hid_close(x->x_hidinterface);
! 		if (x->x_hid_return == HID_RET_SUCCESS) 
! 		{
! 			if (ret) 
! 				post("[usbhid]: closed %s",string_buffer);
! 			else
! 				post("[usbhid]: closed device");
! 			reset_output(x);
! 			add_float_to_output(x,0);
! 			outlet_anything(x->x_status_outlet, gensym("open"), 
! 							x->output_count, x->output);
! 		}
! 		else
! 		{
! 			error("[usbhid] could not close %d, error #%d",x->x_device_number,x->x_hid_return);
! 		}
! 	}
! }
! 
! 
! /* -------------------------------------------------------------------------- */
! static void usbhid_open(t_usbhid *x, t_symbol *vendor_id_hex, t_symbol *product_id_hex)
! {
! 	if(x->debug_level) post("usbhid_open");
! 	char string_buffer[STRING_BUFFER_LENGTH];
! 
! 	if( init_libhid(x) != HID_RET_SUCCESS ) return;
! 
! /* convert hex symbols to ints */
! 	x->vendor_id = (unsigned short) strtol(vendor_id_hex->s_name, NULL, 16);
! 	x->product_id = (unsigned short) strtol(product_id_hex->s_name, NULL, 16);
!  	if( hid_is_opened(x->x_hidinterface) ) 
  	{
+ 		if( (x->vendor_id == x->x_hidinterface->device->descriptor.idVendor) &&
+ 			(x->product_id == x->x_hidinterface->device->descriptor.idProduct))
+ 		{
+ 			post("[usbhid] device already opened");
+ 			return;
+ 		}
+ 		else
+ 		{
+ 			usbhid_close(x);
+ 		}
+ 	}
+ 
+  	if( !hid_is_opened(x->x_hidinterface) ) 
+ 	{
+ 		HIDInterfaceMatcher matcher = { x->vendor_id, 
+ 										x->product_id, 
+ 										NULL, 
+ 										NULL, 
+ 										0 };
  		x->x_hid_return = hid_force_open(x->x_hidinterface, 0, &matcher, 3);
  		if (x->x_hid_return == HID_RET_SUCCESS) 
***************
*** 331,338 ****
  			if (get_device_string(x->x_hidinterface,string_buffer))
  				post("[usbhid]: opened %s",string_buffer);
  		}
  		else
  		{
! 			error("[usbhid] hid_force_open failed with return code %d\n", x->x_hid_return);
  		}
  	}
--- 418,430 ----
  			if (get_device_string(x->x_hidinterface,string_buffer))
  				post("[usbhid]: opened %s",string_buffer);
+ 			reset_output(x);
+ 			add_float_to_output(x,1);
+ 			outlet_anything(x->x_status_outlet, gensym("open"), 
+ 							x->output_count, x->output);
  		}
  		else
  		{
! 			error("[usbhid] hid_force_open failed with return code %d\n", 
! 				  x->x_hid_return);
  		}
  	}
***************
*** 340,381 ****
  
  
  
  /* -------------------------------------------------------------------------- */
! static void usbhid_read(t_usbhid *x,t_float length_arg)
  {
! 	DEBUG(post("usbhid_read"););
! /* int const PATH_IN[PATH_LENGTH] = { 0xffa00001, 0xffa00002, 0xffa10003 }; */
! //	int const PATH_OUT[3] = { 0x00010002, 0x00010001, 0x00010030 };
  	int i;
  	int packet_bytes = (int)length_arg;
- 	t_atom *temp_atom = getbytes(sizeof(t_atom));
- 		
  	char packet[packet_bytes];
  
   	if ( !hid_is_opened(x->x_hidinterface) )
  	{
! //		usbhid_open(x);
  		return;
  	}
  	x->x_hid_return = hid_get_input_report(x->x_hidinterface, 
! 										   x->x_read_elements, 
  										   x->x_read_element_count, 
  										   packet, 
  										   length_arg);
  	if (x->x_hid_return != HID_RET_SUCCESS) 
  		error("[usbhid] hid_get_input_report failed with return code %d\n", 
  			  x->x_hid_return);
  
  	reset_output(x);
  	for(i=0; i<packet_bytes; ++i)
! 	{
! 		SETFLOAT(temp_atom,packet[i]);
! 		add_atom_to_output(x,temp_atom);
! 	}
  	outlet_list(x->x_data_outlet, &s_list, x->output_count, x->output);
! 	
  }
  
  
  
  
--- 432,509 ----
  
  
+ /* -------------------------------------------------------------------------- */
+ static void usbhid_set(t_usbhid *x, t_float length_arg)
+ {
+ 	if(x->debug_level) post("usbhid_set");
+ 	int packet_bytes = (int)length_arg;
+ 	char packet[packet_bytes];
+ 
+  	if ( !hid_is_opened(x->x_hidinterface) )
+ 	{
+ 		error("[usbhid] device not open, can't set data");
+ 		return;
+ 	}
+ 	x->x_hid_return = hid_set_output_report(x->x_hidinterface, 
+ 										   x->x_write_elements, 
+ 										   x->x_write_element_count, 
+ 										   packet, 
+ 										   length_arg);
+ 	if (x->x_hid_return != HID_RET_SUCCESS) 
+ 	{
+ 		error("[usbhid] hid_get_input_report failed with return code %d\n", 
+ 			  x->x_hid_return);
+ 		reset_output(x);
+ 		add_float_to_output(x, x->x_hid_return);
+ 		outlet_anything(x->x_status_outlet, gensym("setError"), 
+ 						x->output_count, x->output);
+ 	}
+ }
  
  /* -------------------------------------------------------------------------- */
! static void usbhid_get(t_usbhid *x, t_float length_arg)
  {
! 	if(x->debug_level) post("usbhid_get");
  	int i;
  	int packet_bytes = (int)length_arg;
  	char packet[packet_bytes];
  
   	if ( !hid_is_opened(x->x_hidinterface) )
  	{
! 		error("[usbhid] device not open, can't get data");
  		return;
  	}
  	x->x_hid_return = hid_get_input_report(x->x_hidinterface, 
! 										   NULL, 
  										   x->x_read_element_count, 
  										   packet, 
  										   length_arg);
  	if (x->x_hid_return != HID_RET_SUCCESS) 
+ 	{
  		error("[usbhid] hid_get_input_report failed with return code %d\n", 
  			  x->x_hid_return);
+ 		reset_output(x);
+ 		add_float_to_output(x, x->x_hid_return);
+ 		outlet_anything(x->x_status_outlet, gensym("getError"), 
+ 						x->output_count, x->output);
+ 	}
  
  	reset_output(x);
  	for(i=0; i<packet_bytes; ++i)
! 		add_float_to_output(x,packet[i]);
  	outlet_list(x->x_data_outlet, &s_list, x->output_count, x->output);
! 	post("x->x_read_elements %d",x->x_read_elements);
  }
  
  
+ /* -------------------------------------------------------------------------- */
+ /* reinit libhid to get update the list of attached devices */
+ static void usbhid_refresh(t_usbhid *x)
+ {
+ 	x->x_hid_return = hid_cleanup();
+ 	if (x->x_hid_return != HID_RET_SUCCESS) 
+ 		error("[usbhid] hid_cleanup failed with return code %d\n", 
+ 			  x->x_hid_return);
+ 	if( init_libhid(x) != HID_RET_SUCCESS ) return;
+ }
  
  
***************
*** 384,388 ****
  static void usbhid_set_read(t_usbhid *x, int argc, t_atom *argv)
  {
! 	DEBUG(post("usbhid_set_read"););
  	t_int i;
  
--- 512,516 ----
  static void usbhid_set_read(t_usbhid *x, int argc, t_atom *argv)
  {
! 	if(x->debug_level) post("usbhid_set_read");
  	t_int i;
  
***************
*** 396,403 ****
  
  /* -------------------------------------------------------------------------- */
  /* set the HID packet for which elements to write */
! static void usbhid_set_write(t_usbhid *x, int argc, t_atom *argv)
  {
! 	DEBUG(post("usbhid_set_write"););
  	t_int i;
  
--- 524,534 ----
  
  /* -------------------------------------------------------------------------- */
+ /* convert a list to a HID packet and set it */
  /* set the HID packet for which elements to write */
! static void usbhid_set_descriptor(t_usbhid *x, int argc, t_atom *argv)
  {
! 	if(x->debug_level) post("usbhid_descriptor");
! /* int const PATH_IN[PATH_LENGTH] = { 0xffa00001, 0xffa00002, 0xffa10003 }; */
! //	int const PATH_OUT[3] = { 0x00010002, 0x00010001, 0x00010030 };
  	t_int i;
  
***************
*** 412,532 ****
  
  /* -------------------------------------------------------------------------- */
! /* convert a list to a HID packet and set it */
! static void usbhid_set(t_usbhid *x, t_symbol *s, int argc, t_atom *argv)
! {
! 	DEBUG(post("usbhid_set"););
! 	t_symbol *subselector;
! 
! 	if(argc)
! 	{
! 		subselector = atom_getsymbol(&argv[0]);
! 		if(strcmp(subselector->s_name,"read") == 0)
! 			usbhid_set_read(x,argc-1,argv+1); 
! 		if(strcmp(subselector->s_name,"write") == 0)
! 			usbhid_set_write(x,argc-1,argv+1);
! 	}
! }
! 
! 
! /* -------------------------------------------------------------------------- */
! static void usbhid_get(t_usbhid *x, t_symbol *s, int argc, t_atom *argv)
  {
! 	DEBUG(post("usbhid_get"););
! 	t_symbol *subselector;
  	unsigned int i = 0;
! 	t_atom *temp_atom = getbytes(sizeof(t_atom));
! 	
  	if (!hid_is_opened(x->x_hidinterface)) {
  		error("[usbget] cannot dump tree of unopened HIDinterface.");
  	}
! 	else if(argc)
  	{
! 		subselector = atom_getsymbol(&argv[0]);
! 		
! 		if(strcmp(subselector->s_name,"read") == 0) 
! 		{
! 			post("[usbhid] parse tree of HIDInterface %s:\n", x->x_hidinterface->id);
! 			reset_output(x);
! 			while (HIDParse(x->x_hidinterface->hid_parser, x->x_hidinterface->hid_data)) {
! 				switch(x->x_hidinterface->hid_data->Type)
! 				{
! 				case 0x80: SETSYMBOL(temp_atom, gensym("input")); break;
! 				case 0x90: SETSYMBOL(temp_atom, gensym("output")); break;
! 				case 0xb0: SETSYMBOL(temp_atom, gensym("feature")); break;
! 				default: SETSYMBOL(temp_atom, gensym("UNKNOWN_TYPE"));
! 				}
! 				add_atom_to_output(x,temp_atom);
! 				SETFLOAT(temp_atom, x->x_hidinterface->hid_data->Size);
! 				add_atom_to_output(x,temp_atom);
! 				SETFLOAT(temp_atom, x->x_hidinterface->hid_data->Offset);
! 				add_atom_to_output(x,temp_atom);
! 				SETSYMBOL(temp_atom, gensym("path"));
! 				add_atom_to_output(x,temp_atom);
! 				for (i = 0; i < x->x_hidinterface->hid_data->Path.Size; ++i) {
! 					SETSYMBOL(temp_atom, gensym("usage"));
! 					add_atom_to_output(x,temp_atom);
! 					SETFLOAT(temp_atom, x->x_hidinterface->hid_data->Path.Node[i].UPage);
! 					add_atom_to_output(x,temp_atom);
! 					SETFLOAT(temp_atom, x->x_hidinterface->hid_data->Path.Node[i].Usage);
! 					add_atom_to_output(x,temp_atom);
! 					post("page: 0x%04x\t%d\t\tusage: 0x%04x\t%d",
! 							x->x_hidinterface->hid_data->Path.Node[i].UPage,
! 							x->x_hidinterface->hid_data->Path.Node[i].UPage,
! 							x->x_hidinterface->hid_data->Path.Node[i].Usage,
! 							x->x_hidinterface->hid_data->Path.Node[i].Usage);
! 				}
! 				post("type: 0x%02x\n", x->x_hidinterface->hid_data->Type);
! 				SETSYMBOL(temp_atom, gensym("logical"));
! 				add_atom_to_output(x,temp_atom);
! 				SETFLOAT(temp_atom, x->x_hidinterface->hid_data->LogMin);
! 				add_atom_to_output(x,temp_atom);
! 				SETFLOAT(temp_atom, x->x_hidinterface->hid_data->LogMax);
! 				add_atom_to_output(x,temp_atom);
  			}
! 			outlet_anything(x->x_control_outlet, gensym("device"), 
! 							x->output_count, x->output);
! 		}
! 		
! 		if(strcmp(subselector->s_name,"write") == 0) 
! 		{
  		}
! 	}
! 	else
! 	{
! 		error("[usbhid] must specify \"read\" or \"write\" as first element of %s message",s->s_name);
  	}
  }
  
- 
  /* -------------------------------------------------------------------------- */
! static void usbhid_close(t_usbhid *x) 
  {
! 	DEBUG(post("usbhid_close"););
! 	t_int ret;
! 	char string_buffer[STRING_BUFFER_LENGTH];
! 
! /* just to be safe, stop it first */
! //	usbhid_stop(x);
! 
! 	if ( hid_is_opened(x->x_hidinterface) ) 
  	{
! 		ret = get_device_string(x->x_hidinterface,string_buffer);
! 		x->x_hid_return = hid_close(x->x_hidinterface);
! 		if (x->x_hid_return == HID_RET_SUCCESS) 
! 		{
! 			if (ret) post("[usbhid]: closed %s",string_buffer);
! 		}
  		else
! 		{
! 			error("[usbhid] could not close %d, error #%d",x->x_device_number,x->x_hid_return);
! 		}
  	}
  }
  
- 
  /* -------------------------------------------------------------------------- */
  static void usbhid_print(t_usbhid *x)
  {
! 	DEBUG(post("usbhid_print"););
  	t_int i;
  	char string_buffer[STRING_BUFFER_LENGTH];
--- 543,621 ----
  
  /* -------------------------------------------------------------------------- */
! static void usbhid_get_descriptor(t_usbhid *x)
  {
! 	if(x->debug_level) post("usbhid_get");
  	unsigned int i = 0;
! 	t_int input_size = 0;
! 	t_int output_size = 0;
! 	t_int feature_size = 0;
! 
  	if (!hid_is_opened(x->x_hidinterface)) {
  		error("[usbget] cannot dump tree of unopened HIDinterface.");
  	}
! 	else 
  	{
! 		post("[usbhid] parse tree of HIDInterface %s:\n", x->x_hidinterface->id);
! 		reset_output(x);
! 		while (HIDParse(x->x_hidinterface->hid_parser, x->x_hidinterface->hid_data)) {
! 			add_symbol_to_output(x, gensym("path"));
! 			switch(x->x_hidinterface->hid_data->Type)
! 			{
! 			case 0x80: 
! 				add_symbol_to_output(x, gensym("input")); 
! 				input_size = input_size + x->x_hidinterface->hid_data->Size;
! 				break;
! 			case 0x90: 
! 				add_symbol_to_output(x, gensym("output")); 
! 				output_size = output_size + x->x_hidinterface->hid_data->Size;
! 				break;
! 			case 0xb0: 
! 				add_symbol_to_output(x, gensym("feature")); 
! 				feature_size = feature_size + x->x_hidinterface->hid_data->Size;
! 				break;
! 			default: add_symbol_to_output(x, gensym("UNKNOWN_TYPE"));
  			}
! 			add_float_to_output(x, x->x_hidinterface->hid_data->Size);
! 			add_float_to_output(x, x->x_hidinterface->hid_data->Offset);
! 			for (i = 0; i < x->x_hidinterface->hid_data->Path.Size; ++i) {
! 				add_symbol_to_output(x, gensym("usage"));
! 				add_float_to_output(x, x->x_hidinterface->hid_data->Path.Node[i].UPage);
! 				add_float_to_output(x, x->x_hidinterface->hid_data->Path.Node[i].Usage);
! 				post("page: 0x%04x\t%d\t\tusage: 0x%04x\t%d",
! 					 x->x_hidinterface->hid_data->Path.Node[i].UPage,
! 					 x->x_hidinterface->hid_data->Path.Node[i].UPage,
! 					 x->x_hidinterface->hid_data->Path.Node[i].Usage,
! 					 x->x_hidinterface->hid_data->Path.Node[i].Usage);
! 			}
! 			post("type: 0x%02x\n", x->x_hidinterface->hid_data->Type);
! 			add_symbol_to_output(x, gensym("logical"));
! 			add_float_to_output(x, x->x_hidinterface->hid_data->LogMin);
! 			add_float_to_output(x, x->x_hidinterface->hid_data->LogMax);
  		}
! 		add_symbol_to_output(x, gensym("totalSize"));
! 		add_float_to_output(x, input_size);
! 		add_float_to_output(x, output_size);
! 		add_float_to_output(x, feature_size);
! 		outlet_anything(x->x_status_outlet, gensym("device"), 
! 						x->output_count, x->output);
  	}
  }
  
  /* -------------------------------------------------------------------------- */
! static void usbhid_descriptor(t_usbhid *x, t_symbol *s, int argc, t_atom *argv)
  {
! 	if(s == gensym("descriptor")) // get rid of unused s warning
  	{
! 		if(argc)
! 			usbhid_set_descriptor(x,argc,argv);
  		else
! 			usbhid_get_descriptor(x);
  	}
  }
  
  /* -------------------------------------------------------------------------- */
  static void usbhid_print(t_usbhid *x)
  {
! 	if(x->debug_level) post("usbhid_print");
  	t_int i;
  	char string_buffer[STRING_BUFFER_LENGTH];
***************
*** 538,542 ****
  			post("hid_id[%d]: %s",i,hid_id[i]);
  	}
! 	if (get_device_string(x->x_hidinterface,string_buffer))
  		post("%s is currently open",string_buffer);
  
--- 627,631 ----
  			post("hid_id[%d]: %s",i,hid_id[i]);
  	}
! 	if(get_device_string(x->x_hidinterface,string_buffer))
  		post("%s is currently open",string_buffer);
  
***************
*** 550,554 ****
  /* 	SETSYMBOL(event_data + 1, gensym(code));	/\* code *\/ */
  /* 	SETSYMBOL(event_data + 2, value);	         /\* value *\/ */
! //	outlet_list(x->x_control_outlet, &s_list,
  }
  
--- 639,643 ----
  /* 	SETSYMBOL(event_data + 1, gensym(code));	/\* code *\/ */
  /* 	SETSYMBOL(event_data + 2, value);	         /\* value *\/ */
! //	outlet_list(x->x_status_outlet, &s_list,
  }
  
***************
*** 557,565 ****
  static void usbhid_reset(t_usbhid *x)
  {
! 	DEBUG(post("usbhid_reset"););
  	
  	hid_reset_HIDInterface(x->x_hidinterface);
  
! 	x->x_hid_return = hid_init();
  }
  
--- 646,673 ----
  static void usbhid_reset(t_usbhid *x)
  {
! 	if(x->debug_level) post("usbhid_reset");
  	
  	hid_reset_HIDInterface(x->x_hidinterface);
+ }
  
! 
! /* -------------------------------------------------------------------------- */
! static void usbhid_debug(t_usbhid *x, t_float f)
! {
! 	x->debug_level = f;
! 	
! 	switch(x->debug_level)
! 	{
! 	case 0: hid_set_usb_debug(0); hid_set_debug(HID_DEBUG_NONE); break;
! 	case 1: hid_set_usb_debug(0); hid_set_debug(HID_DEBUG_ERRORS); break;
! 	case 2: hid_set_usb_debug(0); 
! 		hid_set_debug(HID_DEBUG_ERRORS | HID_DEBUG_WARNINGS); break;
! 	case 3: hid_set_usb_debug(0); 
! 		hid_set_debug(HID_DEBUG_ERRORS | HID_DEBUG_WARNINGS | HID_DEBUG_NOTICES); break;
! 	case 4: hid_set_usb_debug(0); hid_set_debug(HID_DEBUG_NOTRACES); break;
! 	case 5: hid_set_usb_debug(0); hid_set_debug(HID_DEBUG_ALL); break;
! 	default:
! 		hid_set_usb_debug(x->debug_level - 5); hid_set_debug(HID_DEBUG_ALL); break;
! 	}
  }
  
***************
*** 568,583 ****
  static void usbhid_free(t_usbhid* x) 
  {
! 	DEBUG(post("usbhid_free"););
  		
  	usbhid_close(x);
- 	clock_free(x->x_clock);
  
  	freebytes(x->x_read_elements,sizeof(t_int) * x->x_read_element_count);
  	freebytes(x->x_write_elements,sizeof(t_int) * x->x_write_element_count);
  
  	hid_delete_HIDInterface(&(x->x_hidinterface));
! 	x->x_hid_return = hid_cleanup();
! 	if (x->x_hid_return != HID_RET_SUCCESS) 
! 		error("[usbhid] hid_cleanup failed with return code %d\n", x->x_hid_return);
  
  	usbhid_instance_count--;
--- 676,697 ----
  static void usbhid_free(t_usbhid* x) 
  {
! 	if(x->debug_level) post("usbhid_free");
  		
  	usbhid_close(x);
  
  	freebytes(x->x_read_elements,sizeof(t_int) * x->x_read_element_count);
  	freebytes(x->x_write_elements,sizeof(t_int) * x->x_write_element_count);
  
+ 	if(x->debug_level) 
+ 		post("[usbhid] freeing instance %d",usbhid_instance_count);
  	hid_delete_HIDInterface(&(x->x_hidinterface));
! 	if(usbhid_instance_count <= 1)
! 	{
! 		post("[usbhid] freeing last instance");
! 		x->x_hid_return = hid_cleanup();
! 		if (x->x_hid_return != HID_RET_SUCCESS) 
! 			error("[usbhid] hid_cleanup failed with return code %d\n", 
! 				  x->x_hid_return);
! 	}
  
  	usbhid_instance_count--;
***************
*** 593,597 ****
  	t_usbhid *x = (t_usbhid *)pd_new(usbhid_class);
  	
! 	DEBUG(post("usbhid_new"););
  	
  /* only display the version when the first instance is loaded */
--- 707,711 ----
  	t_usbhid *x = (t_usbhid *)pd_new(usbhid_class);
  	
! 	if(x->debug_level) post("usbhid_new");
  	
  /* only display the version when the first instance is loaded */
***************
*** 600,613 ****
  			 USBHID_MAJOR_VERSION, USBHID_MINOR_VERSION);  
  	
- /*   x->x_clock = clock_new(x, (t_method)usbhid_read); */
- 
  	/* create anything outlet used for HID data */ 
  	x->x_data_outlet = outlet_new(&x->x_obj, 0);
! 	x->x_control_outlet = outlet_new(&x->x_obj, 0);
! 	
! 	/* hid_write_library_config(stdout); */
! 	//hid_set_debug(HID_DEBUG_NONE);
! 	hid_set_debug(HID_DEBUG_NOTRACES);
!  	//hid_set_debug(HID_DEBUG_ALL); 
  	hid_set_debug_stream(stdout);
  	hid_set_usb_debug(0);
--- 714,723 ----
  			 USBHID_MAJOR_VERSION, USBHID_MINOR_VERSION);  
  	
  	/* create anything outlet used for HID data */ 
  	x->x_data_outlet = outlet_new(&x->x_obj, 0);
! 	x->x_status_outlet = outlet_new(&x->x_obj, 0);
! 
! 	/* turn off the flood of libhid debug messages by default */
! 	hid_set_debug(HID_DEBUG_NONE);
  	hid_set_debug_stream(stdout);
  	hid_set_usb_debug(0);
***************
*** 618,624 ****
  	for (i = 0 ; i < HID_ID_MAX ; i++)
  		hid_id[i] = NULL;
- 
- 	if (! hid_is_initialised() )
- 		x->x_hid_return = hid_init();
  	
  	x->x_hidinterface = hid_new_HIDInterface();
--- 728,731 ----
***************
*** 629,651 ****
  	x->x_device_number = f;
  
! 	/* find and report the list of devices */
! 	/* open recursively all HID devices found */
! 	while ( (x->x_hid_return = hid_force_open(x->x_hidinterface, 0, &matcher, 2)) != HID_RET_DEVICE_NOT_FOUND)
! 	{
! /* 		printf("************************************************************************\n"); */
! 		
! /* 		hid_write_identification(stdout, x->x_hidinterface); */
! 		
! 		/* Only dump HID tree if asked */
! 		/* hid_dump_tree(stdout, x->x_hidinterface); */
! 		
! 		hid_close(x->x_hidinterface);
! 	}
! 	
! 
!   
! 	/* Open the device and save settings.  If there is an error, return the object
! 	 * anyway, so that the inlets and outlets are created, thus not breaking the
! 	 * patch.   */
  /* 	if (usbhid_open(x,f)) */
  /* 		error("[usbhid] device %d did not open",(t_int)f); */
--- 736,742 ----
  	x->x_device_number = f;
  
! /* Open the device and save settings.  If there is an error, return the object
!  * anyway, so that the inlets and outlets are created, thus not breaking the
!  * patch.   */
  /* 	if (usbhid_open(x,f)) */
  /* 		error("[usbhid] device %d did not open",(t_int)f); */
***************
*** 658,662 ****
  void usbhid_setup(void) 
  {
- 	DEBUG(post("usbhid_setup"););
  	usbhid_class = class_new(gensym("usbhid"), 
  							 (t_newmethod)usbhid_new, 
--- 749,752 ----
***************
*** 673,680 ****
  	class_addmethod(usbhid_class,(t_method) usbhid_print,gensym("print"),0);
  	class_addmethod(usbhid_class,(t_method) usbhid_reset,gensym("reset"),0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_read,gensym("read"),A_DEFFLOAT,0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_set,gensym("set"),A_GIMME,0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_get,gensym("get"),A_GIMME,0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_open,gensym("open"),A_DEFFLOAT,A_DEFFLOAT,0);
  	class_addmethod(usbhid_class,(t_method) usbhid_close,gensym("close"),0);
  }
--- 763,777 ----
  	class_addmethod(usbhid_class,(t_method) usbhid_print,gensym("print"),0);
  	class_addmethod(usbhid_class,(t_method) usbhid_reset,gensym("reset"),0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_refresh,gensym("refresh"),0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_debug,gensym("debug"),
! 					A_DEFFLOAT,0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_descriptor,gensym("descriptor"),
! 					A_GIMME,0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_set,gensym("set"),
! 					A_DEFFLOAT,0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_get,gensym("get"),
! 					A_DEFFLOAT,0);
! 	class_addmethod(usbhid_class,(t_method) usbhid_open,gensym("open"),
! 					A_DEFSYM,A_DEFSYM,0);
  	class_addmethod(usbhid_class,(t_method) usbhid_close,gensym("close"),0);
  }





More information about the Pd-cvs mailing list