package usb // Device represents a USB device type Device struct { BusID string `json:"bus_id"` // e.g. "1-1.4" BusNum uint32 `json:"bus_num"` DevNum uint32 `json:"dev_num"` Speed uint32 `json:"speed"` VendorID uint16 `json:"vendor_id"` ProductID uint16 `json:"product_id"` BcdDevice uint16 `json:"bcd_device"` DeviceClass uint8 `json:"device_class"` DeviceSubClass uint8 `json:"device_sub_class"` DeviceProtocol uint8 `json:"device_protocol"` ConfigValue uint8 `json:"config_value"` NumConfigs uint8 `json:"num_configs"` Manufacturer string `json:"manufacturer"` Product string `json:"product"` Serial string `json:"serial"` SysPath string `json:"sys_path"` // sysfs path DevPath string `json:"dev_path"` // /dev/bus/usb path // Interfaces holds one entry per interface number at alternate setting 0. // These are the interfaces that get claimed when sharing the device. Interfaces []Interface `json:"interfaces"` // Endpoints holds every endpoint of the active configuration across all // alternate settings, keyed by full bEndpointAddress (direction bit // included). Endpoints that only exist in a non-zero alternate setting // are included, so the transfer type stays correct after SET_INTERFACE. Endpoints map[uint8]Endpoint `json:"endpoints"` } // Interface represents a USB interface at one alternate setting type Interface struct { Number uint8 `json:"number"` AltSetting uint8 `json:"alt_setting"` Class uint8 `json:"class"` SubClass uint8 `json:"sub_class"` Protocol uint8 `json:"protocol"` Driver string `json:"driver"` Endpoints []Endpoint `json:"endpoints"` } // Endpoint represents a USB endpoint type Endpoint struct { Address uint8 `json:"address"` // bEndpointAddress (bit 7=direction, bits 3:0=number) TransferType uint8 `json:"transfer_type"` // 0=control, 1=iso, 2=bulk, 3=interrupt MaxPacketSize uint16 `json:"max_packet_size"` Interval uint8 `json:"interval"` // bInterval } // IsIn reports whether this is an IN (device-to-host) endpoint. func (e Endpoint) IsIn() bool { return e.Address&0x80 != 0 } // Number returns the endpoint number without the direction bit. func (e Endpoint) Number() uint8 { return e.Address & 0x0F } // USB transfer types (from bmAttributes) const ( TransferTypeControl = 0 TransferTypeIsochronous = 1 TransferTypeBulk = 2 TransferTypeInterrupt = 3 ) // DevID returns the USB/IP device ID (busnum << 16 | devnum) func (d *Device) DevID() uint32 { return (d.BusNum << 16) | d.DevNum } // IsHub returns true if this is a USB hub func (d *Device) IsHub() bool { return d.DeviceClass == 9 } // DisplayName returns a human-readable device name func (d *Device) DisplayName() string { if d.Product != "" { if d.Manufacturer != "" { return d.Manufacturer + " " + d.Product } return d.Product } return "Unknown USB Device" }