xref: /haiku/src/add-ons/kernel/drivers/network/ether/dec21xxx/glue.c (revision 4a55cc230cf7566cadcbb23b1928eefff8aea9a2)
1 /*
2  * Copyright 2011, Haiku, Inc. All Rights Reserved.
3  * Distributed under the terms of the MIT License.
4  *
5  * Author(s):
6  *		Axel Dörfler <axeld@pinc-software.de>
7  *		Siarzhuk Zharski <imker@gmx.li>
8  */
9 
10 
11 #include <sys/bus.h>
12 #include <sys/mutex.h>
13 #include <sys/systm.h>
14 #include <machine/bus.h>
15 #include <shared.h>
16 
17 #include "if_dcreg.h"
18 
19 
20 HAIKU_FBSD_DRIVERS_GLUE(dec21xxx);
21 HAIKU_DRIVER_REQUIREMENTS(0);
22 
23 
24 int check_disable_interrupts_dc(device_t dev);
25 void reenable_interrupts_dc(device_t dev);
26 
27 extern int check_disable_interrupts_de(device_t dev);
28 extern void reenable_interrupts_de(device_t dev);
29 
30 
31 extern driver_t *DRIVER_MODULE_NAME(dc, pci);
32 extern driver_t *DRIVER_MODULE_NAME(de, pci);
33 
34 status_t
35 __haiku_handle_fbsd_drivers_list(status_t (*handler)(driver_t *[], driver_t *[]))
36 {
37 	driver_t *drivers[] = {
38 		DRIVER_MODULE_NAME(dc, pci),
39 		DRIVER_MODULE_NAME(de, pci),
40 		NULL
41 	};
42 	return (*handler)(drivers, NULL);
43 }
44 
45 
46 extern driver_t *DRIVER_MODULE_NAME(acphy, miibus);
47 extern driver_t *DRIVER_MODULE_NAME(amphy, miibus);
48 extern driver_t *DRIVER_MODULE_NAME(dcphy, miibus);
49 extern driver_t *DRIVER_MODULE_NAME(pnphy, miibus);
50 extern driver_t *DRIVER_MODULE_NAME(ukphy, miibus);
51 
52 driver_t *
53 __haiku_select_miibus_driver(device_t dev)
54 {
55 	driver_t *drivers[] = {
56 		DRIVER_MODULE_NAME(acphy, miibus),
57 		DRIVER_MODULE_NAME(amphy, miibus),
58 		DRIVER_MODULE_NAME(dcphy, miibus),
59 		DRIVER_MODULE_NAME(pnphy, miibus),
60 		DRIVER_MODULE_NAME(ukphy, miibus),
61 		NULL
62 	};
63 
64 	return __haiku_probe_miibus(dev, drivers);
65 }
66 
67 
68 int
69 HAIKU_CHECK_DISABLE_INTERRUPTS(device_t dev)
70 {
71 	uint16 name = *(uint16*)dev->device_name;
72 	switch (name) {
73 		case 'cd':
74 			return check_disable_interrupts_dc(dev);
75 		case 'ed':
76 			return check_disable_interrupts_de(dev);
77 		default:
78 			break;
79 	}
80 
81 	panic("Unsupported device: %#x (%s)!", name, dev->device_name);
82 	return 0;
83 }
84 
85 
86 void
87 HAIKU_REENABLE_INTERRUPTS(device_t dev)
88 {
89 	uint16 name = *(uint16*)dev->device_name;
90 	switch (name) {
91 		case 'cd':
92 			reenable_interrupts_dc(dev);
93 			break;
94 		case 'ed':
95 			reenable_interrupts_de(dev);
96 			break;
97 		default:
98 			panic("Unsupported device: %#x (%s)!", name, dev->device_name);
99 			break;
100 	}
101 }
102 
103 
104 int
105 check_disable_interrupts_dc(device_t dev)
106 {
107 	struct dc_softc *sc = device_get_softc(dev);
108 	uint16_t status;
109 	HAIKU_INTR_REGISTER_STATE;
110 
111 	HAIKU_INTR_REGISTER_ENTER();
112 
113 	status = CSR_READ_4(sc, DC_ISR);
114 	if (status == 0xffff) {
115 		HAIKU_INTR_REGISTER_LEAVE();
116 		return 0;
117 	}
118 
119 	if (status != 0 && (status & DC_INTRS) == 0) {
120 		CSR_WRITE_4(sc, DC_ISR, status);
121 		HAIKU_INTR_REGISTER_LEAVE();
122 		return 0;
123 	}
124 
125 	if ((status & DC_INTRS) == 0) {
126 		HAIKU_INTR_REGISTER_LEAVE();
127 		return 0;
128 	}
129 
130 	CSR_WRITE_4(sc, DC_IMR, 0);
131 
132 	HAIKU_INTR_REGISTER_LEAVE();
133 
134 	return 1;
135 }
136 
137 
138 void
139 reenable_interrupts_dc(device_t dev)
140 {
141 	struct dc_softc *sc = device_get_softc(dev);
142 	DC_LOCK(sc);
143 	CSR_WRITE_4(sc, DC_IMR, DC_INTRS);
144 	DC_UNLOCK(sc);
145 }
146 
147