xref: /haiku/src/add-ons/kernel/bus_managers/mmc/mmc_module.cpp (revision 2413679304fcb529e27d1aff39aeae8ef57fc32c)
125b6a6f1Skrish_iyer /*
27a160a86SAdrien Destugues  * Copyright 2018-2021 Haiku, Inc. All rights reserved.
325b6a6f1Skrish_iyer  * Distributed under the terms of the MIT License.
425b6a6f1Skrish_iyer  *
525b6a6f1Skrish_iyer  * Authors:
625b6a6f1Skrish_iyer  *		B Krishnan Iyer, krishnaniyer97@gmail.com
77a160a86SAdrien Destugues  *		Adrien Destugues, pulkomandy@pulkomandy.tk
825b6a6f1Skrish_iyer  */
925b6a6f1Skrish_iyer #include "mmc_bus.h"
1025b6a6f1Skrish_iyer 
1125b6a6f1Skrish_iyer 
12ff76d2dfSAdrien Destugues #define	MMC_BUS_DEVICE_NAME "bus_managers/mmc_bus/device/v1"
13ff76d2dfSAdrien Destugues 
14ff76d2dfSAdrien Destugues 
1525b6a6f1Skrish_iyer device_manager_info* gDeviceManager = NULL;
1625b6a6f1Skrish_iyer 
1725b6a6f1Skrish_iyer 
1825b6a6f1Skrish_iyer static status_t
1925b6a6f1Skrish_iyer mmc_bus_init(device_node* node, void** _device)
2025b6a6f1Skrish_iyer {
2125b6a6f1Skrish_iyer 	CALLED();
2225b6a6f1Skrish_iyer 	MMCBus* device = new(std::nothrow) MMCBus(node);
2325b6a6f1Skrish_iyer 	if (device == NULL) {
2425b6a6f1Skrish_iyer 		ERROR("Unable to allocate MMC bus\n");
2525b6a6f1Skrish_iyer 		return B_NO_MEMORY;
2625b6a6f1Skrish_iyer 	}
2725b6a6f1Skrish_iyer 
2825b6a6f1Skrish_iyer 	status_t result = device->InitCheck();
2925b6a6f1Skrish_iyer 	if (result != B_OK) {
3025b6a6f1Skrish_iyer 		TRACE("failed to set up mmc bus device object\n");
3125b6a6f1Skrish_iyer 		return result;
3225b6a6f1Skrish_iyer 	}
3325b6a6f1Skrish_iyer 	TRACE("MMC bus object created\n");
3425b6a6f1Skrish_iyer 
3525b6a6f1Skrish_iyer 	*_device = device;
3625b6a6f1Skrish_iyer 	return B_OK;
3725b6a6f1Skrish_iyer }
3825b6a6f1Skrish_iyer 
3925b6a6f1Skrish_iyer 
4025b6a6f1Skrish_iyer static void
4125b6a6f1Skrish_iyer mmc_bus_uninit(void* _device)
4225b6a6f1Skrish_iyer {
4325b6a6f1Skrish_iyer 	CALLED();
4425b6a6f1Skrish_iyer 	MMCBus* device = (MMCBus*)_device;
4525b6a6f1Skrish_iyer 	delete device;
4625b6a6f1Skrish_iyer }
4725b6a6f1Skrish_iyer 
4825b6a6f1Skrish_iyer 
49dedbe94eSAdrien Destugues static status_t
50dedbe94eSAdrien Destugues mmc_bus_register_child(void* _device)
51dedbe94eSAdrien Destugues {
52*24136793SAdrien Destugues 	// Nothing to do, child devices are registered by the scanning thread
53dedbe94eSAdrien Destugues 	return B_OK;
54dedbe94eSAdrien Destugues }
55dedbe94eSAdrien Destugues 
56dedbe94eSAdrien Destugues 
5725b6a6f1Skrish_iyer static void
5825b6a6f1Skrish_iyer mmc_bus_removed(void* _device)
5925b6a6f1Skrish_iyer {
6025b6a6f1Skrish_iyer 	CALLED();
6125b6a6f1Skrish_iyer }
6225b6a6f1Skrish_iyer 
6325b6a6f1Skrish_iyer 
6425b6a6f1Skrish_iyer status_t
6525b6a6f1Skrish_iyer mmc_bus_added_device(device_node* parent)
6625b6a6f1Skrish_iyer {
6725b6a6f1Skrish_iyer 	CALLED();
6825b6a6f1Skrish_iyer 
6925b6a6f1Skrish_iyer 	device_attr attributes[] = {
70dedbe94eSAdrien Destugues 		{ B_DEVICE_BUS, B_STRING_TYPE, { string: "mmc"}},
71dedbe94eSAdrien Destugues 		{ B_DEVICE_PRETTY_NAME, B_STRING_TYPE, { string: "MMC bus root"}},
7225b6a6f1Skrish_iyer 		{ NULL }
7325b6a6f1Skrish_iyer 	};
7425b6a6f1Skrish_iyer 
75ff76d2dfSAdrien Destugues 	return gDeviceManager->register_node(parent, MMC_BUS_DEVICE_NAME,
7625b6a6f1Skrish_iyer 		attributes, NULL, NULL);
7725b6a6f1Skrish_iyer }
7825b6a6f1Skrish_iyer 
7925b6a6f1Skrish_iyer 
8025b6a6f1Skrish_iyer static status_t
8162eaf4c0SAdrien Destugues mmc_bus_execute_command(device_node* node, uint8_t command, uint32_t argument,
8262eaf4c0SAdrien Destugues 	uint32_t* result)
8362eaf4c0SAdrien Destugues {
8474b60970SAnarchos 	// FIXME store the parent cookie in the bus cookie or something instead of
8574b60970SAnarchos 	// getting/putting the parent each time.
8674b60970SAnarchos 	driver_module_info* mmc;
8762eaf4c0SAdrien Destugues 	void* cookie;
8862eaf4c0SAdrien Destugues 
8962eaf4c0SAdrien Destugues 	TRACE("In mmc_bus_execute_command\n");
9062eaf4c0SAdrien Destugues 	device_node* parent = gDeviceManager->get_parent_node(node);
9174b60970SAnarchos 	gDeviceManager->get_driver(parent, &mmc, &cookie);
9262eaf4c0SAdrien Destugues 	gDeviceManager->put_node(parent);
9362eaf4c0SAdrien Destugues 
9474b60970SAnarchos 	MMCBus* bus = (MMCBus*)cookie;
9574b60970SAnarchos 
9674b60970SAnarchos 	bus->AcquireBus();
9774b60970SAnarchos 	status_t error = bus->ExecuteCommand(command, argument, result);
9874b60970SAnarchos 	bus->ReleaseBus();
9974b60970SAnarchos 	return error;
10074b60970SAnarchos }
10174b60970SAnarchos 
10274b60970SAnarchos 
10374b60970SAnarchos static status_t
1049a37366bSAdrien Destugues mmc_bus_do_io(device_node* node, uint16_t rca, uint8_t command,
105d1fee57dSAdrien Destugues 	IOOperation* operation, bool offsetAsSectors)
10674b60970SAnarchos {
10774b60970SAnarchos 	driver_module_info* mmc;
10874b60970SAnarchos 	void* cookie;
10974b60970SAnarchos 
1107a160a86SAdrien Destugues 	// FIXME store the parent cookie in the bus cookie or something instead of
1117a160a86SAdrien Destugues 	// getting/putting the parent each time.
11274b60970SAnarchos 	device_node* parent = gDeviceManager->get_parent_node(node);
11374b60970SAnarchos 	gDeviceManager->get_driver(parent, &mmc, &cookie);
11474b60970SAnarchos 	gDeviceManager->put_node(parent);
11574b60970SAnarchos 
11674b60970SAnarchos 	MMCBus* bus = (MMCBus*)cookie;
11774b60970SAnarchos 	bus->AcquireBus();
1187a160a86SAdrien Destugues 	status_t result = B_OK;
1197a160a86SAdrien Destugues 
120d1fee57dSAdrien Destugues 	result = bus->DoIO(rca, command, operation, offsetAsSectors);
1217a160a86SAdrien Destugues 
12274b60970SAnarchos 	bus->ReleaseBus();
12374b60970SAnarchos 	return result;
12462eaf4c0SAdrien Destugues }
12562eaf4c0SAdrien Destugues 
12662eaf4c0SAdrien Destugues 
12762eaf4c0SAdrien Destugues static status_t
12825b6a6f1Skrish_iyer std_ops(int32 op, ...)
12925b6a6f1Skrish_iyer {
13025b6a6f1Skrish_iyer 	switch (op) {
13125b6a6f1Skrish_iyer 		case B_MODULE_INIT:
13225b6a6f1Skrish_iyer 			// Nothing to do
13325b6a6f1Skrish_iyer 		case B_MODULE_UNINIT:
13425b6a6f1Skrish_iyer 			return B_OK;
13525b6a6f1Skrish_iyer 
13625b6a6f1Skrish_iyer 		default:
13725b6a6f1Skrish_iyer 			break;
13825b6a6f1Skrish_iyer 	}
13925b6a6f1Skrish_iyer 
14025b6a6f1Skrish_iyer 	return B_ERROR;
14125b6a6f1Skrish_iyer }
14225b6a6f1Skrish_iyer 
14325b6a6f1Skrish_iyer 
14425b6a6f1Skrish_iyer driver_module_info mmc_bus_device_module = {
14525b6a6f1Skrish_iyer 	{
146ff76d2dfSAdrien Destugues 		MMC_BUS_DEVICE_NAME,
14725b6a6f1Skrish_iyer 		0,
14825b6a6f1Skrish_iyer 		std_ops
14925b6a6f1Skrish_iyer 	},
15025b6a6f1Skrish_iyer 	NULL, // supported devices
15125b6a6f1Skrish_iyer 	NULL, // register node
15225b6a6f1Skrish_iyer 	mmc_bus_init,
15325b6a6f1Skrish_iyer 	mmc_bus_uninit,
154dedbe94eSAdrien Destugues 	mmc_bus_register_child,
15525b6a6f1Skrish_iyer 	NULL, // rescan
15625b6a6f1Skrish_iyer 	mmc_bus_removed,
15725b6a6f1Skrish_iyer 	NULL, // suspend
15825b6a6f1Skrish_iyer 	NULL // resume
15925b6a6f1Skrish_iyer };
16025b6a6f1Skrish_iyer 
16125b6a6f1Skrish_iyer 
16262eaf4c0SAdrien Destugues mmc_device_interface mmc_bus_controller_module = {
16362eaf4c0SAdrien Destugues 	{
16425b6a6f1Skrish_iyer 		{
165ff76d2dfSAdrien Destugues 			MMC_BUS_MODULE_NAME,
16625b6a6f1Skrish_iyer 			0,
16725b6a6f1Skrish_iyer 			&std_ops
16825b6a6f1Skrish_iyer 		},
16925b6a6f1Skrish_iyer 
17025b6a6f1Skrish_iyer 		NULL, // supported devices
17125b6a6f1Skrish_iyer 		mmc_bus_added_device,
17225b6a6f1Skrish_iyer 		NULL,
17325b6a6f1Skrish_iyer 		NULL,
17425b6a6f1Skrish_iyer 		NULL
17562eaf4c0SAdrien Destugues 	},
17674b60970SAnarchos 	mmc_bus_execute_command,
1777a160a86SAdrien Destugues 	mmc_bus_do_io
17825b6a6f1Skrish_iyer };
17925b6a6f1Skrish_iyer 
18025b6a6f1Skrish_iyer 
18125b6a6f1Skrish_iyer module_dependency module_dependencies[] = {
18225b6a6f1Skrish_iyer 	{ B_DEVICE_MANAGER_MODULE_NAME, (module_info **)&gDeviceManager },
18325b6a6f1Skrish_iyer 	{}
18425b6a6f1Skrish_iyer };
18525b6a6f1Skrish_iyer 
18625b6a6f1Skrish_iyer 
18725b6a6f1Skrish_iyer module_info* modules[] = {
18825b6a6f1Skrish_iyer 	(module_info*)&mmc_bus_controller_module,
18925b6a6f1Skrish_iyer 	(module_info*)&mmc_bus_device_module,
19025b6a6f1Skrish_iyer 	NULL
19125b6a6f1Skrish_iyer };
192