github.com/tinygo-org/tinygo@v0.31.3-0.20240404173401-90b0bf646c27/src/machine/usb/hid/hid.go (about) 1 package hid 2 3 import ( 4 "errors" 5 "machine" 6 "machine/usb" 7 "machine/usb/descriptor" 8 ) 9 10 // from usb-hid.go 11 var ( 12 ErrHIDInvalidPort = errors.New("invalid USB port") 13 ErrHIDInvalidCore = errors.New("invalid USB core") 14 ErrHIDReportTransfer = errors.New("failed to transfer HID report") 15 ) 16 17 const ( 18 hidEndpoint = usb.HID_ENDPOINT_IN 19 20 REPORT_TYPE_INPUT = 1 21 REPORT_TYPE_OUTPUT = 2 22 REPORT_TYPE_FEATURE = 3 23 ) 24 25 type hidDevicer interface { 26 TxHandler() bool 27 RxHandler([]byte) bool 28 } 29 30 var devices [5]hidDevicer 31 var size int 32 33 // SetHandler sets the handler. Only the first time it is called, it 34 // calls machine.EnableHID for USB configuration 35 func SetHandler(d hidDevicer) { 36 if size == 0 { 37 machine.ConfigureUSBEndpoint(descriptor.CDCHID, 38 []usb.EndpointConfig{ 39 { 40 Index: usb.HID_ENDPOINT_OUT, 41 IsIn: false, 42 Type: usb.ENDPOINT_TYPE_INTERRUPT, 43 RxHandler: rxHandler, 44 }, 45 { 46 Index: usb.HID_ENDPOINT_IN, 47 IsIn: true, 48 Type: usb.ENDPOINT_TYPE_INTERRUPT, 49 TxHandler: txHandler, 50 }, 51 }, 52 []usb.SetupConfig{ 53 { 54 Index: usb.HID_INTERFACE, 55 Handler: setupHandler, 56 }, 57 }) 58 } 59 60 devices[size] = d 61 size++ 62 } 63 64 func txHandler() { 65 for _, d := range devices { 66 if d == nil { 67 continue 68 } 69 if done := d.TxHandler(); done { 70 return 71 } 72 } 73 } 74 75 func rxHandler(b []byte) { 76 for _, d := range devices { 77 if d == nil { 78 continue 79 } 80 if done := d.RxHandler(b); done { 81 return 82 } 83 } 84 } 85 86 var DefaultSetupHandler = setupHandler 87 88 func setupHandler(setup usb.Setup) bool { 89 ok := false 90 if setup.BmRequestType == usb.SET_REPORT_TYPE && setup.BRequest == usb.SET_IDLE { 91 machine.SendZlp() 92 ok = true 93 } 94 return ok 95 } 96 97 // SendUSBPacket sends a HIDPacket. 98 func SendUSBPacket(b []byte) { 99 machine.SendUSBInPacket(hidEndpoint, b) 100 }