libxr  1.0
Want to be the best embedded framework
Loading...
Searching...
No Matches
esp_usb.hpp
1#pragma once
2
3#include "esp_def.hpp"
4
5#include <cstddef>
6#include <cstdint>
7
8#include "esp_dma_utils.h"
9#include "esp_heap_caps.h"
10#include "usb/core/ep.hpp"
11
12#if SOC_USB_OTG_SUPPORTED && defined(CONFIG_IDF_TARGET_ESP32S3) && CONFIG_IDF_TARGET_ESP32S3
13
14#include "soc/usb_dwc_struct.h"
15
16namespace LibXR::ESPUSBDetail
17{
18
19inline constexpr uint32_t kDwc2FsRegBase = 0x60080000UL;
20inline constexpr size_t kFifoBaseOffset = 0x1000U;
21inline constexpr size_t kFifoStride = 0x1000U;
22
23inline constexpr uint8_t kRxStatusGlobalOutNak = 1U;
24inline constexpr uint8_t kRxStatusData = 2U;
25inline constexpr uint8_t kRxStatusTransferComplete = 3U;
26inline constexpr uint8_t kRxStatusSetupDone = 4U;
27inline constexpr uint8_t kRxStatusSetupData = 6U;
28
29inline constexpr uint8_t kEnumSpeedFull30To60Mhz = 1U;
30inline constexpr uint8_t kEnumSpeedFull48Mhz = 3U;
31
32inline constexpr size_t kWordSize = sizeof(uint32_t);
33inline constexpr uint8_t kFlushAllTxFifo = 0x10U;
34inline constexpr uint32_t kDmaBurstIncr4 = 4U;
35inline constexpr uint32_t kDmaMemoryCaps =
36 MALLOC_CAP_INTERNAL | MALLOC_CAP_DMA | MALLOC_CAP_8BIT;
37inline constexpr uint16_t kEsp32SxFsDmaMinRxFifoWords = 88U;
38inline constexpr uint16_t kEsp32SxFsMinTxFifoWords = 16U;
39inline constexpr uint32_t kDisableOutWaitGuard = 100000U;
40
41#if defined(CONFIG_USB_ALIGN_SIZE)
42inline constexpr size_t kUsbDmaAlignment = CONFIG_USB_ALIGN_SIZE;
43#elif defined(CONFIG_CACHE_L1_CACHE_LINE_SIZE)
44inline constexpr size_t kUsbDmaAlignment = CONFIG_CACHE_L1_CACHE_LINE_SIZE;
45#else
46inline constexpr size_t kUsbDmaAlignment = 64U;
47#endif
48
49constexpr uint32_t PackTxFifoSizeReg(uint16_t start, uint16_t words)
50{
51 return (static_cast<uint32_t>(words) << 16U) | static_cast<uint32_t>(start);
52}
53
54bool CacheSyncDmaBuffer(const void* addr, size_t size, bool cache_to_mem,
55 bool allow_unaligned = false);
56size_t AlignUp(size_t value, size_t align);
57esp_dma_mem_info_t UsbDmaMemInfo();
58bool CanUseDirectInDmaBuffer(const void* ptr, size_t size);
59bool CanUseDirectOutDmaBuffer(const void* ptr, size_t size);
60uint16_t CalcRxFifoWords(uint16_t largest_packet_size, uint8_t ep_count);
61uint16_t CalcConfiguredRxFifoWords(uint16_t largest_packet_size, uint8_t ep_count,
62 bool dma_enabled);
63uint16_t GetHardwareFifoDepthWords();
64uint8_t EncodeEp0Mps(uint16_t packet_size);
65uint16_t ClampPacketSize(LibXR::USB::Endpoint::Type type, uint16_t requested);
66uint16_t CalcTxFifoWords(uint16_t packet_size, bool dma_enabled);
67volatile uint32_t* GetEndpointFifo(usb_dwc_dev_t* dev, uint8_t ep_num);
68void WriteFifoPacket(volatile uint32_t* fifo, const uint8_t* src, size_t size);
69void ReadFifoPacket(const volatile uint32_t* fifo, uint8_t* dst, size_t size);
70uint16_t PacketCount(size_t size, uint16_t max_packet_size);
71void FlushTxFifo(usb_dwc_dev_t* dev, uint8_t fifo_num);
72void DisableInEndpointAndWait(usb_dwc_dev_t* dev);
73void DisableInEndpointAndWait(usb_dwc_dev_t* dev, uint8_t ep_num);
74
75template <typename EpCtl>
76void StartEndpointTransfer(volatile EpCtl& reg)
77{
78 EpCtl ctl = {};
79 ctl.val = reg.val;
80 ctl.snak = 0;
81 ctl.cnak = 1;
82 ctl.epdis = 0;
83 ctl.epena = 1;
84 reg.val = ctl.val;
85}
86
87template <typename DoepCtl>
88void DisableOutEndpointAndWait(volatile DoepCtl& ctl)
89{
90 DoepCtl disable = {};
91 disable.val = ctl.val;
92 disable.snak = 1;
93 const bool was_enabled = disable.epena;
94 if (was_enabled)
95 {
96 disable.epdis = 1;
97 }
98 ctl.val = disable.val;
99
100 if (!was_enabled)
101 {
102 return;
103 }
104
105 uint32_t guard = kDisableOutWaitGuard;
106 while (ctl.epena && guard > 0U)
107 {
108 --guard;
109 }
110}
111
112} // namespace LibXR::ESPUSBDetail
113
114#endif
Type
端点类型 Endpoint type
Definition ep.hpp:69