xref: /haiku/src/add-ons/kernel/bus_managers/mmc/mmc_bus.cpp (revision 52c4471a3024d2eb81fe88e2c3982b9f8daa5e56)
1 /*
2  * Copyright 2018-2020 Haiku, Inc. All rights reserved.
3  * Distributed under the terms of the MIT License.
4  *
5  * Authors:
6  *		B Krishnan Iyer, krishnaniyer97@gmail.com
7  */
8 #include "mmc_bus.h"
9 
10 #include <Errors.h>
11 
12 #include <stdint.h>
13 
14 
15 MMCBus::MMCBus(device_node* node)
16 	:
17 	fNode(node),
18 	fController(NULL),
19 	fCookie(NULL),
20 	fStatus(B_OK),
21 	fWorkerThread(-1),
22 	fActiveDevice(0)
23 {
24 	CALLED();
25 
26 	// Get the parent info, it includes the API to send commands to the hardware
27 	device_node* parent = gDeviceManager->get_parent_node(node);
28 	fStatus = gDeviceManager->get_driver(parent,
29 		(driver_module_info**)&fController, &fCookie);
30 	gDeviceManager->put_node(parent);
31 
32 	if (fStatus != B_OK) {
33 		ERROR("Not able to establish the bus %s\n",
34 			strerror(fStatus));
35 		return;
36 	}
37 
38 	fScanSemaphore = create_sem(0, "MMC bus scan");
39 	fLockSemaphore = create_sem(1, "MMC bus lock");
40 	fWorkerThread = spawn_kernel_thread(_WorkerThread, "SD bus controller",
41 		B_NORMAL_PRIORITY, this);
42 	resume_thread(fWorkerThread);
43 
44 	fController->set_scan_semaphore(fCookie, fScanSemaphore);
45 }
46 
47 
48 MMCBus::~MMCBus()
49 {
50 	CALLED();
51 
52 	// Tell the worker thread we want to stop
53 	fStatus = B_SHUTTING_DOWN;
54 
55 	// Delete the semaphores (this will unlock the worker thread if it was
56 	// waiting on them)
57 	delete_sem(fScanSemaphore);
58 	delete_sem(fLockSemaphore);
59 
60 	// Wait for the worker thread to terminate
61 	status_t result;
62 	if (fWorkerThread != 0)
63 		wait_for_thread(fWorkerThread, &result);
64 
65 	// TODO power off cards, stop clock, etc if needed.
66 }
67 
68 
69 status_t
70 MMCBus::InitCheck()
71 {
72 	return fStatus;
73 }
74 
75 
76 void
77 MMCBus::Rescan()
78 {
79 	// Just wake up the thread for a scan
80 	release_sem(fScanSemaphore);
81 }
82 
83 
84 status_t
85 MMCBus::ExecuteCommand(uint16_t rca, uint8_t command, uint32_t argument,
86 	uint32_t* response)
87 {
88 	status_t status = _ActivateDevice(rca);
89 	if (status != B_OK)
90 		return status;
91 	return fController->execute_command(fCookie, command, argument, response);
92 }
93 
94 
95 status_t
96 MMCBus::DoIO(uint16_t rca, uint8_t command, IOOperation* operation,
97 	bool offsetAsSectors)
98 {
99 	status_t status = _ActivateDevice(rca);
100 	if (status != B_OK)
101 		return status;
102 	return fController->do_io(fCookie, command, operation, offsetAsSectors);
103 }
104 
105 
106 void
107 MMCBus::SetClock(int frequency)
108 {
109 	fController->set_clock(fCookie, frequency);
110 }
111 
112 
113 void
114 MMCBus::SetBusWidth(int width)
115 {
116 	fController->set_bus_width(fCookie, width);
117 }
118 
119 
120 status_t
121 MMCBus::_ActivateDevice(uint16_t rca)
122 {
123 	// Do nothing if the device is already activated
124 	if (fActiveDevice == rca)
125 		return B_OK;
126 
127 	uint32_t response;
128 	status_t result;
129 	result = fController->execute_command(fCookie, SD_SELECT_DESELECT_CARD,
130 		((uint32)rca) << 16, &response);
131 
132 	if (result == B_OK)
133 		fActiveDevice = rca;
134 
135 	return result;
136 }
137 
138 
139 void MMCBus::_AcquireScanSemaphore()
140 {
141 	release_sem(fLockSemaphore);
142 	acquire_sem(fScanSemaphore);
143 	acquire_sem(fLockSemaphore);
144 }
145 
146 
147 status_t
148 MMCBus::_WorkerThread(void* cookie)
149 {
150 	MMCBus* bus = (MMCBus*)cookie;
151 	uint32_t response;
152 
153 	acquire_sem(bus->fLockSemaphore);
154 
155 	// We assume the bus defaults to 400kHz clock and has already powered on
156 	// cards.
157 
158 	// Reset all cards on the bus
159 	// This does not work if the bus has not been powered on yet (the command
160 	// will timeout), in that case we wait until asked to scan again when a
161 	// card has been inserted and powered on.
162 	status_t result;
163 	do {
164 		bus->_AcquireScanSemaphore();
165 
166 		// Check if we need to exit early (possible if the parent device did
167 		// not manage initialize itself correctly)
168 		if (bus->fStatus == B_SHUTTING_DOWN) {
169 			release_sem(bus->fLockSemaphore);
170 			return B_OK;
171 		}
172 
173 		TRACE("Reset the bus...\n");
174 		result = bus->ExecuteCommand(0, SD_GO_IDLE_STATE, 0, NULL);
175 		TRACE("CMD0 result: %s\n", strerror(result));
176 	} while (result != B_OK);
177 
178 	// Need to wait at least 8 clock cycles after CMD0 before sending the next
179 	// command. With the default 400kHz clock that would be 20 microseconds,
180 	// but we need to wait at least 20ms here, otherwise the next command times
181 	// out
182 	snooze(30000);
183 
184 	while (bus->fStatus != B_SHUTTING_DOWN) {
185 		TRACE("Scanning the bus\n");
186 
187 		// Use the low speed clock and 1bit bus width for scanning
188 		bus->SetClock(400);
189 		bus->SetBusWidth(1);
190 
191 		// Probe the voltage range
192 		enum {
193 			// Table 4-40 in physical layer specification v8.00
194 			// All other values are currently reserved
195 			HOST_27_36V = 1, //Host supplied voltage 2.7-3.6V
196 		};
197 
198 		// An arbitrary value, we just need to check that the response
199 		// containts the same.
200 		static const uint8 kVoltageCheckPattern = 0xAA;
201 
202 		// FIXME MMC cards will not reply to this! They expect CMD1 instead
203 		// SD v1 cards will also not reply, but we can proceed to ACMD41
204 		// If ACMD41 also does not work, it may be an SDIO card, too
205 		uint32_t probe = (HOST_27_36V << 8) | kVoltageCheckPattern;
206 		uint32_t hcs = 1 << 30;
207 		if (bus->ExecuteCommand(0, SD_SEND_IF_COND, probe, &response) != B_OK) {
208 			TRACE("Card does not implement CMD8, may be a V1 SD card\n");
209 			// Do not check for SDHC support in this case
210 			hcs = 0;
211 		} else if (response != probe) {
212 			ERROR("Card does not support voltage range (expected %x, "
213 				"reply %x)\n", probe, response);
214 			// TODO we should power off the bus in this case.
215 		}
216 
217 		// Probe OCR, waiting for card to become ready
218 		// We keep repeating ACMD41 until the card replies that it is
219 		// initialized.
220 		uint32_t ocr;
221 		do {
222 			uint32_t cardStatus;
223 			while (bus->ExecuteCommand(0, SD_APP_CMD, 0, &cardStatus)
224 					== B_BUSY) {
225 				ERROR("Card locked after CMD8...\n");
226 				snooze(1000000);
227 			}
228 			if ((cardStatus & 0xFFFF8000) != 0)
229 				ERROR("SD card reports error %x\n", cardStatus);
230 			if ((cardStatus & (1 << 5)) == 0)
231 				ERROR("Card did not enter ACMD mode\n");
232 
233 			bus->ExecuteCommand(0, SD_SEND_OP_COND, hcs | 0xFF8000, &ocr);
234 
235 			if ((ocr & (1 << 31)) == 0) {
236 				TRACE("Card is busy\n");
237 				snooze(100000);
238 			}
239 		} while (((ocr & (1 << 31)) == 0));
240 
241 		// FIXME this should be asked to each card, when there are multiple
242 		// ones. So ACMD41 should be moved inside the probing loop below?
243 		uint8_t cardType = CARD_TYPE_SD;
244 
245 		if ((ocr & hcs) != 0)
246 			cardType = CARD_TYPE_SDHC;
247 		if ((ocr & (1 << 29)) != 0)
248 			cardType = CARD_TYPE_UHS2;
249 		if ((ocr & (1 << 24)) != 0)
250 			TRACE("Card supports 1.8v");
251 		TRACE("Voltage range: %x\n", ocr & 0xFFFFFF);
252 
253 		// TODO send CMD11 to switch to low voltage mode if card supports it?
254 
255 		// We use CMD2 (ALL_SEND_CID) and CMD3 (SEND_RELATIVE_ADDR) to assign
256 		// an RCA to all cards. Initially all cards have an RCA of 0 and will
257 		// all receive CMD2. But only ne of them will reply (they do collision
258 		// detection while sending the CID in reply). We assign a new RCA to
259 		// that first card, and repeat the process with the remaining ones
260 		// until no one answers to CMD2. Then we know all cards have an RCA
261 		// (and a matching published device on our side).
262 		uint32_t cid[4];
263 
264 		while (bus->ExecuteCommand(0, SD_ALL_SEND_CID, 0, cid) == B_OK) {
265 			bus->ExecuteCommand(0, SD_SEND_RELATIVE_ADDR, 0, &response);
266 
267 			TRACE("RCA: %x Status: %x\n", response >> 16, response & 0xFFFF);
268 
269 			if ((response & 0xFF00) != 0x500) {
270 				TRACE("Card did not enter data state\n");
271 				// This probably means there are no more cards to scan on the
272 				// bus, so exit the loop.
273 				break;
274 			}
275 
276 			// The card now has an RCA and it entered the data phase, which
277 			// means our initializing job is over, we can pass it on to the
278 			// mmc_disk driver.
279 
280 			uint32_t vendor = cid[3] & 0xFFFFFF;
281 			char name[6] = {(char)(cid[2] >> 24), (char)(cid[2] >> 16),
282 				(char)(cid[2] >> 8), (char)cid[2], (char)(cid[1] >> 24), 0};
283 			uint32_t serial = (cid[1] << 16) | (cid[0] >> 16);
284 			uint16_t revision = (cid[1] >> 20) & 0xF;
285 			revision *= 100;
286 			revision += (cid[1] >> 16) & 0xF;
287 			uint8_t month = cid[0] & 0xF;
288 			uint16_t year = 2000 + ((cid[0] >> 4) & 0xFF);
289 			uint16_t rca = response >> 16;
290 
291 			device_attr attrs[] = {
292 				{ B_DEVICE_BUS, B_STRING_TYPE, {.string = "mmc" }},
293 				{ B_DEVICE_PRETTY_NAME, B_STRING_TYPE, {.string = "mmc device" }},
294 				{ B_DEVICE_VENDOR_ID, B_UINT32_TYPE, {.ui32 = vendor}},
295 				{ B_DEVICE_ID, B_STRING_TYPE, {.string = name}},
296 				{ B_DEVICE_UNIQUE_ID, B_UINT32_TYPE, {.ui32 = serial}},
297 				{ "mmc/revision", B_UINT16_TYPE, {.ui16 = revision}},
298 				{ "mmc/month", B_UINT8_TYPE, {.ui8 = month}},
299 				{ "mmc/year", B_UINT16_TYPE, {.ui16 = year}},
300 				{ kMmcRcaAttribute, B_UINT16_TYPE, {.ui16 = rca}},
301 				{ kMmcTypeAttribute, B_UINT8_TYPE, {.ui8 = cardType}},
302 				{}
303 			};
304 
305 			// publish child device for the card
306 			gDeviceManager->register_node(bus->fNode, MMC_BUS_MODULE_NAME,
307 				attrs, NULL, NULL);
308 		}
309 
310 		// TODO if there is a single card active, check if it supports CMD6
311 		// (spec version 1.10 or later in SCR). If it does, check if CMD6 can
312 		// enable high speed mode, use that to go to 50MHz instead of 25.
313 		bus->SetClock(25000);
314 
315 		// FIXME we also need to unpublish devices that are gone. Probably need
316 		// to "ping" all RCAs somehow? Or is there an interrupt we can look for
317 		// to detect added/removed cards?
318 
319 		// Wait for the next scan request
320 		// The thread will spend most of its time waiting here
321 		bus->_AcquireScanSemaphore();
322 	}
323 
324 	release_sem(bus->fLockSemaphore);
325 
326 	TRACE("poller thread terminating");
327 	return B_OK;
328 }
329