diff options
author | Chris Metcalf <cmetcalf@tilera.com> | 2012-04-07 16:53:03 -0400 |
---|---|---|
committer | Chris Metcalf <cmetcalf@tilera.com> | 2012-07-11 16:04:58 -0400 |
commit | bce5bbbb23f780a792be7e594af7cd4b4aae1cd4 (patch) | |
tree | d140d8badb0ed24f4ccc2f89266772ae6836f0f3 /arch/tile/gxio | |
parent | 10104a1ad670889adc1ae3779df968db621b5dbd (diff) |
arch/tile: provide kernel support for the tilegx TRIO shim
Provide kernel support for the tilegx "Transaction I/O" (TRIO) on-chip
hardware. This hardware implements the PCIe interface for tilegx;
the driver changes to use TRIO for PCIe are in a subsequent commit.
The change is layered on top of the tilegx GXIO IORPC subsystem.
Signed-off-by: Chris Metcalf <cmetcalf@tilera.com>
Diffstat (limited to 'arch/tile/gxio')
-rw-r--r-- | arch/tile/gxio/Kconfig | 6 | ||||
-rw-r--r-- | arch/tile/gxio/Makefile | 1 | ||||
-rw-r--r-- | arch/tile/gxio/iorpc_trio.c | 327 | ||||
-rw-r--r-- | arch/tile/gxio/trio.c | 49 |
4 files changed, 383 insertions, 0 deletions
diff --git a/arch/tile/gxio/Kconfig b/arch/tile/gxio/Kconfig index 8aeebb70a3df..68e1cca2cce5 100644 --- a/arch/tile/gxio/Kconfig +++ b/arch/tile/gxio/Kconfig | |||
@@ -15,3 +15,9 @@ config TILE_GXIO_MPIPE | |||
15 | bool | 15 | bool |
16 | select TILE_GXIO | 16 | select TILE_GXIO |
17 | select TILE_GXIO_DMA | 17 | select TILE_GXIO_DMA |
18 | |||
19 | # Support direct access to the TILE-Gx TRIO hardware from kernel space. | ||
20 | config TILE_GXIO_TRIO | ||
21 | bool | ||
22 | select TILE_GXIO | ||
23 | select TILE_GXIO_DMA | ||
diff --git a/arch/tile/gxio/Makefile b/arch/tile/gxio/Makefile index 130eec48c152..2389ef307c73 100644 --- a/arch/tile/gxio/Makefile +++ b/arch/tile/gxio/Makefile | |||
@@ -5,3 +5,4 @@ | |||
5 | obj-$(CONFIG_TILE_GXIO) += iorpc_globals.o kiorpc.o | 5 | obj-$(CONFIG_TILE_GXIO) += iorpc_globals.o kiorpc.o |
6 | obj-$(CONFIG_TILE_GXIO_DMA) += dma_queue.o | 6 | obj-$(CONFIG_TILE_GXIO_DMA) += dma_queue.o |
7 | obj-$(CONFIG_TILE_GXIO_MPIPE) += mpipe.o iorpc_mpipe.o iorpc_mpipe_info.o | 7 | obj-$(CONFIG_TILE_GXIO_MPIPE) += mpipe.o iorpc_mpipe.o iorpc_mpipe_info.o |
8 | obj-$(CONFIG_TILE_GXIO_TRIO) += trio.o iorpc_trio.o | ||
diff --git a/arch/tile/gxio/iorpc_trio.c b/arch/tile/gxio/iorpc_trio.c new file mode 100644 index 000000000000..cef4b2209cda --- /dev/null +++ b/arch/tile/gxio/iorpc_trio.c | |||
@@ -0,0 +1,327 @@ | |||
1 | /* | ||
2 | * Copyright 2012 Tilera Corporation. All Rights Reserved. | ||
3 | * | ||
4 | * This program is free software; you can redistribute it and/or | ||
5 | * modify it under the terms of the GNU General Public License | ||
6 | * as published by the Free Software Foundation, version 2. | ||
7 | * | ||
8 | * This program is distributed in the hope that it will be useful, but | ||
9 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
10 | * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or | ||
11 | * NON INFRINGEMENT. See the GNU General Public License for | ||
12 | * more details. | ||
13 | */ | ||
14 | |||
15 | /* This file is machine-generated; DO NOT EDIT! */ | ||
16 | #include "gxio/iorpc_trio.h" | ||
17 | |||
18 | struct alloc_asids_param { | ||
19 | unsigned int count; | ||
20 | unsigned int first; | ||
21 | unsigned int flags; | ||
22 | }; | ||
23 | |||
24 | int gxio_trio_alloc_asids(gxio_trio_context_t * context, unsigned int count, | ||
25 | unsigned int first, unsigned int flags) | ||
26 | { | ||
27 | struct alloc_asids_param temp; | ||
28 | struct alloc_asids_param *params = &temp; | ||
29 | |||
30 | params->count = count; | ||
31 | params->first = first; | ||
32 | params->flags = flags; | ||
33 | |||
34 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
35 | sizeof(*params), GXIO_TRIO_OP_ALLOC_ASIDS); | ||
36 | } | ||
37 | |||
38 | EXPORT_SYMBOL(gxio_trio_alloc_asids); | ||
39 | |||
40 | |||
41 | struct alloc_memory_maps_param { | ||
42 | unsigned int count; | ||
43 | unsigned int first; | ||
44 | unsigned int flags; | ||
45 | }; | ||
46 | |||
47 | int gxio_trio_alloc_memory_maps(gxio_trio_context_t * context, | ||
48 | unsigned int count, unsigned int first, | ||
49 | unsigned int flags) | ||
50 | { | ||
51 | struct alloc_memory_maps_param temp; | ||
52 | struct alloc_memory_maps_param *params = &temp; | ||
53 | |||
54 | params->count = count; | ||
55 | params->first = first; | ||
56 | params->flags = flags; | ||
57 | |||
58 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
59 | sizeof(*params), GXIO_TRIO_OP_ALLOC_MEMORY_MAPS); | ||
60 | } | ||
61 | |||
62 | EXPORT_SYMBOL(gxio_trio_alloc_memory_maps); | ||
63 | |||
64 | |||
65 | struct alloc_pio_regions_param { | ||
66 | unsigned int count; | ||
67 | unsigned int first; | ||
68 | unsigned int flags; | ||
69 | }; | ||
70 | |||
71 | int gxio_trio_alloc_pio_regions(gxio_trio_context_t * context, | ||
72 | unsigned int count, unsigned int first, | ||
73 | unsigned int flags) | ||
74 | { | ||
75 | struct alloc_pio_regions_param temp; | ||
76 | struct alloc_pio_regions_param *params = &temp; | ||
77 | |||
78 | params->count = count; | ||
79 | params->first = first; | ||
80 | params->flags = flags; | ||
81 | |||
82 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
83 | sizeof(*params), GXIO_TRIO_OP_ALLOC_PIO_REGIONS); | ||
84 | } | ||
85 | |||
86 | EXPORT_SYMBOL(gxio_trio_alloc_pio_regions); | ||
87 | |||
88 | struct init_pio_region_aux_param { | ||
89 | unsigned int pio_region; | ||
90 | unsigned int mac; | ||
91 | uint32_t bus_address_hi; | ||
92 | unsigned int flags; | ||
93 | }; | ||
94 | |||
95 | int gxio_trio_init_pio_region_aux(gxio_trio_context_t * context, | ||
96 | unsigned int pio_region, unsigned int mac, | ||
97 | uint32_t bus_address_hi, unsigned int flags) | ||
98 | { | ||
99 | struct init_pio_region_aux_param temp; | ||
100 | struct init_pio_region_aux_param *params = &temp; | ||
101 | |||
102 | params->pio_region = pio_region; | ||
103 | params->mac = mac; | ||
104 | params->bus_address_hi = bus_address_hi; | ||
105 | params->flags = flags; | ||
106 | |||
107 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
108 | sizeof(*params), GXIO_TRIO_OP_INIT_PIO_REGION_AUX); | ||
109 | } | ||
110 | |||
111 | EXPORT_SYMBOL(gxio_trio_init_pio_region_aux); | ||
112 | |||
113 | |||
114 | struct init_memory_map_mmu_aux_param { | ||
115 | unsigned int map; | ||
116 | unsigned long va; | ||
117 | uint64_t size; | ||
118 | unsigned int asid; | ||
119 | unsigned int mac; | ||
120 | uint64_t bus_address; | ||
121 | unsigned int node; | ||
122 | unsigned int order_mode; | ||
123 | }; | ||
124 | |||
125 | int gxio_trio_init_memory_map_mmu_aux(gxio_trio_context_t * context, | ||
126 | unsigned int map, unsigned long va, | ||
127 | uint64_t size, unsigned int asid, | ||
128 | unsigned int mac, uint64_t bus_address, | ||
129 | unsigned int node, | ||
130 | unsigned int order_mode) | ||
131 | { | ||
132 | struct init_memory_map_mmu_aux_param temp; | ||
133 | struct init_memory_map_mmu_aux_param *params = &temp; | ||
134 | |||
135 | params->map = map; | ||
136 | params->va = va; | ||
137 | params->size = size; | ||
138 | params->asid = asid; | ||
139 | params->mac = mac; | ||
140 | params->bus_address = bus_address; | ||
141 | params->node = node; | ||
142 | params->order_mode = order_mode; | ||
143 | |||
144 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
145 | sizeof(*params), | ||
146 | GXIO_TRIO_OP_INIT_MEMORY_MAP_MMU_AUX); | ||
147 | } | ||
148 | |||
149 | EXPORT_SYMBOL(gxio_trio_init_memory_map_mmu_aux); | ||
150 | |||
151 | struct get_port_property_param { | ||
152 | struct pcie_trio_ports_property trio_ports; | ||
153 | }; | ||
154 | |||
155 | int gxio_trio_get_port_property(gxio_trio_context_t * context, | ||
156 | struct pcie_trio_ports_property *trio_ports) | ||
157 | { | ||
158 | int __result; | ||
159 | struct get_port_property_param temp; | ||
160 | struct get_port_property_param *params = &temp; | ||
161 | |||
162 | __result = | ||
163 | hv_dev_pread(context->fd, 0, (HV_VirtAddr) params, sizeof(*params), | ||
164 | GXIO_TRIO_OP_GET_PORT_PROPERTY); | ||
165 | *trio_ports = params->trio_ports; | ||
166 | |||
167 | return __result; | ||
168 | } | ||
169 | |||
170 | EXPORT_SYMBOL(gxio_trio_get_port_property); | ||
171 | |||
172 | struct config_legacy_intr_param { | ||
173 | union iorpc_interrupt interrupt; | ||
174 | unsigned int mac; | ||
175 | unsigned int intx; | ||
176 | }; | ||
177 | |||
178 | int gxio_trio_config_legacy_intr(gxio_trio_context_t * context, int inter_x, | ||
179 | int inter_y, int inter_ipi, int inter_event, | ||
180 | unsigned int mac, unsigned int intx) | ||
181 | { | ||
182 | struct config_legacy_intr_param temp; | ||
183 | struct config_legacy_intr_param *params = &temp; | ||
184 | |||
185 | params->interrupt.kernel.x = inter_x; | ||
186 | params->interrupt.kernel.y = inter_y; | ||
187 | params->interrupt.kernel.ipi = inter_ipi; | ||
188 | params->interrupt.kernel.event = inter_event; | ||
189 | params->mac = mac; | ||
190 | params->intx = intx; | ||
191 | |||
192 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
193 | sizeof(*params), GXIO_TRIO_OP_CONFIG_LEGACY_INTR); | ||
194 | } | ||
195 | |||
196 | EXPORT_SYMBOL(gxio_trio_config_legacy_intr); | ||
197 | |||
198 | struct config_msi_intr_param { | ||
199 | union iorpc_interrupt interrupt; | ||
200 | unsigned int mac; | ||
201 | unsigned int mem_map; | ||
202 | uint64_t mem_map_base; | ||
203 | uint64_t mem_map_limit; | ||
204 | unsigned int asid; | ||
205 | }; | ||
206 | |||
207 | int gxio_trio_config_msi_intr(gxio_trio_context_t * context, int inter_x, | ||
208 | int inter_y, int inter_ipi, int inter_event, | ||
209 | unsigned int mac, unsigned int mem_map, | ||
210 | uint64_t mem_map_base, uint64_t mem_map_limit, | ||
211 | unsigned int asid) | ||
212 | { | ||
213 | struct config_msi_intr_param temp; | ||
214 | struct config_msi_intr_param *params = &temp; | ||
215 | |||
216 | params->interrupt.kernel.x = inter_x; | ||
217 | params->interrupt.kernel.y = inter_y; | ||
218 | params->interrupt.kernel.ipi = inter_ipi; | ||
219 | params->interrupt.kernel.event = inter_event; | ||
220 | params->mac = mac; | ||
221 | params->mem_map = mem_map; | ||
222 | params->mem_map_base = mem_map_base; | ||
223 | params->mem_map_limit = mem_map_limit; | ||
224 | params->asid = asid; | ||
225 | |||
226 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
227 | sizeof(*params), GXIO_TRIO_OP_CONFIG_MSI_INTR); | ||
228 | } | ||
229 | |||
230 | EXPORT_SYMBOL(gxio_trio_config_msi_intr); | ||
231 | |||
232 | |||
233 | struct set_mps_mrs_param { | ||
234 | uint16_t mps; | ||
235 | uint16_t mrs; | ||
236 | unsigned int mac; | ||
237 | }; | ||
238 | |||
239 | int gxio_trio_set_mps_mrs(gxio_trio_context_t * context, uint16_t mps, | ||
240 | uint16_t mrs, unsigned int mac) | ||
241 | { | ||
242 | struct set_mps_mrs_param temp; | ||
243 | struct set_mps_mrs_param *params = &temp; | ||
244 | |||
245 | params->mps = mps; | ||
246 | params->mrs = mrs; | ||
247 | params->mac = mac; | ||
248 | |||
249 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
250 | sizeof(*params), GXIO_TRIO_OP_SET_MPS_MRS); | ||
251 | } | ||
252 | |||
253 | EXPORT_SYMBOL(gxio_trio_set_mps_mrs); | ||
254 | |||
255 | struct force_rc_link_up_param { | ||
256 | unsigned int mac; | ||
257 | }; | ||
258 | |||
259 | int gxio_trio_force_rc_link_up(gxio_trio_context_t * context, unsigned int mac) | ||
260 | { | ||
261 | struct force_rc_link_up_param temp; | ||
262 | struct force_rc_link_up_param *params = &temp; | ||
263 | |||
264 | params->mac = mac; | ||
265 | |||
266 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
267 | sizeof(*params), GXIO_TRIO_OP_FORCE_RC_LINK_UP); | ||
268 | } | ||
269 | |||
270 | EXPORT_SYMBOL(gxio_trio_force_rc_link_up); | ||
271 | |||
272 | struct force_ep_link_up_param { | ||
273 | unsigned int mac; | ||
274 | }; | ||
275 | |||
276 | int gxio_trio_force_ep_link_up(gxio_trio_context_t * context, unsigned int mac) | ||
277 | { | ||
278 | struct force_ep_link_up_param temp; | ||
279 | struct force_ep_link_up_param *params = &temp; | ||
280 | |||
281 | params->mac = mac; | ||
282 | |||
283 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
284 | sizeof(*params), GXIO_TRIO_OP_FORCE_EP_LINK_UP); | ||
285 | } | ||
286 | |||
287 | EXPORT_SYMBOL(gxio_trio_force_ep_link_up); | ||
288 | |||
289 | struct get_mmio_base_param { | ||
290 | HV_PTE base; | ||
291 | }; | ||
292 | |||
293 | int gxio_trio_get_mmio_base(gxio_trio_context_t * context, HV_PTE *base) | ||
294 | { | ||
295 | int __result; | ||
296 | struct get_mmio_base_param temp; | ||
297 | struct get_mmio_base_param *params = &temp; | ||
298 | |||
299 | __result = | ||
300 | hv_dev_pread(context->fd, 0, (HV_VirtAddr) params, sizeof(*params), | ||
301 | GXIO_TRIO_OP_GET_MMIO_BASE); | ||
302 | *base = params->base; | ||
303 | |||
304 | return __result; | ||
305 | } | ||
306 | |||
307 | EXPORT_SYMBOL(gxio_trio_get_mmio_base); | ||
308 | |||
309 | struct check_mmio_offset_param { | ||
310 | unsigned long offset; | ||
311 | unsigned long size; | ||
312 | }; | ||
313 | |||
314 | int gxio_trio_check_mmio_offset(gxio_trio_context_t * context, | ||
315 | unsigned long offset, unsigned long size) | ||
316 | { | ||
317 | struct check_mmio_offset_param temp; | ||
318 | struct check_mmio_offset_param *params = &temp; | ||
319 | |||
320 | params->offset = offset; | ||
321 | params->size = size; | ||
322 | |||
323 | return hv_dev_pwrite(context->fd, 0, (HV_VirtAddr) params, | ||
324 | sizeof(*params), GXIO_TRIO_OP_CHECK_MMIO_OFFSET); | ||
325 | } | ||
326 | |||
327 | EXPORT_SYMBOL(gxio_trio_check_mmio_offset); | ||
diff --git a/arch/tile/gxio/trio.c b/arch/tile/gxio/trio.c new file mode 100644 index 000000000000..69f0b8df3ce3 --- /dev/null +++ b/arch/tile/gxio/trio.c | |||
@@ -0,0 +1,49 @@ | |||
1 | /* | ||
2 | * Copyright 2012 Tilera Corporation. All Rights Reserved. | ||
3 | * | ||
4 | * This program is free software; you can redistribute it and/or | ||
5 | * modify it under the terms of the GNU General Public License | ||
6 | * as published by the Free Software Foundation, version 2. | ||
7 | * | ||
8 | * This program is distributed in the hope that it will be useful, but | ||
9 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
10 | * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or | ||
11 | * NON INFRINGEMENT. See the GNU General Public License for | ||
12 | * more details. | ||
13 | */ | ||
14 | |||
15 | /* | ||
16 | * Implementation of trio gxio calls. | ||
17 | */ | ||
18 | |||
19 | #include <linux/errno.h> | ||
20 | #include <linux/io.h> | ||
21 | #include <linux/module.h> | ||
22 | |||
23 | #include <gxio/trio.h> | ||
24 | #include <gxio/iorpc_globals.h> | ||
25 | #include <gxio/iorpc_trio.h> | ||
26 | #include <gxio/kiorpc.h> | ||
27 | |||
28 | int gxio_trio_init(gxio_trio_context_t *context, unsigned int trio_index) | ||
29 | { | ||
30 | char file[32]; | ||
31 | int fd; | ||
32 | |||
33 | snprintf(file, sizeof(file), "trio/%d/iorpc", trio_index); | ||
34 | fd = hv_dev_open((HV_VirtAddr) file, 0); | ||
35 | if (fd < 0) { | ||
36 | context->fd = -1; | ||
37 | |||
38 | if (fd >= GXIO_ERR_MIN && fd <= GXIO_ERR_MAX) | ||
39 | return fd; | ||
40 | else | ||
41 | return -ENODEV; | ||
42 | } | ||
43 | |||
44 | context->fd = fd; | ||
45 | |||
46 | return 0; | ||
47 | } | ||
48 | |||
49 | EXPORT_SYMBOL_GPL(gxio_trio_init); | ||