xref: /netbsd-src/sys/arch/arm/xscale/i80321_space.c (revision 54816b7eeb06d08fae439cc7d3a90822da182dc5)
1*54816b7eSmacallan /*	$NetBSD: i80321_space.c,v 1.18 2018/11/21 19:03:18 macallan Exp $	*/
2f5362116Sthorpej 
3f5362116Sthorpej /*
4f5362116Sthorpej  * Copyright (c) 2001, 2002 Wasabi Systems, Inc.
5f5362116Sthorpej  * All rights reserved.
6f5362116Sthorpej  *
7f5362116Sthorpej  * Written by Jason R. Thorpe for Wasabi Systems, Inc.
8f5362116Sthorpej  *
9f5362116Sthorpej  * Redistribution and use in source and binary forms, with or without
10f5362116Sthorpej  * modification, are permitted provided that the following conditions
11f5362116Sthorpej  * are met:
12f5362116Sthorpej  * 1. Redistributions of source code must retain the above copyright
13f5362116Sthorpej  *    notice, this list of conditions and the following disclaimer.
14f5362116Sthorpej  * 2. Redistributions in binary form must reproduce the above copyright
15f5362116Sthorpej  *    notice, this list of conditions and the following disclaimer in the
16f5362116Sthorpej  *    documentation and/or other materials provided with the distribution.
17f5362116Sthorpej  * 3. All advertising materials mentioning features or use of this software
18f5362116Sthorpej  *    must display the following acknowledgement:
19f5362116Sthorpej  *	This product includes software developed for the NetBSD Project by
20f5362116Sthorpej  *	Wasabi Systems, Inc.
21f5362116Sthorpej  * 4. The name of Wasabi Systems, Inc. may not be used to endorse
22f5362116Sthorpej  *    or promote products derived from this software without specific prior
23f5362116Sthorpej  *    written permission.
24f5362116Sthorpej  *
25f5362116Sthorpej  * THIS SOFTWARE IS PROVIDED BY WASABI SYSTEMS, INC. ``AS IS'' AND
26f5362116Sthorpej  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
27f5362116Sthorpej  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
28f5362116Sthorpej  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL WASABI SYSTEMS, INC
29f5362116Sthorpej  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
30f5362116Sthorpej  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
31f5362116Sthorpej  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
32f5362116Sthorpej  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
33f5362116Sthorpej  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
34f5362116Sthorpej  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
35f5362116Sthorpej  * POSSIBILITY OF SUCH DAMAGE.
36f5362116Sthorpej  */
37f5362116Sthorpej 
38f5362116Sthorpej /*
39f5362116Sthorpej  * bus_space functions for i80321 I/O Processor.
40f5362116Sthorpej  */
41f5362116Sthorpej 
4208716eaeSlukem #include <sys/cdefs.h>
43*54816b7eSmacallan __KERNEL_RCSID(0, "$NetBSD: i80321_space.c,v 1.18 2018/11/21 19:03:18 macallan Exp $");
4408716eaeSlukem 
45f5362116Sthorpej #include <sys/param.h>
46f5362116Sthorpej #include <sys/systm.h>
47f5362116Sthorpej 
48f5362116Sthorpej #include <uvm/uvm_extern.h>
49f5362116Sthorpej 
50ed9977b1Sdyoung #include <sys/bus.h>
51f5362116Sthorpej 
52f5362116Sthorpej #include <arm/xscale/i80321reg.h>
53f5362116Sthorpej #include <arm/xscale/i80321var.h>
54f5362116Sthorpej 
55392aeaadSgavan #include "opt_i80321.h"
56392aeaadSgavan 
57f5362116Sthorpej /* Prototypes for all the bus_space structure functions */
58f5362116Sthorpej bs_protos(i80321);
59f5362116Sthorpej bs_protos(i80321_io);
60f5362116Sthorpej bs_protos(i80321_mem);
6180146a51Sthorpej bs_protos(generic);
6280146a51Sthorpej bs_protos(generic_armv4);
63f5362116Sthorpej bs_protos(bs_notimpl);
64f5362116Sthorpej 
65f5362116Sthorpej /*
66f5362116Sthorpej  * Template bus_space -- copied, and the bits that are NULL are
67f5362116Sthorpej  * filled in.
68f5362116Sthorpej  */
69f5362116Sthorpej const struct bus_space i80321_bs_tag_template = {
70f5362116Sthorpej 	/* cookie */
71509197b6Sryo 	.bs_cookie = (void *) 0,
72f5362116Sthorpej 
73f5362116Sthorpej 	/* mapping/unmapping */
74509197b6Sryo 	.bs_map = NULL,
75509197b6Sryo 	.bs_unmap = NULL,
76509197b6Sryo 	.bs_subregion = i80321_bs_subregion,
77f5362116Sthorpej 
78f5362116Sthorpej 	/* allocation/deallocation */
79509197b6Sryo 	.bs_alloc = NULL,
80509197b6Sryo 	.bs_free = NULL,
81f5362116Sthorpej 
82f5362116Sthorpej 	/* get kernel virtual address */
83509197b6Sryo 	.bs_vaddr = i80321_bs_vaddr,
84f5362116Sthorpej 
85f5362116Sthorpej 	/* mmap */
86509197b6Sryo 	.bs_mmap = i80321_bs_mmap,
87f5362116Sthorpej 
88f5362116Sthorpej 	/* barrier */
89509197b6Sryo 	.bs_barrier = i80321_bs_barrier,
90f5362116Sthorpej 
91f5362116Sthorpej 	/* read (single) */
92509197b6Sryo 	.bs_r_1 = generic_bs_r_1,
93509197b6Sryo 	.bs_r_2 = generic_armv4_bs_r_2,
94509197b6Sryo 	.bs_r_4 = generic_bs_r_4,
95509197b6Sryo 	.bs_r_8 = bs_notimpl_bs_r_8,
96f5362116Sthorpej 
9760617b8eSmacallan #ifdef __BUS_SPACE_HAS_STREAM_METHODS
9860617b8eSmacallan 	/* read (single, stream) */
9960617b8eSmacallan 	.bs_r_1_s = generic_bs_r_1,
10060617b8eSmacallan 	.bs_r_2_s = generic_armv4_bs_r_2,
10160617b8eSmacallan 	.bs_r_4_s = generic_bs_r_4,
10260617b8eSmacallan 	.bs_r_8_s = bs_notimpl_bs_r_8,
10360617b8eSmacallan #endif
10460617b8eSmacallan 
105f5362116Sthorpej 	/* read multiple */
106509197b6Sryo 	.bs_rm_1 = generic_bs_rm_1,
107509197b6Sryo 	.bs_rm_2 = generic_armv4_bs_rm_2,
108509197b6Sryo 	.bs_rm_4 = generic_bs_rm_4,
109509197b6Sryo 	.bs_rm_8 = bs_notimpl_bs_rm_8,
110f5362116Sthorpej 
11160617b8eSmacallan #ifdef __BUS_SPACE_HAS_STREAM_METHODS
11260617b8eSmacallan 	/* read multiple, stream */
11360617b8eSmacallan 	.bs_rm_1_s = generic_bs_rm_1,
11460617b8eSmacallan 	.bs_rm_2_s = generic_armv4_bs_rm_2,
11560617b8eSmacallan 	.bs_rm_4_s = generic_bs_rm_4,
11660617b8eSmacallan 	.bs_rm_8_s = bs_notimpl_bs_rm_8,
11760617b8eSmacallan #endif
11860617b8eSmacallan 
119f5362116Sthorpej 	/* read region */
120509197b6Sryo 	.bs_rr_1 = generic_bs_rr_1,
121509197b6Sryo 	.bs_rr_2 = generic_armv4_bs_rr_2,
122509197b6Sryo 	.bs_rr_4 = generic_bs_rr_4,
123509197b6Sryo 	.bs_rr_8 = bs_notimpl_bs_rr_8,
124f5362116Sthorpej 
12560617b8eSmacallan #ifdef __BUS_SPACE_HAS_STREAM_METHODS
12660617b8eSmacallan 	/* read region, stream */
12760617b8eSmacallan 	.bs_rr_1_s = generic_bs_rr_1,
12860617b8eSmacallan 	.bs_rr_2_s = generic_armv4_bs_rr_2,
12960617b8eSmacallan 	.bs_rr_4_s = generic_bs_rr_4,
13060617b8eSmacallan 	.bs_rr_8_s = bs_notimpl_bs_rr_8,
13160617b8eSmacallan #endif
13260617b8eSmacallan 
133f5362116Sthorpej 	/* write (single) */
134509197b6Sryo 	.bs_w_1 = generic_bs_w_1,
135509197b6Sryo 	.bs_w_2 = generic_armv4_bs_w_2,
136509197b6Sryo 	.bs_w_4 = generic_bs_w_4,
137509197b6Sryo 	.bs_w_8 = bs_notimpl_bs_w_8,
138f5362116Sthorpej 
13960617b8eSmacallan #ifdef __BUS_SPACE_HAS_STREAM_METHODS
14060617b8eSmacallan 	/* write (single, stream) */
14160617b8eSmacallan 	.bs_w_1_s = generic_bs_w_1,
14260617b8eSmacallan 	.bs_w_2_s = generic_armv4_bs_w_2,
14360617b8eSmacallan 	.bs_w_4_s = generic_bs_w_4,
14460617b8eSmacallan 	.bs_w_8_s = bs_notimpl_bs_w_8,
14560617b8eSmacallan #endif
14660617b8eSmacallan 
147f5362116Sthorpej 	/* write multiple */
148509197b6Sryo 	.bs_wm_1 = generic_bs_wm_1,
149509197b6Sryo 	.bs_wm_2 = generic_armv4_bs_wm_2,
150509197b6Sryo 	.bs_wm_4 = generic_bs_wm_4,
151509197b6Sryo 	.bs_wm_8 = bs_notimpl_bs_wm_8,
152f5362116Sthorpej 
15360617b8eSmacallan #ifdef __BUS_SPACE_HAS_STREAM_METHODS
15460617b8eSmacallan 	/* write multiple, stream */
15560617b8eSmacallan 	.bs_wm_1_s = generic_bs_wm_1,
15660617b8eSmacallan 	.bs_wm_2_s = generic_armv4_bs_wm_2,
15760617b8eSmacallan 	.bs_wm_4_s = generic_bs_wm_4,
15860617b8eSmacallan 	.bs_wm_8_s = bs_notimpl_bs_wm_8,
15960617b8eSmacallan #endif
16060617b8eSmacallan 
161f5362116Sthorpej 	/* write region */
162509197b6Sryo 	.bs_wr_1 = generic_bs_wr_1,
163509197b6Sryo 	.bs_wr_2 = generic_armv4_bs_wr_2,
164509197b6Sryo 	.bs_wr_4 = generic_bs_wr_4,
165509197b6Sryo 	.bs_wr_8 = bs_notimpl_bs_wr_8,
166f5362116Sthorpej 
16760617b8eSmacallan #ifdef __BUS_SPACE_HAS_STREAM_METHODS
16860617b8eSmacallan 	/* write region, stream */
16960617b8eSmacallan 	.bs_wr_1_s = generic_bs_wr_1,
17060617b8eSmacallan 	.bs_wr_2_s = generic_armv4_bs_wr_2,
17160617b8eSmacallan 	.bs_wr_4_s = generic_bs_wr_4,
17260617b8eSmacallan 	.bs_wr_8_s = bs_notimpl_bs_wr_8,
17360617b8eSmacallan #endif
17460617b8eSmacallan 
175f5362116Sthorpej 	/* set multiple */
176509197b6Sryo 	.bs_sm_1 = bs_notimpl_bs_sm_1,
177509197b6Sryo 	.bs_sm_2 = bs_notimpl_bs_sm_2,
178509197b6Sryo 	.bs_sm_4 = bs_notimpl_bs_sm_4,
179509197b6Sryo 	.bs_sm_8 = bs_notimpl_bs_sm_8,
180f5362116Sthorpej 
181f5362116Sthorpej 	/* set region */
182509197b6Sryo 	.bs_sr_1 = bs_notimpl_bs_sr_1,
183509197b6Sryo 	.bs_sr_2 = generic_armv4_bs_sr_2,
184509197b6Sryo 	.bs_sr_4 = generic_bs_sr_4,
185509197b6Sryo 	.bs_sr_8 = bs_notimpl_bs_sr_8,
186f5362116Sthorpej 
187f5362116Sthorpej 	/* copy */
188509197b6Sryo 	.bs_c_1 = bs_notimpl_bs_c_1,
189509197b6Sryo 	.bs_c_2 = generic_armv4_bs_c_2,
190509197b6Sryo 	.bs_c_4 = bs_notimpl_bs_c_4,
191509197b6Sryo 	.bs_c_8 = bs_notimpl_bs_c_8,
192f5362116Sthorpej };
193f5362116Sthorpej 
194f5362116Sthorpej void
i80321_bs_init(bus_space_tag_t bs,void * cookie)195f5362116Sthorpej i80321_bs_init(bus_space_tag_t bs, void *cookie)
196f5362116Sthorpej {
197f5362116Sthorpej 
198f5362116Sthorpej 	*bs = i80321_bs_tag_template;
199f5362116Sthorpej 	bs->bs_cookie = cookie;
200f5362116Sthorpej }
201f5362116Sthorpej 
202f5362116Sthorpej void
i80321_io_bs_init(bus_space_tag_t bs,void * cookie)203f5362116Sthorpej i80321_io_bs_init(bus_space_tag_t bs, void *cookie)
204f5362116Sthorpej {
205f5362116Sthorpej 
206f5362116Sthorpej 	*bs = i80321_bs_tag_template;
207f5362116Sthorpej 	bs->bs_cookie = cookie;
208f5362116Sthorpej 
209f5362116Sthorpej 	bs->bs_map = i80321_io_bs_map;
210f5362116Sthorpej 	bs->bs_unmap = i80321_io_bs_unmap;
211f5362116Sthorpej 	bs->bs_alloc = i80321_io_bs_alloc;
212f5362116Sthorpej 	bs->bs_free = i80321_io_bs_free;
213f5362116Sthorpej 
214f5362116Sthorpej 	bs->bs_vaddr = i80321_io_bs_vaddr;
21560617b8eSmacallan 	bs->bs_mmap = i80321_io_bs_mmap;
216f5362116Sthorpej }
217f5362116Sthorpej 
218f5362116Sthorpej void
i80321_mem_bs_init(bus_space_tag_t bs,void * cookie)219f5362116Sthorpej i80321_mem_bs_init(bus_space_tag_t bs, void *cookie)
220f5362116Sthorpej {
221f5362116Sthorpej 
222f5362116Sthorpej 	*bs = i80321_bs_tag_template;
223f5362116Sthorpej 	bs->bs_cookie = cookie;
224f5362116Sthorpej 
225f5362116Sthorpej 	bs->bs_map = i80321_mem_bs_map;
226f5362116Sthorpej 	bs->bs_unmap = i80321_mem_bs_unmap;
227f5362116Sthorpej 	bs->bs_alloc = i80321_mem_bs_alloc;
228f5362116Sthorpej 	bs->bs_free = i80321_mem_bs_free;
229f5362116Sthorpej 	bs->bs_mmap = i80321_mem_bs_mmap;
230f5362116Sthorpej }
231f5362116Sthorpej 
232f5362116Sthorpej /* *** Routines shared by i80321, PCI IO, and PCI MEM. *** */
233f5362116Sthorpej 
234f5362116Sthorpej int
i80321_bs_subregion(void * t,bus_space_handle_t bsh,bus_size_t offset,bus_size_t size,bus_space_handle_t * nbshp)235f5362116Sthorpej i80321_bs_subregion(void *t, bus_space_handle_t bsh, bus_size_t offset,
236f5362116Sthorpej     bus_size_t size, bus_space_handle_t *nbshp)
237f5362116Sthorpej {
238f5362116Sthorpej 
239f5362116Sthorpej 	*nbshp = bsh + offset;
240f5362116Sthorpej 	return (0);
241f5362116Sthorpej }
242f5362116Sthorpej 
243f5362116Sthorpej void
i80321_bs_barrier(void * t,bus_space_handle_t bsh,bus_size_t offset,bus_size_t len,int flags)244f5362116Sthorpej i80321_bs_barrier(void *t, bus_space_handle_t bsh, bus_size_t offset,
245f5362116Sthorpej     bus_size_t len, int flags)
246f5362116Sthorpej {
247f5362116Sthorpej 
248f5362116Sthorpej 	/* Nothing to do. */
249f5362116Sthorpej }
250f5362116Sthorpej 
251f5362116Sthorpej void *
i80321_bs_vaddr(void * t,bus_space_handle_t bsh)252f5362116Sthorpej i80321_bs_vaddr(void *t, bus_space_handle_t bsh)
253f5362116Sthorpej {
254f5362116Sthorpej 
255f5362116Sthorpej 	return ((void *)bsh);
256f5362116Sthorpej }
257f5362116Sthorpej 
258f5362116Sthorpej paddr_t
i80321_bs_mmap(void * t,bus_addr_t addr,off_t off,int prot,int flags)259f5362116Sthorpej i80321_bs_mmap(void *t, bus_addr_t addr, off_t off, int prot, int flags)
260f5362116Sthorpej {
261f5362116Sthorpej 
262f5362116Sthorpej 	/* Not supported. */
263f5362116Sthorpej 	return (-1);
264f5362116Sthorpej }
265f5362116Sthorpej 
266f5362116Sthorpej /* *** Routines for PCI IO. *** */
267f5362116Sthorpej 
268f5362116Sthorpej int
i80321_io_bs_map(void * t,bus_addr_t bpa,bus_size_t size,int flags,bus_space_handle_t * bshp)269f5362116Sthorpej i80321_io_bs_map(void *t, bus_addr_t bpa, bus_size_t size, int flags,
270f5362116Sthorpej     bus_space_handle_t *bshp)
271f5362116Sthorpej {
272f5362116Sthorpej 	struct i80321_softc *sc = t;
273f5362116Sthorpej 	vaddr_t winvaddr;
274f5362116Sthorpej 	uint32_t busbase;
275f5362116Sthorpej 
276f5362116Sthorpej 	if (bpa >= sc->sc_ioout_xlate &&
277f5362116Sthorpej 	    bpa < (sc->sc_ioout_xlate + VERDE_OUT_XLATE_IO_WIN_SIZE)) {
278f5362116Sthorpej 		busbase = sc->sc_ioout_xlate;
279f5362116Sthorpej 		winvaddr = sc->sc_iow_vaddr;
280f5362116Sthorpej 	} else
281f5362116Sthorpej 		return (EINVAL);
282f5362116Sthorpej 
283f5362116Sthorpej 	if ((bpa + size) >= (busbase + VERDE_OUT_XLATE_IO_WIN_SIZE))
284f5362116Sthorpej 		return (EINVAL);
285f5362116Sthorpej 
286f5362116Sthorpej 	/*
287f5362116Sthorpej 	 * Found the window -- PCI I/O space is mapped at a fixed
288f5362116Sthorpej 	 * virtual address by board-specific code.  Translate the
289f5362116Sthorpej 	 * bus address to the virtual address.
290f5362116Sthorpej 	 */
291f5362116Sthorpej 	*bshp = winvaddr + (bpa - busbase);
292f5362116Sthorpej 
293f5362116Sthorpej 	return (0);
294f5362116Sthorpej }
295f5362116Sthorpej 
29660617b8eSmacallan paddr_t
i80321_io_bs_mmap(void * t,bus_addr_t addr,off_t off,int prot,int flags)29760617b8eSmacallan i80321_io_bs_mmap(void *t, bus_addr_t addr, off_t off, int prot, int flags)
29860617b8eSmacallan {
29960617b8eSmacallan 	struct i80321_softc *sc = t;
30060617b8eSmacallan 	paddr_t bpa = addr + off, winpaddr, busbase;
30160617b8eSmacallan 
30260617b8eSmacallan 	if (bpa >= sc->sc_ioout_xlate &&
30360617b8eSmacallan 	    bpa < (sc->sc_ioout_xlate + VERDE_OUT_XLATE_IO_WIN_SIZE)) {
30460617b8eSmacallan 		busbase = sc->sc_ioout_xlate;
30560617b8eSmacallan 		winpaddr = VERDE_OUT_XLATE_IO_WIN0_BASE;
30660617b8eSmacallan 	} else
30731997526Sthorpej 		return (-1);
30860617b8eSmacallan 
30960617b8eSmacallan 	return (arm_btop(winpaddr + (bpa - busbase)));
31060617b8eSmacallan }
31160617b8eSmacallan 
312f5362116Sthorpej void
i80321_io_bs_unmap(void * t,bus_space_handle_t bsh,bus_size_t size)313f5362116Sthorpej i80321_io_bs_unmap(void *t, bus_space_handle_t bsh, bus_size_t size)
314f5362116Sthorpej {
315f5362116Sthorpej 
316f5362116Sthorpej 	/* Nothing to do. */
317f5362116Sthorpej }
318f5362116Sthorpej 
319f5362116Sthorpej int
i80321_io_bs_alloc(void * t,bus_addr_t rstart,bus_addr_t rend,bus_size_t size,bus_size_t alignment,bus_size_t boundary,int flags,bus_addr_t * bpap,bus_space_handle_t * bshp)320f5362116Sthorpej i80321_io_bs_alloc(void *t, bus_addr_t rstart, bus_addr_t rend,
321f5362116Sthorpej     bus_size_t size, bus_size_t alignment, bus_size_t boundary, int flags,
322f5362116Sthorpej     bus_addr_t *bpap, bus_space_handle_t *bshp)
323f5362116Sthorpej {
324f5362116Sthorpej 
3250f09ed48Sprovos 	panic("i80321_io_bs_alloc(): not implemented");
326f5362116Sthorpej }
327f5362116Sthorpej 
328f5362116Sthorpej void
i80321_io_bs_free(void * t,bus_space_handle_t bsh,bus_size_t size)329f5362116Sthorpej i80321_io_bs_free(void *t, bus_space_handle_t bsh, bus_size_t size)
330f5362116Sthorpej {
331f5362116Sthorpej 
3320f09ed48Sprovos 	panic("i80321_io_bs_free(): not implemented");
333f5362116Sthorpej }
334f5362116Sthorpej 
335f5362116Sthorpej void *
i80321_io_bs_vaddr(void * t,bus_space_handle_t bsh)336f5362116Sthorpej i80321_io_bs_vaddr(void *t, bus_space_handle_t bsh)
337f5362116Sthorpej {
338f5362116Sthorpej 
339f5362116Sthorpej 	/* Not supported. */
340f5362116Sthorpej 	return (NULL);
341f5362116Sthorpej }
342f5362116Sthorpej 
343f5362116Sthorpej /* *** Routines for PCI MEM. *** */
344f5362116Sthorpej 
345f5362116Sthorpej int
i80321_mem_bs_map(void * t,bus_addr_t bpa,bus_size_t size,int flags,bus_space_handle_t * bshp)346f5362116Sthorpej i80321_mem_bs_map(void *t, bus_addr_t bpa, bus_size_t size, int flags,
347f5362116Sthorpej     bus_space_handle_t *bshp)
348f5362116Sthorpej {
349f5362116Sthorpej 
350392aeaadSgavan #ifndef I80321_USE_DIRECT_WIN
351f5362116Sthorpej 	struct i80321_softc *sc = t;
352392aeaadSgavan #endif
353f5362116Sthorpej 	vaddr_t va;
354f5362116Sthorpej 	uint32_t busbase;
355f5362116Sthorpej 	paddr_t pa, endpa, physbase;
356f5362116Sthorpej 
357392aeaadSgavan #ifdef I80321_USE_DIRECT_WIN
3586eb573f0Sjoerg 	if (
3596eb573f0Sjoerg #if VERDE_OUT_DIRECT_WIN_BASE != 0
3606eb573f0Sjoerg 	    bpa >= (VERDE_OUT_DIRECT_WIN_BASE) &&
3616eb573f0Sjoerg #endif
362392aeaadSgavan 	    bpa < (VERDE_OUT_DIRECT_WIN_BASE + VERDE_OUT_DIRECT_WIN_SIZE)) {
363392aeaadSgavan 		busbase = VERDE_OUT_DIRECT_WIN_BASE;
364392aeaadSgavan 		physbase = VERDE_OUT_DIRECT_WIN_BASE;
365392aeaadSgavan 	} else
366392aeaadSgavan 		return (EINVAL);
367392aeaadSgavan 	if ((bpa + size) >= (VERDE_OUT_DIRECT_WIN_BASE +
368392aeaadSgavan 	    VERDE_OUT_DIRECT_WIN_SIZE))
369392aeaadSgavan 		return (EINVAL);
370392aeaadSgavan #else
371f5362116Sthorpej 	if (bpa >= sc->sc_owin[0].owin_xlate_lo &&
372f5362116Sthorpej 	    bpa < (sc->sc_owin[0].owin_xlate_lo +
373f5362116Sthorpej 		   VERDE_OUT_XLATE_MEM_WIN_SIZE)) {
374f5362116Sthorpej 		busbase = sc->sc_owin[0].owin_xlate_lo;
375f5362116Sthorpej 		physbase = sc->sc_iwin[1].iwin_xlate;
376f5362116Sthorpej 	} else
377f5362116Sthorpej 		return (EINVAL);
378f5362116Sthorpej 
379f5362116Sthorpej 	if ((bpa + size) >= (busbase + VERDE_OUT_XLATE_MEM_WIN_SIZE))
380f5362116Sthorpej 		return (EINVAL);
381392aeaadSgavan #endif
382f5362116Sthorpej 
383f5362116Sthorpej 	/*
384952a515dSskrll 	 * Found the window -- PCI MEM space is now mapped by allocating
385f5362116Sthorpej 	 * some kernel VA space and mapping the pages with pmap_enter().
386f5362116Sthorpej 	 * pmap_enter() will map unmanaged pages as non-cacheable.
387f5362116Sthorpej 	 */
388f5362116Sthorpej 	pa = trunc_page((bpa - busbase) + physbase);
389f5362116Sthorpej 	endpa = round_page(((bpa - busbase) + physbase) + size);
390f5362116Sthorpej 
391bc21da4cSyamt 	va = uvm_km_alloc(kernel_map, endpa - pa, 0,
392bc21da4cSyamt 	    UVM_KMF_VAONLY | UVM_KMF_NOWAIT);
393f5362116Sthorpej 	if (va == 0)
394f5362116Sthorpej 		return (ENOMEM);
395f5362116Sthorpej 
396f5362116Sthorpej 	*bshp = va + (bpa & PAGE_MASK);
397f5362116Sthorpej 
398f5362116Sthorpej 	for (; pa < endpa; pa += PAGE_SIZE, va += PAGE_SIZE) {
399f5362116Sthorpej 		pmap_enter(pmap_kernel(), va, pa,
400df011fdaSthorpej 		    VM_PROT_READ | VM_PROT_WRITE,
40160617b8eSmacallan 		    VM_PROT_READ | VM_PROT_WRITE | PMAP_WIRED |
40260617b8eSmacallan 		    ((flags & BUS_SPACE_MAP_PREFETCHABLE) ?
40360617b8eSmacallan 		       ARM_MMAP_WRITECOMBINE : 0));
404f5362116Sthorpej 	}
405f5362116Sthorpej 	pmap_update(pmap_kernel());
406f5362116Sthorpej 
407f5362116Sthorpej 	return (0);
408f5362116Sthorpej }
409f5362116Sthorpej 
410f5362116Sthorpej void
i80321_mem_bs_unmap(void * t,bus_space_handle_t bsh,bus_size_t size)411f5362116Sthorpej i80321_mem_bs_unmap(void *t, bus_space_handle_t bsh, bus_size_t size)
412f5362116Sthorpej {
413f5362116Sthorpej 	vaddr_t va, endva;
414f5362116Sthorpej 
415f5362116Sthorpej 	va = trunc_page(bsh);
416f5362116Sthorpej 	endva = round_page(bsh + size);
417f5362116Sthorpej 
4186b2d8b66Syamt 	pmap_remove(pmap_kernel(), va, endva - va);
4196b2d8b66Syamt 	pmap_update(pmap_kernel());
4206b2d8b66Syamt 
421f5362116Sthorpej 	/* Free the kernel virtual mapping. */
4226b2d8b66Syamt 	uvm_km_free(kernel_map, va, endva - va, UVM_KMF_VAONLY);
423f5362116Sthorpej }
424f5362116Sthorpej 
425f5362116Sthorpej int
i80321_mem_bs_alloc(void * t,bus_addr_t rstart,bus_addr_t rend,bus_size_t size,bus_size_t alignment,bus_size_t boundary,int flags,bus_addr_t * bpap,bus_space_handle_t * bshp)426f5362116Sthorpej i80321_mem_bs_alloc(void *t, bus_addr_t rstart, bus_addr_t rend,
427f5362116Sthorpej     bus_size_t size, bus_size_t alignment, bus_size_t boundary, int flags,
428f5362116Sthorpej     bus_addr_t *bpap, bus_space_handle_t *bshp)
429f5362116Sthorpej {
430f5362116Sthorpej 
4310f09ed48Sprovos 	panic("i80321_mem_bs_alloc(): not implemented");
432f5362116Sthorpej }
433f5362116Sthorpej 
434f5362116Sthorpej void
i80321_mem_bs_free(void * t,bus_space_handle_t bsh,bus_size_t size)435f5362116Sthorpej i80321_mem_bs_free(void *t, bus_space_handle_t bsh, bus_size_t size)
436f5362116Sthorpej {
437f5362116Sthorpej 
4380f09ed48Sprovos 	panic("i80321_mem_bs_free(): not implemented");
439f5362116Sthorpej }
440f5362116Sthorpej 
441f5362116Sthorpej paddr_t
i80321_mem_bs_mmap(void * t,bus_addr_t addr,off_t off,int prot,int flags)442f5362116Sthorpej i80321_mem_bs_mmap(void *t, bus_addr_t addr, off_t off, int prot, int flags)
443f5362116Sthorpej {
44460617b8eSmacallan #ifndef I80321_USE_DIRECT_WIN
44560617b8eSmacallan 	struct i80321_softc *sc = t;
44660617b8eSmacallan #endif
44760617b8eSmacallan 	uint32_t busbase;
44860617b8eSmacallan 	paddr_t pa, physbase, bpa = addr + off, pflags = 0;
449f5362116Sthorpej 
45060617b8eSmacallan #ifdef I80321_USE_DIRECT_WIN
45160617b8eSmacallan 	if (
45260617b8eSmacallan #if VERDE_OUT_DIRECT_WIN_BASE != 0
45360617b8eSmacallan 	    bpa >= (VERDE_OUT_DIRECT_WIN_BASE) &&
45460617b8eSmacallan #endif
45560617b8eSmacallan 	    bpa < (VERDE_OUT_DIRECT_WIN_BASE + VERDE_OUT_DIRECT_WIN_SIZE)) {
45660617b8eSmacallan 		busbase = VERDE_OUT_DIRECT_WIN_BASE;
45760617b8eSmacallan 		physbase = VERDE_OUT_DIRECT_WIN_BASE;
45860617b8eSmacallan 	} else
45931997526Sthorpej 		return (-1);
46060617b8eSmacallan #else
46160617b8eSmacallan 	if (bpa >= sc->sc_owin[0].owin_xlate_lo &&
46260617b8eSmacallan 	    bpa < (sc->sc_owin[0].owin_xlate_lo +
46360617b8eSmacallan 		   VERDE_OUT_XLATE_MEM_WIN_SIZE)) {
46460617b8eSmacallan 		busbase = sc->sc_owin[0].owin_xlate_lo;
46560617b8eSmacallan 		physbase = sc->sc_iwin[1].iwin_xlate;
46660617b8eSmacallan 	} else
46731997526Sthorpej 		return (-1);
46860617b8eSmacallan #endif
46960617b8eSmacallan 
47060617b8eSmacallan 	pa = trunc_page((bpa - busbase) + physbase);
47160617b8eSmacallan 	if (flags & BUS_SPACE_MAP_PREFETCHABLE) {
47260617b8eSmacallan 		pflags = ARM_MMAP_WRITECOMBINE;
47360617b8eSmacallan 	}
47460617b8eSmacallan 	return (arm_btop(pa) | pflags);
475f5362116Sthorpej }
476