make sure the arm implementation struct is aligned
[AROS.git] / arch / arm-native / soc / broadcom / 283x / sdcard / sdcard_bcm283xinit.c
blob99cbe9f91ff93b83991fe1253b1e575bddedde6b
1 /*
2 Copyright © 2013, The AROS Development Team. All rights reserved.
3 $Id$
4 */
6 #define DEBUG 0
7 #include <aros/debug.h>
9 #include <proto/exec.h>
10 #include <proto/vcmbox.h>
11 #include <proto/kernel.h>
13 #include <hardware/mmc.h>
14 #include <hardware/sdhc.h>
16 #include "sdcard_intern.h"
17 #include "timer.h"
19 #include <hardware/arasan.h>
20 #include <hardware/videocore.h>
22 APTR VCMBoxBase;
23 unsigned int VCMBoxMessage[8] __attribute__((used, aligned(16)));
24 IPTR __arm_periiobase __attribute__((used)) = 0 ;
26 static int FNAME_BCMSDC(BCM283xInit)(struct SDCardBase *SDCardBase)
28 struct sdcard_Bus *__BCM283xBus;
29 int retVal = FALSE;
31 DINIT(bug("[SDCard--] %s()\n", __PRETTY_FUNCTION__));
33 __arm_periiobase = KrnGetSystemAttr(KATTR_PeripheralBase);
35 if ((VCMBoxBase = OpenResource("vcmbox.resource")) == NULL)
37 bug("[SDCard--] %s: Failed to open vcmbox.resource\n", __PRETTY_FUNCTION__);
38 goto bcminit_fail;
41 VCMBoxMessage[0] = 8 * 4;
42 VCMBoxMessage[1] = VCTAG_REQ;
43 VCMBoxMessage[2] = VCTAG_GETPOWER;
44 VCMBoxMessage[3] = 8;
45 VCMBoxMessage[4] = 4;
46 VCMBoxMessage[5] = VCPOWER_SDHCI;
47 VCMBoxMessage[6] = 0;
49 VCMBoxMessage[7] = 0; // terminate tag
51 VCMBoxWrite((APTR)VCMB_BASE, VCMB_PROPCHAN, VCMBoxMessage);
52 if (VCMBoxRead((APTR)VCMB_BASE, VCMB_PROPCHAN) != VCMBoxMessage)
54 DINIT(bug("[SDCard--] %s: Failed to read controller's Power state\n", __PRETTY_FUNCTION__));
55 goto bcminit_fail;
58 if (!(VCMBoxMessage[6] & VCPOWER_STATE_ON))
60 DINIT(bug("[SDCard--] %s: Powering on Arasan SDHCI controller...\n", __PRETTY_FUNCTION__));
62 VCMBoxMessage[0] = 8 * 4;
63 VCMBoxMessage[1] = VCTAG_REQ;
64 VCMBoxMessage[2] = VCTAG_SETPOWER;
65 VCMBoxMessage[3] = 8;
66 VCMBoxMessage[4] = 8;
67 VCMBoxMessage[5] = VCPOWER_SDHCI;
68 VCMBoxMessage[6] = VCPOWER_STATE_ON | VCPOWER_STATE_WAIT;
70 VCMBoxMessage[7] = 0; // terminate tag
72 VCMBoxWrite((APTR)VCMB_BASE, VCMB_PROPCHAN, VCMBoxMessage);
73 if ((VCMBoxRead((APTR)VCMB_BASE, VCMB_PROPCHAN) != VCMBoxMessage) || (!(VCMBoxMessage[6] & VCPOWER_STATE_ON)))
75 DINIT(bug("[SDCard--] %s: Failed to power on controller\n", __PRETTY_FUNCTION__));
76 goto bcminit_fail;
80 VCMBoxMessage[0] = 8 * 4;
81 VCMBoxMessage[1] = VCTAG_REQ;
82 VCMBoxMessage[2] = VCTAG_GETCLKRATE;
83 VCMBoxMessage[3] = 8;
84 VCMBoxMessage[4] = 4;
85 VCMBoxMessage[5] = VCCLOCK_SDHCI;
86 VCMBoxMessage[6] = 0;
88 VCMBoxMessage[7] = 0; // terminate tag
90 VCMBoxWrite((APTR)VCMB_BASE, VCMB_PROPCHAN, VCMBoxMessage);
91 if (VCMBoxRead((APTR)VCMB_BASE, VCMB_PROPCHAN) != VCMBoxMessage)
93 DINIT(bug("[SDCard--] %s: Failed to determine Max SDHC Clock\n", __PRETTY_FUNCTION__));
94 goto bcminit_fail;
97 if ((__BCM283xBus = AllocPooled(SDCardBase->sdcard_MemPool, sizeof(struct sdcard_Bus))) != NULL)
99 __BCM283xBus->sdcb_DeviceBase = SDCardBase;
100 __BCM283xBus->sdcb_IOBase = (APTR)ARASAN_BASE;
101 __BCM283xBus->sdcb_BusIRQ = IRQ_VC_ARASANSDIO;
103 __BCM283xBus->sdcb_ClockMax = VCMBoxMessage[6];
104 __BCM283xBus->sdcb_ClockMin = BCM283xSDCLOCK_MIN;
106 __BCM283xBus->sdcb_LEDCtrl = FNAME_BCMSDCBUS(BCMLEDCtrl);
107 __BCM283xBus->sdcb_IOReadByte = FNAME_BCMSDCBUS(BCMMMIOReadByte);
108 __BCM283xBus->sdcb_IOReadWord = FNAME_BCMSDCBUS(BCMMMIOReadWord);
109 __BCM283xBus->sdcb_IOReadLong = FNAME_BCMSDCBUS(BCMMMIOReadLong);
111 __BCM283xBus->sdcb_IOWriteByte = FNAME_BCMSDCBUS(BCMMMIOWriteByte);
112 __BCM283xBus->sdcb_IOWriteWord = FNAME_BCMSDCBUS(BCMMMIOWriteWord);
113 __BCM283xBus->sdcb_IOWriteLong = FNAME_BCMSDCBUS(BCMMMIOWriteLong);
115 if ((__BCM283xBus->sdcb_BusUnits = AllocPooled(SDCardBase->sdcard_MemPool, sizeof(struct sdcard_BusUnits))) != NULL)
117 ObtainSemaphore(&SDCardBase->sdcard_BusSem);
118 __BCM283xBus->sdcb_BusUnits->sdcbu_UnitBase = SDCardBase->sdcard_TotalBusUnits;
119 __BCM283xBus->sdcb_BusUnits->sdcbu_UnitMax = BCM283xSDUNIT_MAX;
120 SDCardBase->sdcard_TotalBusUnits += __BCM283xBus->sdcb_BusUnits->sdcbu_UnitMax;
121 __BCM283xBus->sdcb_BusNum = SDCardBase->sdcard_BusCnt++;
122 ReleaseSemaphore(&SDCardBase->sdcard_BusSem);
124 DINIT(bug("[SDCard--] %s: Bus #%02u - %u Unit(s) starting from %02u\n", __PRETTY_FUNCTION__,
125 __BCM283xBus->sdcb_BusNum,
126 __BCM283xBus->sdcb_BusUnits->sdcbu_UnitMax,
127 __BCM283xBus->sdcb_BusUnits->sdcbu_UnitBase));
129 __BCM283xBus->sdcb_SectorShift = 9;
131 DINIT(bug("[SDCard--] %s: Reseting SDHCI...\n", __PRETTY_FUNCTION__));
133 FNAME_SDCBUS(SoftReset)(SDHCI_RESET_ALL, __BCM283xBus);
135 DINIT(bug("[SDCard--] %s: SDHC Max Clock Rate : %dMHz\n", __PRETTY_FUNCTION__, __BCM283xBus->sdcb_ClockMax / 1000000));
136 DINIT(bug("[SDCard--] %s: SDHC Min Clock Rate : %dHz (hardcoded)\n", __PRETTY_FUNCTION__, __BCM283xBus->sdcb_ClockMin));
138 __BCM283xBus->sdcb_Version = FNAME_BCMSDCBUS(BCMMMIOReadWord)(SDHCI_HOST_VERSION, __BCM283xBus);
139 __BCM283xBus->sdcb_Capabilities = FNAME_BCMSDCBUS(BCMMMIOReadLong)(SDHCI_CAPABILITIES, __BCM283xBus);
140 __BCM283xBus->sdcb_Quirks = AB_Quirk_MissingCapabilities|AF_Quirk_AtomicTMAndCMD;
141 __BCM283xBus->sdcb_Power = MMC_VDD_165_195 | MMC_VDD_320_330 | MMC_VDD_330_340;
143 DINIT(bug("[SDCard--] %s: SDHCI Host Vers : %d [SD Host Spec %d]\n", __PRETTY_FUNCTION__, ((__BCM283xBus->sdcb_Version & 0xFF00) >> 8), (__BCM283xBus->sdcb_Version & 0xFF) + 1));
144 DINIT(bug("[SDCard--] %s: SDHCI Capabilities : 0x%08x\n", __PRETTY_FUNCTION__, __BCM283xBus->sdcb_Capabilities));
145 DINIT(bug("[SDCard--] %s: SDHCI Voltages : 0x%08x (hardcoded)\n", __PRETTY_FUNCTION__, __BCM283xBus->sdcb_Power));
147 __BCM283xBus->sdcb_Private = (IPTR)sdcard_CurrentTime();
149 FNAME_SDC(RegisterBus)(__BCM283xBus, SDCardBase);
151 retVal = TRUE;
153 else
155 FreePooled(SDCardBase->sdcard_MemPool, __BCM283xBus, sizeof(struct sdcard_Bus));
158 bcminit_fail:
160 return retVal;
163 ADD2INITLIB(FNAME_BCMSDC(BCM283xInit), SDCARD_BUSINITPRIO)