4 * Config Southbridge USB controller
8 * @xrefitem bom "File Content Label" "Release Content"
11 * @e \$Revision:$ @e \$Date:$
15 *****************************************************************************
17 * Copyright (c) 2011, Advanced Micro Devices, Inc.
18 * All rights reserved.
20 * Redistribution and use in source and binary forms, with or without
21 * modification, are permitted provided that the following conditions are met:
22 * * Redistributions of source code must retain the above copyright
23 * notice, this list of conditions and the following disclaimer.
24 * * Redistributions in binary form must reproduce the above copyright
25 * notice, this list of conditions and the following disclaimer in the
26 * documentation and/or other materials provided with the distribution.
27 * * Neither the name of Advanced Micro Devices, Inc. nor the names of
28 * its contributors may be used to endorse or promote products derived
29 * from this software without specific prior written permission.
31 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
32 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
33 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
34 * DISCLAIMED. IN NO EVENT SHALL ADVANCED MICRO DEVICES, INC. BE LIABLE FOR ANY
35 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
36 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
37 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
38 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
39 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
40 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
42 * ***************************************************************************
47 #include "SBPLATFORM.h"
51 // Declaration of local functions
55 * EhciInitAfterPciInit - Config USB controller after PCI emulation
57 * @param[in] Value Controller PCI config address (bus# + device# + function#)
58 * @param[in] pConfig Southbridge configuration structure pointer.
60 VOID EhciInitAfterPciInit (IN UINT32 Value, IN AMDSBCFG* pConfig);
62 * OhciInitAfterPciInit - Config USB OHCI controller after PCI emulation
64 * @param[in] Value Controller PCI config address (bus# + device# + function#)
65 * @param[in] pConfig Southbridge configuration structure pointer.
67 VOID OhciInitAfterPciInit (IN UINT32 Value, IN AMDSBCFG* pConfig);
70 * SetEhciP11Wr - FIXME
72 * @param[in] Value Controller PCI config address (bus# + device# + function#)
73 * @param[in] pConfig Southbridge configuration structure pointer.
75 UINT32 SetEhciPllWr (IN UINT32 Value, IN AMDSBCFG* pConfig);
79 * usbInitBeforePciEnum - Config USB controller before PCI emulation
83 * @param[in] pConfig Southbridge configuration structure pointer.
87 usbInitBeforePciEnum (
91 // Disabled All USB controller
92 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGEF, AccWidthUint8, BIT7, 0);
93 // Clear PM_IO 0x65[4] UsbResetByPciRstEnable, Set this bit so that usb gets reset whenever there is PCIRST.
94 // Enable UsbResumeEnable (USB PME) * Default value
95 // In SB700 USB SleepCtrl set as BIT10+BIT9, but SB800 default is BIT9+BIT8 (6 uframes)
96 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGF0, AccWidthUint16 | S3_SAVE, ~BIT2, BIT2 + BIT7 + BIT8 + BIT9);
97 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGEF, AccWidthUint8, 0, pConfig->USBMODE.UsbModeReg);
101 * usbInitAfterPciInit - Config USB controller after PCI emulation
105 * @param[in] pConfig Southbridge configuration structure pointer.
109 usbInitAfterPciInit (
113 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGED, AccWidthUint8, ~BIT1, BIT1);
115 usb1EhciInitAfterPciInit (pConfig);
116 usb2EhciInitAfterPciInit (pConfig);
117 usb3EhciInitAfterPciInit (pConfig);
118 usb1OhciInitAfterPciInit (pConfig);
119 usb2OhciInitAfterPciInit (pConfig);
120 usb3OhciInitAfterPciInit (pConfig);
121 usb4OhciInitAfterPciInit (pConfig);
123 if ( pConfig->UsbPhyPowerDown ) {
124 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGF0, AccWidthUint8, ~BIT0, BIT0);
127 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGF0, AccWidthUint8, ~BIT0, 0);
133 * usb1EhciInitAfterPciInit - Config USB1 EHCI controller after PCI emulation
137 * @param[in] pConfig Southbridge configuration structure pointer.
141 usb1EhciInitAfterPciInit (
146 ddDeviceId = (USB1_EHCI_BUS_DEV_FUN << 16);
147 EhciInitAfterPciInit (ddDeviceId, pConfig);
151 * usb2EhciInitAfterPciInit - Config USB2 EHCI controller after PCI emulation
155 * @param[in] pConfig Southbridge configuration structure pointer.
159 usb2EhciInitAfterPciInit (
164 ddDeviceId = (USB2_EHCI_BUS_DEV_FUN << 16);
165 EhciInitAfterPciInit (ddDeviceId, pConfig);
169 * usb3EhciInitAfterPciInit - Config USB3 EHCI controller after PCI emulation
173 * @param[in] pConfig Southbridge configuration structure pointer.
177 usb3EhciInitAfterPciInit (
182 ddDeviceId = (USB3_EHCI_BUS_DEV_FUN << 16);
183 EhciInitAfterPciInit (ddDeviceId, pConfig);
187 EhciInitAfterPciInit (
195 ReadPCI ((UINT32) Value + SB_EHCI_REG10, AccWidthUint32, &ddBarAddress);
196 if ( (ddBarAddress != - 1) && (ddBarAddress != 0) ) {
197 //Enable Memory access
198 RWPCI ((UINT32) Value + SB_EHCI_REG04, AccWidthUint8, 0, BIT1);
199 if (pConfig->BuildParameters.EhciSsid != NULL ) {
200 RWPCI ((UINT32) Value + SB_EHCI_REG2C, AccWidthUint32 | S3_SAVE, 0x00, pConfig->BuildParameters.EhciSsid);
202 //USB Common PHY CAL & Control Register setting
204 WriteMEM (ddBarAddress + SB_EHCI_BAR_REGC0, AccWidthUint32, &ddVar);
205 // RPR IN AND OUT DATA PACKET FIFO THRESHOLD
206 // EHCI BAR 0xA4 //IN threshold bits[7:0]=0x40 //OUT threshold bits[23:16]=0x40
207 RWMEM (ddBarAddress + SB_EHCI_BAR_REGA4, AccWidthUint32, 0xFF00FF00, 0x00400040);
208 // RPR EHCI Dynamic Clock Gating Feature
209 RWMEM (ddBarAddress + SB_EHCI_BAR_REGBC, AccWidthUint32, ~BIT12, 0);
210 // RPR Enable adding extra flops to PHY rsync path
212 // EHCI_BAR 0xB4 [6] = 1
213 // EHCI_BAR 0xB4 [7] = 0
214 // EHCI_BAR 0xB4 [12] = 0 ("VLoad")
215 // All other bit field untouched
217 // EHCI_BAR 0xB4[12] = 1
218 RWMEM (ddBarAddress + SB_EHCI_BAR_REGB4, AccWidthUint32, ~(BIT6 + BIT7 + BIT12), 0x00);
219 RWMEM (ddBarAddress + SB_EHCI_BAR_REGB4, AccWidthUint32, ~BIT12, BIT12);
220 //Set EHCI_pci_configx50[6]='1' to disable EHCI MSI support
221 //RPR recommended setting "EHCI Async Park Mode"
222 //Set EHCI_pci_configx50[23]='0' to enable "EHCI Async Park Mode support"
223 //RPR Enabling EHCI Async Stop Enhancement
224 //Set EHCI_pci_configx50[29]='1' to disableEnabling EHCI Async Stop Enhancement
225 RWPCI ((UINT32) Value + SB_EHCI_REG50, AccWidthUint32 | S3_SAVE, ~(BIT23), BIT29 + BIT23 + BIT8 + BIT6);
226 // RPR recommended setting "EHCI Advance PHY Power Savings"
227 // Set EHCI_pci_configx50[31]='1'
228 // Fix for EHCI controller driver yellow sign issue under device manager
229 // when used in conjunction with HSET tool driver. EHCI PCI config 0x50[20]=1
230 RWPCI ((UINT32) Value + SB_EHCI_REG50 + 2, AccWidthUint16 | S3_SAVE, (UINT16)0xFFFF, BIT15);
231 // RPR USB Delay A-Link Express L1 State
232 // RPR PING Response Fix Enable EHCI_PCI_Config x54[1] = 1
233 // RPR Empty-list Detection Fix Enable EHCI_PCI_Config x54[3] = 1
234 RWPCI ((UINT32) Value + SB_EHCI_REG54, AccWidthUint32 | S3_SAVE, ~BIT0, BIT0);
235 if ( pConfig->BuildParameters.UsbMsi) {
236 RWPCI ((UINT32) Value + SB_EHCI_REG50, AccWidthUint32 | S3_SAVE, ~BIT6, 0x00);
242 * usb1OhciInitAfterPciInit - Config USB1 OHCI controller after PCI emulation
246 * @param[in] pConfig Southbridge configuration structure pointer.
250 usb1OhciInitAfterPciInit (
255 ddDeviceId = (USB1_OHCI_BUS_DEV_FUN << 16);
256 OhciInitAfterPciInit (ddDeviceId, pConfig);
260 * usb2OhciInitAfterPciInit - Config USB2 OHCI controller after PCI emulation
264 * @param[in] pConfig Southbridge configuration structure pointer.
268 usb2OhciInitAfterPciInit (
273 ddDeviceId = (USB2_OHCI_BUS_DEV_FUN << 16);
274 OhciInitAfterPciInit (ddDeviceId, pConfig);
278 * usb3OhciInitAfterPciInit - Config USB3 OHCI controller after PCI emulation
282 * @param[in] pConfig Southbridge configuration structure pointer.
286 usb3OhciInitAfterPciInit (
291 ddDeviceId = (USB3_OHCI_BUS_DEV_FUN << 16);
292 OhciInitAfterPciInit (ddDeviceId, pConfig);
296 * usb4OhciInitAfterPciInit - Config USB4 OHCI controller after PCI emulation
300 * @param[in] pConfig Southbridge configuration structure pointer.
304 usb4OhciInitAfterPciInit (
309 ddDeviceId = (USB4_OHCI_BUS_DEV_FUN << 16);
310 OhciInitAfterPciInit (ddDeviceId, pConfig);
311 if (pConfig->BuildParameters.Ohci4Ssid != NULL ) {
312 RWPCI ((USB4_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG2C, AccWidthUint32 | S3_SAVE, 0x00, pConfig->BuildParameters.Ohci4Ssid);
317 OhciInitAfterPciInit (
322 // Disable the MSI capability of USB host controllers
323 RWPCI ((UINT32) Value + SB_OHCI_REG40 + 1, AccWidthUint8 | S3_SAVE, 0xFF, BIT0);
324 RWPCI ((UINT32) Value + SB_OHCI_REG50, AccWidthUint8 | S3_SAVE, ~(BIT5 + BIT12), 0x00);
325 // RPR USB SMI Handshake
326 RWPCI ((UINT32) Value + SB_OHCI_REG50 + 1, AccWidthUint8 | S3_SAVE, ~BIT4, 0x00);
328 RWPCI ((UINT32) Value + SB_OHCI_REG50 + 1, AccWidthUint8 | S3_SAVE, 0xFC, 0x00);
329 if (Value != (USB4_OHCI_BUS_DEV_FUN << 16)) {
330 if ( pConfig->BuildParameters.OhciSsid != NULL ) {
331 RWPCI ((UINT32) Value + SB_OHCI_REG2C, AccWidthUint32 | S3_SAVE, 0x00, pConfig->BuildParameters.OhciSsid);
334 //RPR recommended setting to, enable fix to cover the corner case S3 wake up issue from some USB 1.1 devices
335 //OHCI 0_PCI_Config 0x50[30] = 1
336 RWPCI ((UINT32) Value + SB_OHCI_REG50 + 3, AccWidthUint8 | S3_SAVE, ~BIT6, BIT6);
337 if ( pConfig->BuildParameters.UsbMsi) {
338 RWPCI ((UINT32) Value + SB_OHCI_REG40 + 1, AccWidthUint8 | S3_SAVE, ~BIT0, 0x00);
339 RWPCI ((UINT32) Value + SB_OHCI_REG50, AccWidthUint8 | S3_SAVE, ~BIT5, BIT5);
350 UINT32 ddRetureValue;
359 RWPCI ((UINT32) Value + 0xC4, AccWidthUint8, 0xF0, 0x00);
360 RWPCI ((UINT32) Value + 0x04, AccWidthUint8, 0xFF, 0x02);
362 ReadPCI ((UINT32) Value + 0x10, AccWidthUint32, &ddBarAddress);
363 for (portSC = 0x64; portSC < 0x75; portSC += 0x04 ) {
364 // Get OHCI command registers
365 ReadMEM (ddBarAddress + portSC, AccWidthUint16, &dwVar);
366 if ( dwVar & BIT6 ) {
367 ddRetureValue = ddBarAddress + portSC;
368 RWMEM (ddBarAddress + portSC, AccWidthUint16, ~BIT6, 0);
371 ReadMEM (ddBarAddress + portSC, AccWidthUint16, &dwData);
372 if (dwData == 0x1005) break;
377 return ddRetureValue;
385 UINT32 resumeEhciPortTmp;
386 UINT32 resumeEhciPort;
387 resumeEhciPortTmp = 0;
389 // UINT32 ddDeviceId;
390 //if Force Port Resume == 1
392 // clear Force Port Resume;
393 // while (!(PORTSC == 0x1005)){wait 5 us; read PORTSC;}
395 if (pConfig->USBMODE.UsbModeReg & BIT1) {
396 resumeEhciPortTmp = SetEhciPllWr (USB1_EHCI_BUS_DEV_FUN << 16, pConfig);
397 if (resumeEhciPortTmp > 0) resumeEhciPort = resumeEhciPortTmp;
399 if (pConfig->USBMODE.UsbModeReg & BIT3) {
400 resumeEhciPortTmp = SetEhciPllWr (USB2_EHCI_BUS_DEV_FUN << 16, pConfig);
401 if (resumeEhciPortTmp > 0) resumeEhciPort = resumeEhciPortTmp;
403 if (pConfig->USBMODE.UsbModeReg & BIT5) {
404 resumeEhciPortTmp = SetEhciPllWr (USB3_EHCI_BUS_DEV_FUN << 16, pConfig);
405 if (resumeEhciPortTmp > 0) resumeEhciPort = resumeEhciPortTmp;
408 RWPCI ((UINT32) (USB1_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, 0);
409 RWPCI ((UINT32) (USB2_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, 0);
410 RWPCI ((UINT32) (USB3_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, 0);
411 RWPCI ((UINT32) (USB4_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, 0);
412 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGF3, AccWidthUint8, 0, 0x20);
414 RWMEM (ACPI_MMIO_BASE + PMIO_BASE + SB_PMIOA_REGF3, AccWidthUint8, 0, 0x00);
415 RWPCI ((UINT32) (USB1_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, BIT29);
416 RWPCI ((UINT32) (USB2_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, BIT29);
417 RWPCI ((UINT32) (USB3_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, BIT29);
418 RWPCI ((UINT32) (USB4_OHCI_BUS_DEV_FUN << 16) + SB_OHCI_REG50, AccWidthUint32, ~BIT29, BIT29);
420 if (resumeEhciPort > 0) {
421 RWMEM (resumeEhciPort, AccWidthUint8, ~BIT7, BIT7);
423 RWMEM (resumeEhciPort, AccWidthUint8, ~BIT6, BIT6);
426 RWPCI ((UINT32) (USB1_EHCI_BUS_DEV_FUN << 16) + 0xC4, AccWidthUint8, 0xF0, 0x03);
427 RWPCI ((UINT32) (USB2_EHCI_BUS_DEV_FUN << 16) + 0xC4, AccWidthUint8, 0xF0, 0x03);
428 RWPCI ((UINT32) (USB3_EHCI_BUS_DEV_FUN << 16) + 0xC4, AccWidthUint8, 0xF0, 0x03);