1 ///////////////////////////////////////////////////////////////////////// 2 // $Id: uhci_core.h 14148 2021-02-16 17:04:04Z vruppert $ 3 ///////////////////////////////////////////////////////////////////////// 4 // 5 // Copyright (C) 2009-2016 Benjamin D Lunt (fys [at] fysnet [dot] net) 6 // 2009-2021 The Bochs Project 7 // 8 // This library is free software; you can redistribute it and/or 9 // modify it under the terms of the GNU Lesser General Public 10 // License as published by the Free Software Foundation; either 11 // version 2 of the License, or (at your option) any later version. 12 // 13 // This library is distributed in the hope that it will be useful, 14 // but WITHOUT ANY WARRANTY; without even the implied warranty of 15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 16 // Lesser General Public License for more details. 17 // 18 // You should have received a copy of the GNU Lesser General Public 19 // License along with this library; if not, write to the Free Software 20 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 21 22 #ifndef BX_IODEV_UHCI_CORE_H 23 #define BX_IODEV_UHCI_CORE_H 24 25 #define USB_UHCI_PORTS 2 26 27 typedef struct { 28 int timer_index; 29 30 // Registers 31 // Base + 0x00 Command register 32 // Base + 0x02 Status register 33 // Base + 0x04 Interrupt Enable register 34 // Base + 0x06 Frame Number register 35 // Base + 0x08 Frame Base Register (32-bit) 36 // Base + 0x0C Start of Frame Modify register 37 // Base + 0x0D 38 // Base + 0x0E 39 // Base + 0x0F 40 // Base + 0x10 Eight(?) 16-bit ports (one for each port on hub) 41 42 // Bit reps of registers above 43 // Command Register 44 // Bits 15-8 are reserved 45 // Bit 7 = Maximum packet size 46 // Bit 6 = Host Controller has been configured (set by software) 47 // Bit 5 = software debug mode 48 // Bit 4 = force global resume 49 // Bit 3 = enter global suspend mode 50 // Bit 2 = global reset 51 // Bit 1 = host controller reset 52 // Bit 0 = run/stop schedule 53 struct { 54 bool max_packet_size; //(bit 7) 0 = 32 bytes, 1 = 64 bytes 55 bool configured; //(bit 6) 56 bool debug; //(bit 5) 57 bool resume; //(bit 4) 58 bool suspend; //(bit 3) 59 bool reset; //(bit 2) 60 bool host_reset; //(bit 1) 61 bool schedule; //(bit 0) 0 = Stop, 1 = Run 62 } usb_command; 63 64 // Status Register 65 // Bits 15-6 are reserved 66 // Bit 5 = Host controller halted 67 // Bit 4 = Host controller process error 68 // Bit 3 = PCI Bus error 69 // Bit 2 = resume received 70 // Bit 1 = USB error interrupt 71 // Bit 0 = USB interrupt 72 struct { 73 bool host_halted; //(bit 5) 74 bool host_error; //(bit 4) 75 bool pci_error; //(bit 3) 76 bool resume; //(bit 2) 77 bool error_interrupt; //(bit 1) 78 bool interrupt; //(bit 0) 79 Bit8u status2; // bit 0 and 1 are used to generate the interrupt 80 } usb_status; 81 82 // Interrupt Enable Register 83 // Bits 15-4 are reserved 84 // Bit 3 = enable short packet interrupts 85 // Bit 2 = enable interrupt On Complete 86 // Bit 1 = enable resume 87 // Bit 0 = enable timeout/crc 88 struct { 89 bool short_packet; //(bit 3) 90 bool on_complete; //(bit 2) 91 bool resume; //(bit 1) 92 bool timeout_crc; //(bit 0) 93 } usb_enable; 94 95 // Frame Number Register 96 // Bits 15-11 are reserved 97 // Bits 10-0 Frame List Current Index/Frame Number 98 struct { 99 Bit16u frame_num; 100 } usb_frame_num; 101 102 // Frame List Base Address Register 103 // Bits 31-12 Base 104 // Bits 11-0 *must* be zeros when written to 105 struct { 106 Bit32u frame_base; 107 } usb_frame_base; 108 109 // Start of Frame Modify Register 110 // Bit 7 reserved 111 // Bits 6-0 SOF timing value (default 64) 112 // SOF cycle time equals 11936+timing value 113 struct { 114 Bit8u sof_timing; 115 } usb_sof; 116 117 // Port Register (0-1) 118 // Bits 15-13 are reserved 119 // Bit 12 suspend port 120 // Bit 11-10 are reserved 121 // Bit 9 port in reset state 122 // Bit 8 low-speed device is attached (read-only) 123 // Bit 7 reserved 124 // Bit 6 resume detected (read-only) 125 // Bit 5 line-status D+ (read-only) 126 // Bit 4 line-status D- (read-only) 127 // Bit 3 port enabled/disable status has changed 128 // (write 1 to this bit to clear it) 129 // Bit 2 port is enabled 130 // Bit 1 connect status has changed 131 // (write 1 to this bit to clear it) 132 // Bit 0 current connect status (read-only) 133 // Can only write in WORD sizes (Read in byte sizes???) 134 struct { 135 // our data 136 usb_device_c *device; // device connected to this port 137 138 // bit reps of actual port 139 bool suspend; 140 bool reset; 141 bool low_speed; 142 bool resume; 143 bool line_dminus; 144 bool line_dplus; 145 bool able_changed; 146 bool enabled; 147 bool connect_changed; 148 bool status; 149 } usb_port[USB_UHCI_PORTS]; 150 151 Bit8u devfunc; 152 } bx_uhci_core_t; 153 154 #pragma pack (push, 1) 155 struct TD { 156 Bit32u dword0; 157 Bit32u dword1; 158 Bit32u dword2; 159 Bit32u dword3; 160 Bit32u resv[4]; 161 }; 162 #pragma pack (pop) 163 164 #define HC_HORZ 0x80 165 #define HC_VERT 0x81 166 struct HCSTACK { 167 Bit32u next; 168 Bit8u d; // if queue, denotes VERT or HORZ 169 bool q; 170 bool t; 171 }; 172 173 class bx_uhci_core_c : public bx_pci_device_c { 174 public: 175 bx_uhci_core_c(); 176 virtual ~bx_uhci_core_c(); 177 virtual void init_uhci(Bit8u devfunc, Bit16u devid, Bit8u headt, Bit8u intp); 178 virtual void reset_uhci(unsigned); 179 void uhci_register_state(bx_list_c *parent); 180 virtual void after_restore_state(void); 181 virtual void set_port_device(int port, usb_device_c *dev); 182 virtual void pci_write_handler(Bit8u address, Bit32u value, unsigned io_len); 183 184 void event_handler(int event, USBPacket *packet, int port); 185 186 protected: 187 bx_uhci_core_t hub; 188 Bit8u global_reset; 189 bool busy; 190 191 USBAsync *packets; 192 193 void update_irq(void); 194 195 int broadcast_packet(USBPacket *p); 196 bool set_connect_status(Bit8u port, bool connected); 197 198 static void uhci_timer_handler(void *); 199 void uhci_timer(void); 200 bool DoTransfer(Bit32u address, Bit32u queue_num, struct TD *); 201 void set_status(struct TD *td, bool stalled, bool data_buffer_error, bool babble, 202 bool nak, bool crc_time_out, bool bitstuff_error, Bit16u act_len); 203 204 static Bit32u read_handler(void *this_ptr, Bit32u address, unsigned io_len); 205 static void write_handler(void *this_ptr, Bit32u address, Bit32u value, unsigned io_len); 206 Bit32u read(Bit32u address, unsigned io_len); 207 void write(Bit32u address, Bit32u value, unsigned io_len); 208 }; 209 210 #endif 211