+#if AO_USB_DIRECTIO
+uint16_t *
+ao_usb_alloc(void)
+{
+ uint16_t *buffer;
+
+ if (!ao_usb_running)
+ return NULL;
+ buffer = ao_usb_packet_buffer_addr(ao_usb_sram_addr);
+ ao_usb_sram_addr += AO_USB_IN_SIZE;
+ return buffer;
+}
+
+void
+ao_usb_free(uint16_t *addr)
+{
+ uint16_t offset = ao_usb_packet_buffer_offset(addr);
+ if (offset < ao_usb_sram_addr)
+ ao_usb_sram_addr = offset;
+}
+
+void
+ao_usb_write(uint16_t *buffer, uint16_t len)
+{
+ ao_arch_block_interrupts();
+
+ /* Flush any pending regular */
+ if (ao_usb_tx_count)
+ _ao_usb_in_send();
+
+ while (ao_usb_in_pending)
+ ao_sleep(&ao_usb_in_pending);
+ ao_usb_in_pending = 1;
+ ao_usb_in_flushed = (len != AO_USB_IN_SIZE);
+ ao_usb_bdt[AO_USB_IN_EPR].single.addr_tx = ao_usb_packet_buffer_offset(buffer);
+ ao_usb_bdt[AO_USB_IN_EPR].single.count_tx = len;
+ _ao_usb_set_stat_tx(AO_USB_IN_EPR, STM_USB_EPR_STAT_TX_VALID);
+ ao_arch_release_interrupts();
+}
+#endif
+