@@ 38,6 38,29 @@ struct usb_class_header_t;
struct usb_device_t;
typedef struct usb_device_t usb_device_t;
+typedef enum {
+ PACKET_GLOBAL_OUT_NAK = 1,
+ PACKET_OUT_DATA_PACKET_RCVD = 2,
+ PACKET_OUT_TRANSFER_COMPLETED = 3,
+ PACKET_SETUP_TRANSACTION_COMPLETED = 4,
+ PACKET_SETUP_DATA_PACKET_RECEIVED = 6,
+} packet_status_t;
+
+typedef enum {
+ DATA0 = 0,
+ DATA1 = 1,
+ DATA2 = 2,
+ MDATA = 3
+} packet_dpid_t;
+
+typedef struct {
+ packet_status_t packet_status;
+ packet_dpid_t dpid;
+ uint8_t byte_count;
+ uint8_t endpoint_num;
+ uint8_t status_phase_start;
+} packet_info_t;
+
/**
* @struct usb_class_vtable_t
* A vtable struct for usb class,
@@ 125,12 148,22 @@ typedef struct {
void (*rxfifo_empty_callback)(usb_device_t* device, uint8_t endpoint);
/**
- * @brief Callback on transmission done - all data were sent from configured size.
+ * @brief Callback on tx transmission done - all data were sent from configured size.
* @param[in,out] device The usb device.
* @param[in] endpoint The number of the endpoint.
* @return Description
*/
- void (*transmit_done_callback)(usb_device_t* device, uint8_t endpoint);
+ void (*tx_done_callback)(usb_device_t* device, uint8_t endpoint);
+
+/**
+ * @brief Callback on rx transmission done - all data were sent from configured size.
+ * @param[in,out] device The usb device.
+ * @param[in] endpoint The number of the endpoint.
+ * @return Description
+ */
+ void (*rx_done_callback)(usb_device_t* device, uint8_t endpoint);
+
+ void (*received_data_callback)(usb_device_t* device, packet_info_t* packet);
/**
* @brief Callback on nak being effective.
@@ 130,29 130,6 @@ void usb_device_setup(void* device_ptr) {
/* while (((device->core->GINTSTS) & USB_OTG_GINTSTS_ENUMDNE) == 0) {} */
}
-typedef enum {
- PACKET_GLOBAL_OUT_NAK = 1,
- PACKET_OUT_DATA_PACKET_RCVD = 2,
- PACKET_OUT_TRANSFER_COMPLETED = 3,
- PACKET_SETUP_TRANSACTION_COMPLETED = 4,
- PACKET_SETUP_DATA_PACKET_RECEIVED = 6,
-} packet_status_t;
-
-typedef enum {
- DATA0 = 0,
- DATA1 = 1,
- DATA2 = 2,
- MDATA = 3
-} packet_dpid_t;
-
-typedef struct {
- packet_status_t packet_status;
- packet_dpid_t dpid;
- uint8_t byte_count;
- uint8_t endpoint_num;
- uint8_t status_phase_start;
-} packet_info_t;
-
task_result_t usb_handle_setup_command(usb_device_t *device, usb_setup_command_t* cmd) {
task_result_t result = RES_ERROR;
@@ 459,7 436,7 @@ void usb_handle_rxflvl_int(usb_device_t *device) {
if (packet_info.endpoint_num == 0) {
usb_handle_rxflvl_control_int(device, &packet_info);
} else {
- // TODO: ...
+ device->vt.received_data_callback(device, &packet_info);
}
}
@@ 544,7 521,7 @@ void usb_handle_endpoint_in_int(usb_device_t* device) {
if (interrupt_reg & USB_OTG_DIEPINT_XFRC) {
// Transfer is completed.
if (device->state == ENUMERATED) {
- device->vt.transmit_done_callback(device, ep_id);
+ device->vt.rx_done_callback(device, ep_id);
}
if (ep_id == 0) {
@@ 606,10 583,10 @@ void usb_handle_endpoint_out_int(usb_device_t* device) {
reg_clear_bits(&device->out[ep_id].DOEPINT, USB_OTG_DOEPINT_B2BSTUP);
}
if (interrupt_reg & USB_OTG_DOEPINT_OTEPSPR) {
- // This is valid only for DATA phases where the host sends us data.
- // Those are not supported yet! After they are, here is the place to
- // set STALL or send zero length packet.
- // TODO: ack or stall the status phase?
+ // TODO: is there someting to do? The data sending is usually handled prior
+ // to this, in handling of setup / data stages. Maybe it should be
+ // moved here instead, since it's possible other packet will be
+ // received in the meantime?
reg_clear_bits(&device->out[ep_id].DOEPINT, USB_OTG_DOEPINT_OTEPSPR);
}
if (interrupt_reg & USB_OTG_DOEPINT_OTEPDIS) {
@@ 633,7 610,7 @@ void usb_handle_endpoint_out_int(usb_device_t* device) {
device->out[0].DOEPCTL = USB_OTG_DOEPCTL_CNAK | USB_OTG_DOEPCTL_EPENA;
reg_clear_bits(&device->out[ep_id].DOEPINT, USB_OTG_DOEPINT_XFRC);
- // TODO: handle data? - callback to device data handle?
+ device->vt.rx_done_callback(device, ep_id);
if (ep_id == 0) {
usb_handle_setup(device, USB_GOT_ACK);
@@ 671,9 648,9 @@ void otg_hs_handler(void) {
device->device->DIEPMSK |= USB_OTG_DIEPMSK_XFRCM | USB_OTG_DIEPMSK_TOM | USB_OTG_DIEPEACHMSK1_NAKM | USB_OTG_DIEPEACHMSK1_INEPNEM;
// 512 bytes
- device->core->GRXFSIZ = 256 / 4;
+ device->core->GRXFSIZ = 1024 / 4;
// 64 bytes, beginning of ram
- device->core->DIEPTXF[0] = (0) << USB_OTG_TX0FSA_Pos | (128 / 4) << USB_OTG_TX0FD_Pos;
+ device->core->DIEPTXF[0] = (0 << USB_OTG_DIEPTXF_INEPTXSA_Pos) | ((128 / 4) << USB_OTG_DIEPTXF_INEPTXFD_Pos);
// 3 packets to receive as setup
reg_write_bits_pos(&device->out->DOEPTSIZ, 3, USB_OTG_DOEPTSIZ_STUPCNT_Pos, 3);
@@ 691,7 668,6 @@ void otg_hs_handler(void) {
// We do not need to know the speed, it can be either full speed or high
// speed, both have maximum size 64 bytes. Only low speed or super high
// speed would differ, but these are not supported!
- // TODO: does 0 mean 64 bits here??? This is NOT in the spec! It's in the spec only for out endpoint, not for the in one!!!
reg_write_bits_pos(&device->in[0].DIEPCTL, 0, USB_OTG_DIEPCTL_MPSIZ_Pos, 0x7FFUL);
device->in->DIEPCTL |= USB_OTG_DOEPCTL_SNAK;
@@ 728,7 704,6 @@ void otg_hs_handler(void) {
}
if (device->core->GINTSTS & (USB_OTG_GINTSTS_RXFLVL)) {
- // TODO
usb_handle_rxflvl_int(device);
return;
}