Skip to content

Commit 0207a6e

Browse files
committed
adding host support for rp2040
1 parent 8e7c7a5 commit 0207a6e

File tree

8 files changed

+295
-17
lines changed

8 files changed

+295
-17
lines changed

examples/DualRole/device_info_rp2040/.feather_rp2040_tinyusb.test.only

Whitespace-only changes.
Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
/*********************************************************************
2+
Adafruit invests time and resources providing this open source code,
3+
please support Adafruit and open-source hardware by purchasing
4+
products from Adafruit!
5+
6+
MIT license, check LICENSE for more information
7+
Copyright (c) 2019 Ha Thach for Adafruit Industries
8+
All text above, and the splash screen below must be included in
9+
any redistribution
10+
*********************************************************************/
11+
12+
// pio-usb is required for rp2040 host
13+
#include "pio_usb.h"
14+
#define HOST_PIN_DP 2 // Pin used as D+ for host, D- = D+ + 1
15+
16+
#include "Adafruit_TinyUSB.h"
17+
18+
// USB Host object
19+
Adafruit_USBH_Host USBHost;
20+
21+
// the setup function runs once when you press reset or power the board
22+
void setup()
23+
{
24+
Serial1.begin(115200);
25+
26+
Serial.begin(115200);
27+
//while ( !Serial ) delay(10); // wait for native usb
28+
29+
Serial.println("TinyUSB Dual Device Info Example");
30+
31+
// Check for CPU frequency, must be multiple of 120Mhz for bit-banging USB
32+
uint32_t cpu_hz = clock_get_hz(clk_sys);
33+
if ( cpu_hz != 120000000UL && cpu_hz != 240000000UL ) {
34+
while ( !Serial ) delay(10); // wait for native usb
35+
Serial.printf("Error: CPU Clock = %u, PIO USB require CPU clock must be multiple of 120 Mhz\r\n", cpu_hz);
36+
Serial.printf("Change your CPU Clock to either 120 or 240 Mhz in Menu->CPU Speed \r\n", cpu_hz);
37+
while(1) delay(1);
38+
}
39+
40+
pio_usb_configuration_t pio_cfg = PIO_USB_DEFAULT_CONFIG;
41+
pio_cfg.pin_dp = HOST_PIN_DP;
42+
USBHost.configure_pio_usb(1, &pio_cfg);
43+
44+
// run host stack on controller (rhport) 1
45+
// Note: For rp2040 pico-pio-usb, calling USBHost.begin() on core1 will have most of the
46+
// host bit-banging processing works done in core1 to free up core0 for other works
47+
USBHost.begin(1);
48+
}
49+
50+
void loop()
51+
{
52+
USBHost.task();
53+
}
54+
55+
#if 0
56+
57+
// core1's setup
58+
void setup1() {
59+
//while ( !Serial ) delay(10); // wait for native usb
60+
Serial.println("Core1 setup to run TinyUSB host with pio-usb");
61+
62+
// Check for CPU frequency, must be multiple of 120Mhz for bit-banging USB
63+
uint32_t cpu_hz = clock_get_hz(clk_sys);
64+
if ( cpu_hz != 120000000UL && cpu_hz != 240000000UL ) {
65+
while ( !Serial ) delay(10); // wait for native usb
66+
Serial.printf("Error: CPU Clock = %u, PIO USB require CPU clock must be multiple of 120 Mhz\r\n", cpu_hz);
67+
Serial.printf("Change your CPU Clock to either 120 or 240 Mhz in Menu->CPU Speed \r\n", cpu_hz);
68+
while(1) delay(1);
69+
}
70+
71+
pio_usb_configuration_t pio_cfg = PIO_USB_DEFAULT_CONFIG;
72+
pio_cfg.pin_dp = HOST_PIN_DP;
73+
USBHost.configure_pio_usb(1, &pio_cfg);
74+
75+
// run host stack on controller (rhport) 1
76+
// Note: For rp2040 pico-pio-usb, calling USBHost.begin() on core1 will have most of the
77+
// host bit-banging processing works done in core1 to free up core0 for other works
78+
USBHost.begin(1);
79+
}
80+
81+
// core1's loop
82+
void loop1()
83+
{
84+
USBHost.task();
85+
}
86+
87+
#endif
88+

src/Adafruit_TinyUSB.h

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,9 +33,9 @@
3333

3434
#include "tusb_option.h"
3535

36+
// Device
3637
#if TUSB_OPT_DEVICE_ENABLED
3738

38-
3939
#include "arduino/Adafruit_USBD_Device.h"
4040
#if CFG_TUD_CDC
4141
#include "arduino/Adafruit_USBD_CDC.h"
@@ -60,4 +60,11 @@ void TinyUSB_Device_Init(uint8_t rhport);
6060

6161
#endif
6262

63+
// Host
64+
#if CFG_TUH_ENABLED
65+
66+
#include "arduino/Adafruit_USBH_Host.h"
67+
68+
#endif
69+
6370
#endif /* ADAFRUIT_TINYUSB_H_ */

src/arduino/Adafruit_USBH_Host.cpp

Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
/*
2+
* The MIT License (MIT)
3+
*
4+
* Copyright (c) 2022, Ha Thach (tinyusb.org) for Adafruit
5+
*
6+
* Permission is hereby granted, free of charge, to any person obtaining a copy
7+
* of this software and associated documentation files (the "Software"), to deal
8+
* in the Software without restriction, including without limitation the rights
9+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10+
* copies of the Software, and to permit persons to whom the Software is
11+
* furnished to do so, subject to the following conditions:
12+
*
13+
* The above copyright notice and this permission notice shall be included in
14+
* all copies or substantial portions of the Software.
15+
*
16+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22+
* THE SOFTWARE.
23+
*/
24+
25+
#include "tusb_option.h"
26+
27+
#if CFG_TUH_ENABLED
28+
29+
#include "Adafruit_TinyUSB_API.h"
30+
#include "Adafruit_USBH_Host.h"
31+
32+
Adafruit_USBH_Host::Adafruit_USBH_Host(void)
33+
{
34+
35+
}
36+
37+
bool Adafruit_USBH_Host::configure(uint8_t rhport, uint32_t cfg_id, const void* cfg_param)
38+
{
39+
return tuh_configure(rhport, cfg_id, cfg_param);
40+
}
41+
42+
#ifdef ARDUINO_ARCH_RP2040
43+
bool Adafruit_USBH_Host::configure_pio_usb(uint8_t rhport, const void* cfg_param)
44+
{
45+
return configure(rhport, TUH_CFGID_RPI_PIO_USB_CONFIGURATION, cfg_param);
46+
}
47+
#endif
48+
49+
bool Adafruit_USBH_Host::begin(uint8_t rhport)
50+
{
51+
return tuh_init(rhport);
52+
}
53+
54+
void Adafruit_USBH_Host::task(void)
55+
{
56+
tuh_task();
57+
}
58+
59+
// Invoked when device with hid interface is mounted
60+
// Report descriptor is also available for use. tuh_hid_parse_report_descriptor()
61+
// can be used to parse common/simple enough descriptor.
62+
// Note: if report descriptor length > CFG_TUH_ENUMERATION_BUFSIZE, it will be skipped
63+
// therefore report_desc = NULL, desc_len = 0
64+
void tuh_hid_mount_cb(uint8_t dev_addr, uint8_t instance, uint8_t const* desc_report, uint16_t desc_len)
65+
{
66+
(void)desc_report;
67+
(void)desc_len;
68+
}
69+
70+
// Invoked when device with hid interface is un-mounted
71+
void tuh_hid_umount_cb(uint8_t dev_addr, uint8_t instance)
72+
{
73+
}
74+
75+
// Invoked when received report from device via interrupt endpoint
76+
void tuh_hid_report_received_cb(uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
77+
{
78+
(void) len;
79+
}
80+
#endif

src/arduino/Adafruit_USBH_Host.h

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
/*
2+
* The MIT License (MIT)
3+
*
4+
* Copyright (c) 2019 Ha Thach for Adafruit Industries
5+
*
6+
* Permission is hereby granted, free of charge, to any person obtaining a copy
7+
* of this software and associated documentation files (the "Software"), to deal
8+
* in the Software without restriction, including without limitation the rights
9+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10+
* copies of the Software, and to permit persons to whom the Software is
11+
* furnished to do so, subject to the following conditions:
12+
*
13+
* The above copyright notice and this permission notice shall be included in
14+
* all copies or substantial portions of the Software.
15+
*
16+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22+
* THE SOFTWARE.
23+
*/
24+
25+
#ifndef ADAFRUIT_USBH_HOST_H_
26+
#define ADAFRUIT_USBH_HOST_H_
27+
28+
#include "Adafruit_USBD_Interface.h"
29+
#include "tusb.h"
30+
31+
#ifdef ARDUINO_ARCH_ESP32
32+
#include "esp32-hal-tinyusb.h"
33+
#endif
34+
35+
class Adafruit_USBH_Host {
36+
private:
37+
38+
public:
39+
Adafruit_USBH_Host(void);
40+
41+
bool configure(uint8_t rhport, uint32_t cfg_id, const void* cfg_param);
42+
43+
#ifdef ARDUINO_ARCH_RP2040
44+
bool configure_pio_usb(uint8_t rhport, const void* cfg_param);
45+
#endif
46+
47+
bool begin(uint8_t rhport);
48+
void task(void);
49+
50+
private:
51+
// uint16_t const *descrip`tor_string_cb(uint8_t index, uint16_t langid);
52+
//
53+
// friend uint8_t const *tud_descriptor_device_cb(void);
54+
// friend uint8_t const *tud_descriptor_configuration_cb(uint8_t index);
55+
// friend uint16_t const *tud_descriptor_string_cb(uint8_t index,
56+
// uint16_t langid);
57+
};
58+
59+
//extern Adafruit_USBH_Host TinyUSBHost;
60+
//
61+
//// USBHost has a high chance to conflict with other usb stack
62+
//// only define if supported BSP
63+
//#ifdef USE_TINYUSB
64+
//#define USBHost TinyUSBHost
65+
//#endif
66+
67+
#endif /* ADAFRUIT_USBH_HOST_H_ */

src/arduino/ports/rp2040/Adafruit_TinyUSB_rp2040.cpp

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -149,6 +149,21 @@ void TinyUSB_Device_Task(void) {
149149
mutex_exit(&__usb_mutex);
150150
}
151151
}
152+
153+
// Debug log with Serial1
154+
#if CFG_TUSB_DEBUG
155+
int serial1_printf(const char *__restrict format, ...) {
156+
char buf[256];
157+
int len;
158+
va_list ap;
159+
va_start(ap, format);
160+
len = vsnprintf(buf, sizeof(buf), format, ap);
161+
Serial1.write(buf);
162+
va_end(ap);
163+
return len;
164+
}
165+
#endif
166+
152167
}
153168

154169
#endif

src/arduino/ports/rp2040/tusb_config_rp2040.h

Lines changed: 34 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -34,32 +34,40 @@ extern "C" {
3434
//--------------------------------------------------------------------
3535
#define CFG_TUSB_RHPORT0_MODE OPT_MODE_DEVICE
3636

37+
// Enable device stack
38+
#define CFG_TUD_ENABLED 1
39+
40+
// Enable host stack with pio-usb if Pico-PIO-USB library is available
41+
#if __has_include("pio_usb.h")
42+
#define CFG_TUH_ENABLED 1
43+
#define CFG_TUH_RPI_PIO_USB 1
44+
#endif
45+
3746
#ifndef CFG_TUSB_MCU
3847
#define CFG_TUSB_MCU OPT_MCU_RP2040
3948
#endif
4049
#define CFG_TUSB_OS OPT_OS_PICO
4150

42-
#define CFG_TUSB_DEBUG 0
43-
//#if CFG_TUSB_DEBUG
44-
// #define tu_printf serial1_printf
45-
// extern int serial1_printf(const char *__restrict __format, ...);
46-
//#endif
51+
#define CFG_TUSB_DEBUG 2
52+
#if CFG_TUSB_DEBUG
53+
#define CFG_TUSB_DEBUG_PRINTF serial1_printf
54+
extern int serial1_printf(const char *__restrict __format, ...);
55+
#endif
4756

4857
#define CFG_TUSB_MEM_SECTION
49-
#define CFG_TUSB_MEM_ALIGN TU_ATTR_ALIGNED(4)
58+
#define CFG_TUSB_MEM_ALIGN TU_ATTR_ALIGNED(4)
5059

5160
//--------------------------------------------------------------------
52-
// DEVICE CONFIGURATION
61+
// Device Configuration
5362
//--------------------------------------------------------------------
5463

5564
#define CFG_TUD_ENDOINT0_SIZE 64
5665

57-
//------------- CLASS -------------//
58-
#define CFG_TUD_CDC 1
59-
#define CFG_TUD_MSC 1
60-
#define CFG_TUD_HID 1
61-
#define CFG_TUD_MIDI 1
62-
#define CFG_TUD_VENDOR 1
66+
#define CFG_TUD_CDC 1
67+
#define CFG_TUD_MSC 1
68+
#define CFG_TUD_HID 1
69+
#define CFG_TUD_MIDI 1
70+
#define CFG_TUD_VENDOR 1
6371

6472
// CDC FIFO size of TX and RX
6573
#define CFG_TUD_CDC_RX_BUFSIZE 256
@@ -79,6 +87,19 @@ extern "C" {
7987
#define CFG_TUD_VENDOR_RX_BUFSIZE 64
8088
#define CFG_TUD_VENDOR_TX_BUFSIZE 64
8189

90+
//--------------------------------------------------------------------
91+
// Host Configuration
92+
//--------------------------------------------------------------------
93+
94+
// Size of buffer to hold descriptors and other data used for enumeration
95+
#define CFG_TUH_ENUMERATION_BUFSIZE 256
96+
97+
#define CFG_TUH_HUB 1
98+
// max device support (excluding hub device)
99+
#define CFG_TUH_DEVICE_MAX (CFG_TUH_HUB ? 4 : 1) // hub typically has 4 ports
100+
101+
#define CFG_TUH_HID 4
102+
82103
#ifdef __cplusplus
83104
}
84105
#endif

src/arduino/ports/samd/Adafruit_TinyUSB_samd.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -52,11 +52,9 @@ void USB_Handler(void) { tud_int_handler(0); }
5252

5353
#endif
5454

55-
} // extern C
56-
5755
// Debug log with Serial1
5856
#if CFG_TUSB_DEBUG
59-
extern "C" int serial1_printf(const char *__restrict format, ...) {
57+
int serial1_printf(const char *__restrict format, ...) {
6058
char buf[256];
6159
int len;
6260
va_list ap;
@@ -68,6 +66,8 @@ extern "C" int serial1_printf(const char *__restrict format, ...) {
6866
}
6967
#endif
7068

69+
} // extern C
70+
7171
//--------------------------------------------------------------------+
7272
// Porting API
7373
//--------------------------------------------------------------------+

0 commit comments

Comments
 (0)