machine/usb: allow USB Endpoint settings to be changed externally
Этот коммит содержится в:
родитель
d1eb642d45
коммит
069e4f0d98
5 изменённых файлов: 130 добавлений и 46 удалений
|
@ -263,47 +263,52 @@ func EnableCDC(txHandler func(), rxHandler func([]byte), setupHandler func(usb.S
|
||||||
usbDescriptor = descriptor.CDC
|
usbDescriptor = descriptor.CDC
|
||||||
}
|
}
|
||||||
// Initialization of endpoints is required even for non-CDC
|
// Initialization of endpoints is required even for non-CDC
|
||||||
endPoints[usb.CDC_ENDPOINT_ACM] = (usb.ENDPOINT_TYPE_INTERRUPT | usb.EndpointIn)
|
ConfigureUSBEndpoint(usbDescriptor,
|
||||||
endPoints[usb.CDC_ENDPOINT_OUT] = (usb.ENDPOINT_TYPE_BULK | usb.EndpointOut)
|
[]usb.EndpointConfig{
|
||||||
endPoints[usb.CDC_ENDPOINT_IN] = (usb.ENDPOINT_TYPE_BULK | usb.EndpointIn)
|
{
|
||||||
usbRxHandler[usb.CDC_ENDPOINT_OUT] = rxHandler
|
No: usb.CDC_ENDPOINT_ACM,
|
||||||
usbTxHandler[usb.CDC_ENDPOINT_IN] = txHandler
|
IsIn: true,
|
||||||
usbSetupHandler[usb.CDC_ACM_INTERFACE] = setupHandler // 0x02 (Communications and CDC Control)
|
Type: usb.ENDPOINT_TYPE_INTERRUPT,
|
||||||
usbSetupHandler[usb.CDC_DATA_INTERFACE] = nil // 0x0A (CDC-Data)
|
},
|
||||||
|
{
|
||||||
|
No: usb.CDC_ENDPOINT_OUT,
|
||||||
|
IsIn: false,
|
||||||
|
Type: usb.ENDPOINT_TYPE_BULK,
|
||||||
|
RxHandler: rxHandler,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
No: usb.CDC_ENDPOINT_IN,
|
||||||
|
IsIn: true,
|
||||||
|
Type: usb.ENDPOINT_TYPE_BULK,
|
||||||
|
TxHandler: txHandler,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
[]usb.SetupConfig{
|
||||||
|
{
|
||||||
|
No: usb.CDC_ACM_INTERFACE,
|
||||||
|
Handler: setupHandler,
|
||||||
|
},
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
// EnableHID enables HID. This function must be executed from the init().
|
func ConfigureUSBEndpoint(desc descriptor.Descriptor, epSettings []usb.EndpointConfig, setup []usb.SetupConfig) {
|
||||||
func EnableHID(txHandler func(), rxHandler func([]byte), setupHandler func(usb.Setup) bool) {
|
usbDescriptor = desc
|
||||||
usbDescriptor = descriptor.CDCHID
|
|
||||||
endPoints[usb.HID_ENDPOINT_IN] = (usb.ENDPOINT_TYPE_INTERRUPT | usb.EndpointIn)
|
|
||||||
usbTxHandler[usb.HID_ENDPOINT_IN] = txHandler
|
|
||||||
usbSetupHandler[usb.HID_INTERFACE] = setupHandler // 0x03 (HID - Human Interface Device)
|
|
||||||
}
|
|
||||||
|
|
||||||
// EnableMIDI enables MIDI. This function must be executed from the init().
|
for _, ep := range epSettings {
|
||||||
func EnableMIDI(txHandler func(), rxHandler func([]byte), setupHandler func(usb.Setup) bool) {
|
if ep.IsIn {
|
||||||
usbDescriptor = descriptor.CDCMIDI
|
endPoints[ep.No] = uint32(ep.Type | usb.EndpointIn)
|
||||||
endPoints[usb.MIDI_ENDPOINT_OUT] = (usb.ENDPOINT_TYPE_BULK | usb.EndpointOut)
|
if ep.TxHandler != nil {
|
||||||
endPoints[usb.MIDI_ENDPOINT_IN] = (usb.ENDPOINT_TYPE_BULK | usb.EndpointIn)
|
usbTxHandler[ep.No] = ep.TxHandler
|
||||||
usbRxHandler[usb.MIDI_ENDPOINT_OUT] = rxHandler
|
}
|
||||||
usbTxHandler[usb.MIDI_ENDPOINT_IN] = txHandler
|
} else {
|
||||||
}
|
endPoints[ep.No] = uint32(ep.Type | usb.EndpointOut)
|
||||||
|
if ep.RxHandler != nil {
|
||||||
// EnableJoystick enables HID. This function must be executed from the init().
|
usbRxHandler[ep.No] = ep.RxHandler
|
||||||
func EnableJoystick(txHandler func(), rxHandler func([]byte), setupHandler func(usb.Setup) bool, hidDesc []byte) {
|
}
|
||||||
class, err := descriptor.FindClassHIDType(descriptor.CDCJoystick.Configuration, descriptor.ClassHIDJoystick.Bytes())
|
}
|
||||||
if err != nil {
|
|
||||||
// TODO: some way to notify about error
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class.ClassLength(uint16(len(hidDesc)))
|
for _, s := range setup {
|
||||||
descriptor.CDCJoystick.HID[2] = hidDesc
|
usbSetupHandler[s.No] = s.Handler
|
||||||
|
}
|
||||||
usbDescriptor = descriptor.CDCJoystick
|
|
||||||
endPoints[usb.HID_ENDPOINT_OUT] = (usb.ENDPOINT_TYPE_INTERRUPT | usb.EndpointOut)
|
|
||||||
usbRxHandler[usb.HID_ENDPOINT_OUT] = rxHandler
|
|
||||||
endPoints[usb.HID_ENDPOINT_IN] = (usb.ENDPOINT_TYPE_INTERRUPT | usb.EndpointIn)
|
|
||||||
usbTxHandler[usb.HID_ENDPOINT_IN] = txHandler
|
|
||||||
usbSetupHandler[usb.HID_INTERFACE] = setupHandler // 0x03 (HID - Human Interface Device)
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@ package midi
|
||||||
import (
|
import (
|
||||||
"machine"
|
"machine"
|
||||||
"machine/usb"
|
"machine/usb"
|
||||||
|
"machine/usb/descriptor"
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
@ -40,7 +41,23 @@ func newMidi() *midi {
|
||||||
m := &midi{
|
m := &midi{
|
||||||
buf: NewRingBuffer(),
|
buf: NewRingBuffer(),
|
||||||
}
|
}
|
||||||
machine.EnableMIDI(m.Handler, m.RxHandler, nil)
|
machine.ConfigureUSBEndpoint(descriptor.CDCMIDI,
|
||||||
|
[]usb.EndpointConfig{
|
||||||
|
{
|
||||||
|
No: usb.MIDI_ENDPOINT_OUT,
|
||||||
|
IsIn: false,
|
||||||
|
Type: usb.ENDPOINT_TYPE_BULK,
|
||||||
|
RxHandler: m.RxHandler,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
No: usb.MIDI_ENDPOINT_IN,
|
||||||
|
IsIn: true,
|
||||||
|
Type: usb.ENDPOINT_TYPE_BULK,
|
||||||
|
TxHandler: m.Handler,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
[]usb.SetupConfig{},
|
||||||
|
)
|
||||||
return m
|
return m
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
14
src/machine/usb/config.go
Обычный файл
14
src/machine/usb/config.go
Обычный файл
|
@ -0,0 +1,14 @@
|
||||||
|
package usb
|
||||||
|
|
||||||
|
type EndpointConfig struct {
|
||||||
|
No uint8
|
||||||
|
IsIn bool
|
||||||
|
TxHandler func()
|
||||||
|
RxHandler func([]byte)
|
||||||
|
Type uint8
|
||||||
|
}
|
||||||
|
|
||||||
|
type SetupConfig struct {
|
||||||
|
No uint8
|
||||||
|
Handler func(Setup) bool
|
||||||
|
}
|
|
@ -4,6 +4,7 @@ import (
|
||||||
"errors"
|
"errors"
|
||||||
"machine"
|
"machine"
|
||||||
"machine/usb"
|
"machine/usb"
|
||||||
|
"machine/usb/descriptor"
|
||||||
)
|
)
|
||||||
|
|
||||||
// from usb-hid.go
|
// from usb-hid.go
|
||||||
|
@ -32,7 +33,21 @@ var size int
|
||||||
// calls machine.EnableHID for USB configuration
|
// calls machine.EnableHID for USB configuration
|
||||||
func SetHandler(d hidDevicer) {
|
func SetHandler(d hidDevicer) {
|
||||||
if size == 0 {
|
if size == 0 {
|
||||||
machine.EnableHID(handler, nil, setupHandler)
|
machine.ConfigureUSBEndpoint(descriptor.CDCHID,
|
||||||
|
[]usb.EndpointConfig{
|
||||||
|
{
|
||||||
|
No: usb.HID_ENDPOINT_IN,
|
||||||
|
IsIn: true,
|
||||||
|
Type: usb.ENDPOINT_TYPE_INTERRUPT,
|
||||||
|
TxHandler: handler,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
[]usb.SetupConfig{
|
||||||
|
{
|
||||||
|
No: usb.HID_INTERFACE,
|
||||||
|
Handler: setupHandler,
|
||||||
|
},
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
devices[size] = d
|
devices[size] = d
|
||||||
|
|
|
@ -3,6 +3,7 @@ package joystick
|
||||||
import (
|
import (
|
||||||
"machine"
|
"machine"
|
||||||
"machine/usb"
|
"machine/usb"
|
||||||
|
"machine/usb/descriptor"
|
||||||
"machine/usb/hid"
|
"machine/usb/hid"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -32,18 +33,50 @@ func UseSettings(def Definitions, rxHandlerFunc func(b []byte), setupFunc func(s
|
||||||
if setupFunc == nil {
|
if setupFunc == nil {
|
||||||
setupFunc = hid.DefaultSetupHandler
|
setupFunc = hid.DefaultSetupHandler
|
||||||
}
|
}
|
||||||
machine.EnableJoystick(js.handler, rxHandlerFunc, setupFunc, hidDesc)
|
if rxHandlerFunc == nil {
|
||||||
|
rxHandlerFunc = js.rxHandlerFunc
|
||||||
|
}
|
||||||
|
if len(hidDesc) == 0 {
|
||||||
|
hidDesc = descriptor.JoystickDefaultHIDReport
|
||||||
|
}
|
||||||
|
class, err := descriptor.FindClassHIDType(descriptor.CDCJoystick.Configuration, descriptor.ClassHIDJoystick.Bytes())
|
||||||
|
if err != nil {
|
||||||
|
// TODO: some way to notify about error
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
class.ClassLength(uint16(len(hidDesc)))
|
||||||
|
descriptor.CDCJoystick.HID[2] = hidDesc
|
||||||
|
|
||||||
|
machine.ConfigureUSBEndpoint(descriptor.CDCJoystick,
|
||||||
|
[]usb.EndpointConfig{
|
||||||
|
{
|
||||||
|
No: usb.HID_ENDPOINT_OUT,
|
||||||
|
IsIn: false,
|
||||||
|
Type: usb.ENDPOINT_TYPE_INTERRUPT,
|
||||||
|
RxHandler: rxHandlerFunc,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
No: usb.HID_ENDPOINT_IN,
|
||||||
|
IsIn: true,
|
||||||
|
Type: usb.ENDPOINT_TYPE_INTERRUPT,
|
||||||
|
TxHandler: js.handler,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
[]usb.SetupConfig{
|
||||||
|
{
|
||||||
|
No: usb.HID_INTERFACE,
|
||||||
|
Handler: setupFunc,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
)
|
||||||
Joystick = js
|
Joystick = js
|
||||||
return js
|
return js
|
||||||
}
|
}
|
||||||
|
|
||||||
func newDefaultJoystick() *joystick {
|
func newDefaultJoystick() *joystick {
|
||||||
def := DefaultDefinitions()
|
def := DefaultDefinitions()
|
||||||
js := &joystick{
|
js := UseSettings(def, nil, nil, nil)
|
||||||
State: def.NewState(),
|
|
||||||
buf: hid.NewRingBuffer(),
|
|
||||||
}
|
|
||||||
machine.EnableJoystick(js.handler, js.rxHandler, hid.DefaultSetupHandler, def.Descriptor())
|
|
||||||
return js
|
return js
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Загрузка…
Создание таблицы
Сослаться в новой задаче