xref: /freebsd/sys/dev/agp/agp_i810.c (revision aa77200569e397d6ff1fdb4d255d0fa254d0a128)
1 /*-
2  * Copyright (c) 2000 Doug Rabson
3  * Copyright (c) 2000 Ruslan Ermilov
4  * Copyright (c) 2011 The FreeBSD Foundation
5  * All rights reserved.
6  *
7  * Portions of this software were developed by Konstantin Belousov
8  * under sponsorship from the FreeBSD Foundation.
9  *
10  * Redistribution and use in source and binary forms, with or without
11  * modification, are permitted provided that the following conditions
12  * are met:
13  * 1. Redistributions of source code must retain the above copyright
14  *    notice, this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in the
17  *    documentation and/or other materials provided with the distribution.
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
20  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
23  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29  * SUCH DAMAGE.
30  */
31 
32 /*
33  * Fixes for 830/845G support: David Dawes <dawes@xfree86.org>
34  * 852GM/855GM/865G support added by David Dawes <dawes@xfree86.org>
35  *
36  * This is generic Intel GTT handling code, morphed from the AGP
37  * bridge code.
38  */
39 
40 #include <sys/cdefs.h>
41 __FBSDID("$FreeBSD$");
42 
43 #if 0
44 #define	KTR_AGP_I810	KTR_DEV
45 #else
46 #define	KTR_AGP_I810	0
47 #endif
48 
49 #include <sys/param.h>
50 #include <sys/systm.h>
51 #include <sys/malloc.h>
52 #include <sys/kernel.h>
53 #include <sys/ktr.h>
54 #include <sys/module.h>
55 #include <sys/bus.h>
56 #include <sys/lock.h>
57 #include <sys/mutex.h>
58 #include <sys/proc.h>
59 
60 #include <dev/agp/agppriv.h>
61 #include <dev/agp/agpreg.h>
62 #include <dev/agp/agp_i810.h>
63 #include <dev/pci/pcivar.h>
64 #include <dev/pci/pcireg.h>
65 #include <dev/pci/pci_private.h>
66 
67 #include <vm/vm.h>
68 #include <vm/vm_param.h>
69 #include <vm/vm_object.h>
70 #include <vm/vm_page.h>
71 #include <vm/vm_pageout.h>
72 #include <vm/pmap.h>
73 
74 #include <machine/bus.h>
75 #include <machine/resource.h>
76 #include <machine/md_var.h>
77 #include <sys/rman.h>
78 
79 MALLOC_DECLARE(M_AGP);
80 
81 struct agp_i810_match;
82 
83 static int agp_i810_check_active(device_t bridge_dev);
84 static int agp_i830_check_active(device_t bridge_dev);
85 static int agp_i915_check_active(device_t bridge_dev);
86 static int agp_sb_check_active(device_t bridge_dev);
87 
88 static void agp_82852_set_desc(device_t dev,
89     const struct agp_i810_match *match);
90 static void agp_i810_set_desc(device_t dev, const struct agp_i810_match *match);
91 
92 static void agp_i810_dump_regs(device_t dev);
93 static void agp_i830_dump_regs(device_t dev);
94 static void agp_i855_dump_regs(device_t dev);
95 static void agp_i915_dump_regs(device_t dev);
96 static void agp_i965_dump_regs(device_t dev);
97 static void agp_sb_dump_regs(device_t dev);
98 
99 static int agp_i810_get_stolen_size(device_t dev);
100 static int agp_i830_get_stolen_size(device_t dev);
101 static int agp_i915_get_stolen_size(device_t dev);
102 static int agp_sb_get_stolen_size(device_t dev);
103 
104 static int agp_i810_get_gtt_mappable_entries(device_t dev);
105 static int agp_i830_get_gtt_mappable_entries(device_t dev);
106 static int agp_i915_get_gtt_mappable_entries(device_t dev);
107 
108 static int agp_i810_get_gtt_total_entries(device_t dev);
109 static int agp_i965_get_gtt_total_entries(device_t dev);
110 static int agp_gen5_get_gtt_total_entries(device_t dev);
111 static int agp_sb_get_gtt_total_entries(device_t dev);
112 
113 static int agp_i810_install_gatt(device_t dev);
114 static int agp_i830_install_gatt(device_t dev);
115 
116 static void agp_i810_deinstall_gatt(device_t dev);
117 static void agp_i830_deinstall_gatt(device_t dev);
118 
119 static void agp_i810_install_gtt_pte(device_t dev, u_int index,
120     vm_offset_t physical, int flags);
121 static void agp_i830_install_gtt_pte(device_t dev, u_int index,
122     vm_offset_t physical, int flags);
123 static void agp_i915_install_gtt_pte(device_t dev, u_int index,
124     vm_offset_t physical, int flags);
125 static void agp_i965_install_gtt_pte(device_t dev, u_int index,
126     vm_offset_t physical, int flags);
127 static void agp_g4x_install_gtt_pte(device_t dev, u_int index,
128     vm_offset_t physical, int flags);
129 static void agp_sb_install_gtt_pte(device_t dev, u_int index,
130     vm_offset_t physical, int flags);
131 
132 static void agp_i810_write_gtt(device_t dev, u_int index, uint32_t pte);
133 static void agp_i915_write_gtt(device_t dev, u_int index, uint32_t pte);
134 static void agp_i965_write_gtt(device_t dev, u_int index, uint32_t pte);
135 static void agp_g4x_write_gtt(device_t dev, u_int index, uint32_t pte);
136 static void agp_sb_write_gtt(device_t dev, u_int index, uint32_t pte);
137 
138 static u_int32_t agp_i810_read_gtt_pte(device_t dev, u_int index);
139 static u_int32_t agp_i915_read_gtt_pte(device_t dev, u_int index);
140 static u_int32_t agp_i965_read_gtt_pte(device_t dev, u_int index);
141 static u_int32_t agp_g4x_read_gtt_pte(device_t dev, u_int index);
142 
143 static vm_paddr_t agp_i810_read_gtt_pte_paddr(device_t dev, u_int index);
144 static vm_paddr_t agp_i915_read_gtt_pte_paddr(device_t dev, u_int index);
145 static vm_paddr_t agp_sb_read_gtt_pte_paddr(device_t dev, u_int index);
146 
147 static int agp_i810_set_aperture(device_t dev, u_int32_t aperture);
148 static int agp_i830_set_aperture(device_t dev, u_int32_t aperture);
149 static int agp_i915_set_aperture(device_t dev, u_int32_t aperture);
150 
151 static int agp_i810_chipset_flush_setup(device_t dev);
152 static int agp_i915_chipset_flush_setup(device_t dev);
153 static int agp_i965_chipset_flush_setup(device_t dev);
154 
155 static void agp_i810_chipset_flush_teardown(device_t dev);
156 static void agp_i915_chipset_flush_teardown(device_t dev);
157 static void agp_i965_chipset_flush_teardown(device_t dev);
158 
159 static void agp_i810_chipset_flush(device_t dev);
160 static void agp_i830_chipset_flush(device_t dev);
161 static void agp_i915_chipset_flush(device_t dev);
162 
163 enum {
164 	CHIP_I810,	/* i810/i815 */
165 	CHIP_I830,	/* 830M/845G */
166 	CHIP_I855,	/* 852GM/855GM/865G */
167 	CHIP_I915,	/* 915G/915GM */
168 	CHIP_I965,	/* G965 */
169 	CHIP_G33,	/* G33/Q33/Q35 */
170 	CHIP_IGD,	/* Pineview */
171 	CHIP_G4X,	/* G45/Q45 */
172 	CHIP_SB,	/* SandyBridge */
173 };
174 
175 /* The i810 through i855 have the registers at BAR 1, and the GATT gets
176  * allocated by us.  The i915 has registers in BAR 0 and the GATT is at the
177  * start of the stolen memory, and should only be accessed by the OS through
178  * BAR 3.  The G965 has registers and GATT in the same BAR (0) -- first 512KB
179  * is registers, second 512KB is GATT.
180  */
181 static struct resource_spec agp_i810_res_spec[] = {
182 	{ SYS_RES_MEMORY, AGP_I810_MMADR, RF_ACTIVE | RF_SHAREABLE },
183 	{ -1, 0 }
184 };
185 
186 static struct resource_spec agp_i915_res_spec[] = {
187 	{ SYS_RES_MEMORY, AGP_I915_MMADR, RF_ACTIVE | RF_SHAREABLE },
188 	{ SYS_RES_MEMORY, AGP_I915_GTTADR, RF_ACTIVE | RF_SHAREABLE },
189 	{ -1, 0 }
190 };
191 
192 static struct resource_spec agp_i965_res_spec[] = {
193 	{ SYS_RES_MEMORY, AGP_I965_GTTMMADR, RF_ACTIVE | RF_SHAREABLE },
194 	{ -1, 0 }
195 };
196 
197 static struct resource_spec agp_g4x_res_spec[] = {
198 	{ SYS_RES_MEMORY, AGP_G4X_MMADR, RF_ACTIVE | RF_SHAREABLE },
199 	{ SYS_RES_MEMORY, AGP_G4X_GTTADR, RF_ACTIVE | RF_SHAREABLE },
200 	{ -1, 0 }
201 };
202 
203 struct agp_i810_softc {
204 	struct agp_softc agp;
205 	u_int32_t initial_aperture;	/* aperture size at startup */
206 	struct agp_gatt *gatt;
207 	u_int32_t dcache_size;		/* i810 only */
208 	u_int32_t stolen;		/* number of i830/845 gtt
209 					   entries for stolen memory */
210 	u_int stolen_size;		/* BIOS-reserved graphics memory */
211 	u_int gtt_total_entries;	/* Total number of gtt ptes */
212 	u_int gtt_mappable_entries;	/* Number of gtt ptes mappable by CPU */
213 	device_t bdev;			/* bridge device */
214 	void *argb_cursor;		/* contigmalloc area for ARGB cursor */
215 	struct resource *sc_res[2];
216 	const struct agp_i810_match *match;
217 	int sc_flush_page_rid;
218 	struct resource *sc_flush_page_res;
219 	void *sc_flush_page_vaddr;
220 	int sc_bios_allocated_flush_page;
221 };
222 
223 static device_t intel_agp;
224 
225 struct agp_i810_driver {
226 	int chiptype;
227 	int gen;
228 	int busdma_addr_mask_sz;
229 	struct resource_spec *res_spec;
230 	int (*check_active)(device_t);
231 	void (*set_desc)(device_t, const struct agp_i810_match *);
232 	void (*dump_regs)(device_t);
233 	int (*get_stolen_size)(device_t);
234 	int (*get_gtt_total_entries)(device_t);
235 	int (*get_gtt_mappable_entries)(device_t);
236 	int (*install_gatt)(device_t);
237 	void (*deinstall_gatt)(device_t);
238 	void (*write_gtt)(device_t, u_int, uint32_t);
239 	void (*install_gtt_pte)(device_t, u_int, vm_offset_t, int);
240 	u_int32_t (*read_gtt_pte)(device_t, u_int);
241 	vm_paddr_t (*read_gtt_pte_paddr)(device_t , u_int);
242 	int (*set_aperture)(device_t, u_int32_t);
243 	int (*chipset_flush_setup)(device_t);
244 	void (*chipset_flush_teardown)(device_t);
245 	void (*chipset_flush)(device_t);
246 };
247 
248 static const struct agp_i810_driver agp_i810_i810_driver = {
249 	.chiptype = CHIP_I810,
250 	.gen = 1,
251 	.busdma_addr_mask_sz = 32,
252 	.res_spec = agp_i810_res_spec,
253 	.check_active = agp_i810_check_active,
254 	.set_desc = agp_i810_set_desc,
255 	.dump_regs = agp_i810_dump_regs,
256 	.get_stolen_size = agp_i810_get_stolen_size,
257 	.get_gtt_mappable_entries = agp_i810_get_gtt_mappable_entries,
258 	.get_gtt_total_entries = agp_i810_get_gtt_total_entries,
259 	.install_gatt = agp_i810_install_gatt,
260 	.deinstall_gatt = agp_i810_deinstall_gatt,
261 	.write_gtt = agp_i810_write_gtt,
262 	.install_gtt_pte = agp_i810_install_gtt_pte,
263 	.read_gtt_pte = agp_i810_read_gtt_pte,
264 	.read_gtt_pte_paddr = agp_i810_read_gtt_pte_paddr,
265 	.set_aperture = agp_i810_set_aperture,
266 	.chipset_flush_setup = agp_i810_chipset_flush_setup,
267 	.chipset_flush_teardown = agp_i810_chipset_flush_teardown,
268 	.chipset_flush = agp_i810_chipset_flush,
269 };
270 
271 static const struct agp_i810_driver agp_i810_i815_driver = {
272 	.chiptype = CHIP_I810,
273 	.gen = 2,
274 	.busdma_addr_mask_sz = 32,
275 	.res_spec = agp_i810_res_spec,
276 	.check_active = agp_i810_check_active,
277 	.set_desc = agp_i810_set_desc,
278 	.dump_regs = agp_i810_dump_regs,
279 	.get_stolen_size = agp_i810_get_stolen_size,
280 	.get_gtt_mappable_entries = agp_i830_get_gtt_mappable_entries,
281 	.get_gtt_total_entries = agp_i810_get_gtt_total_entries,
282 	.install_gatt = agp_i810_install_gatt,
283 	.deinstall_gatt = agp_i810_deinstall_gatt,
284 	.write_gtt = agp_i810_write_gtt,
285 	.install_gtt_pte = agp_i810_install_gtt_pte,
286 	.read_gtt_pte = agp_i810_read_gtt_pte,
287 	.read_gtt_pte_paddr = agp_i810_read_gtt_pte_paddr,
288 	.set_aperture = agp_i810_set_aperture,
289 	.chipset_flush_setup = agp_i810_chipset_flush_setup,
290 	.chipset_flush_teardown = agp_i810_chipset_flush_teardown,
291 	.chipset_flush = agp_i830_chipset_flush,
292 };
293 
294 static const struct agp_i810_driver agp_i810_i830_driver = {
295 	.chiptype = CHIP_I830,
296 	.gen = 2,
297 	.busdma_addr_mask_sz = 32,
298 	.res_spec = agp_i810_res_spec,
299 	.check_active = agp_i830_check_active,
300 	.set_desc = agp_i810_set_desc,
301 	.dump_regs = agp_i830_dump_regs,
302 	.get_stolen_size = agp_i830_get_stolen_size,
303 	.get_gtt_mappable_entries = agp_i830_get_gtt_mappable_entries,
304 	.get_gtt_total_entries = agp_i810_get_gtt_total_entries,
305 	.install_gatt = agp_i830_install_gatt,
306 	.deinstall_gatt = agp_i830_deinstall_gatt,
307 	.write_gtt = agp_i810_write_gtt,
308 	.install_gtt_pte = agp_i830_install_gtt_pte,
309 	.read_gtt_pte = agp_i810_read_gtt_pte,
310 	.read_gtt_pte_paddr = agp_i810_read_gtt_pte_paddr,
311 	.set_aperture = agp_i830_set_aperture,
312 	.chipset_flush_setup = agp_i810_chipset_flush_setup,
313 	.chipset_flush_teardown = agp_i810_chipset_flush_teardown,
314 	.chipset_flush = agp_i830_chipset_flush,
315 };
316 
317 static const struct agp_i810_driver agp_i810_i855_driver = {
318 	.chiptype = CHIP_I855,
319 	.gen = 2,
320 	.busdma_addr_mask_sz = 32,
321 	.res_spec = agp_i810_res_spec,
322 	.check_active = agp_i830_check_active,
323 	.set_desc = agp_82852_set_desc,
324 	.dump_regs = agp_i855_dump_regs,
325 	.get_stolen_size = agp_i915_get_stolen_size,
326 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
327 	.get_gtt_total_entries = agp_i810_get_gtt_total_entries,
328 	.install_gatt = agp_i830_install_gatt,
329 	.deinstall_gatt = agp_i830_deinstall_gatt,
330 	.write_gtt = agp_i810_write_gtt,
331 	.install_gtt_pte = agp_i830_install_gtt_pte,
332 	.read_gtt_pte = agp_i810_read_gtt_pte,
333 	.read_gtt_pte_paddr = agp_i810_read_gtt_pte_paddr,
334 	.set_aperture = agp_i830_set_aperture,
335 	.chipset_flush_setup = agp_i810_chipset_flush_setup,
336 	.chipset_flush_teardown = agp_i810_chipset_flush_teardown,
337 	.chipset_flush = agp_i830_chipset_flush,
338 };
339 
340 static const struct agp_i810_driver agp_i810_i865_driver = {
341 	.chiptype = CHIP_I855,
342 	.gen = 2,
343 	.busdma_addr_mask_sz = 32,
344 	.res_spec = agp_i810_res_spec,
345 	.check_active = agp_i830_check_active,
346 	.set_desc = agp_i810_set_desc,
347 	.dump_regs = agp_i855_dump_regs,
348 	.get_stolen_size = agp_i915_get_stolen_size,
349 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
350 	.get_gtt_total_entries = agp_i810_get_gtt_total_entries,
351 	.install_gatt = agp_i830_install_gatt,
352 	.deinstall_gatt = agp_i830_deinstall_gatt,
353 	.write_gtt = agp_i810_write_gtt,
354 	.install_gtt_pte = agp_i830_install_gtt_pte,
355 	.read_gtt_pte = agp_i810_read_gtt_pte,
356 	.read_gtt_pte_paddr = agp_i810_read_gtt_pte_paddr,
357 	.set_aperture = agp_i915_set_aperture,
358 	.chipset_flush_setup = agp_i810_chipset_flush_setup,
359 	.chipset_flush_teardown = agp_i810_chipset_flush_teardown,
360 	.chipset_flush = agp_i830_chipset_flush,
361 };
362 
363 static const struct agp_i810_driver agp_i810_i915_driver = {
364 	.chiptype = CHIP_I915,
365 	.gen = 3,
366 	.busdma_addr_mask_sz = 32,
367 	.res_spec = agp_i915_res_spec,
368 	.check_active = agp_i915_check_active,
369 	.set_desc = agp_i810_set_desc,
370 	.dump_regs = agp_i915_dump_regs,
371 	.get_stolen_size = agp_i915_get_stolen_size,
372 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
373 	.get_gtt_total_entries = agp_i810_get_gtt_total_entries,
374 	.install_gatt = agp_i830_install_gatt,
375 	.deinstall_gatt = agp_i830_deinstall_gatt,
376 	.write_gtt = agp_i915_write_gtt,
377 	.install_gtt_pte = agp_i915_install_gtt_pte,
378 	.read_gtt_pte = agp_i915_read_gtt_pte,
379 	.read_gtt_pte_paddr = agp_i915_read_gtt_pte_paddr,
380 	.set_aperture = agp_i915_set_aperture,
381 	.chipset_flush_setup = agp_i915_chipset_flush_setup,
382 	.chipset_flush_teardown = agp_i915_chipset_flush_teardown,
383 	.chipset_flush = agp_i915_chipset_flush,
384 };
385 
386 static const struct agp_i810_driver agp_i810_g965_driver = {
387 	.chiptype = CHIP_I965,
388 	.gen = 4,
389 	.busdma_addr_mask_sz = 36,
390 	.res_spec = agp_i965_res_spec,
391 	.check_active = agp_i915_check_active,
392 	.set_desc = agp_i810_set_desc,
393 	.dump_regs = agp_i965_dump_regs,
394 	.get_stolen_size = agp_i915_get_stolen_size,
395 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
396 	.get_gtt_total_entries = agp_i965_get_gtt_total_entries,
397 	.install_gatt = agp_i830_install_gatt,
398 	.deinstall_gatt = agp_i830_deinstall_gatt,
399 	.write_gtt = agp_i965_write_gtt,
400 	.install_gtt_pte = agp_i965_install_gtt_pte,
401 	.read_gtt_pte = agp_i965_read_gtt_pte,
402 	.read_gtt_pte_paddr = agp_i915_read_gtt_pte_paddr,
403 	.set_aperture = agp_i915_set_aperture,
404 	.chipset_flush_setup = agp_i965_chipset_flush_setup,
405 	.chipset_flush_teardown = agp_i965_chipset_flush_teardown,
406 	.chipset_flush = agp_i915_chipset_flush,
407 };
408 
409 static const struct agp_i810_driver agp_i810_g33_driver = {
410 	.chiptype = CHIP_G33,
411 	.gen = 3,
412 	.busdma_addr_mask_sz = 36,
413 	.res_spec = agp_i915_res_spec,
414 	.check_active = agp_i915_check_active,
415 	.set_desc = agp_i810_set_desc,
416 	.dump_regs = agp_i965_dump_regs,
417 	.get_stolen_size = agp_i915_get_stolen_size,
418 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
419 	.get_gtt_total_entries = agp_i965_get_gtt_total_entries,
420 	.install_gatt = agp_i830_install_gatt,
421 	.deinstall_gatt = agp_i830_deinstall_gatt,
422 	.write_gtt = agp_i915_write_gtt,
423 	.install_gtt_pte = agp_i915_install_gtt_pte,
424 	.read_gtt_pte = agp_i915_read_gtt_pte,
425 	.read_gtt_pte_paddr = agp_i915_read_gtt_pte_paddr,
426 	.set_aperture = agp_i915_set_aperture,
427 	.chipset_flush_setup = agp_i965_chipset_flush_setup,
428 	.chipset_flush_teardown = agp_i965_chipset_flush_teardown,
429 	.chipset_flush = agp_i915_chipset_flush,
430 };
431 
432 static const struct agp_i810_driver agp_i810_igd_driver = {
433 	.chiptype = CHIP_IGD,
434 	.gen = 3,
435 	.busdma_addr_mask_sz = 36,
436 	.res_spec = agp_i915_res_spec,
437 	.check_active = agp_i915_check_active,
438 	.set_desc = agp_i810_set_desc,
439 	.dump_regs = agp_i915_dump_regs,
440 	.get_stolen_size = agp_i915_get_stolen_size,
441 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
442 	.get_gtt_total_entries = agp_i965_get_gtt_total_entries,
443 	.install_gatt = agp_i830_install_gatt,
444 	.deinstall_gatt = agp_i830_deinstall_gatt,
445 	.write_gtt = agp_i915_write_gtt,
446 	.install_gtt_pte = agp_i915_install_gtt_pte,
447 	.read_gtt_pte = agp_i915_read_gtt_pte,
448 	.read_gtt_pte_paddr = agp_i915_read_gtt_pte_paddr,
449 	.set_aperture = agp_i915_set_aperture,
450 	.chipset_flush_setup = agp_i965_chipset_flush_setup,
451 	.chipset_flush_teardown = agp_i965_chipset_flush_teardown,
452 	.chipset_flush = agp_i915_chipset_flush,
453 };
454 
455 static const struct agp_i810_driver agp_i810_g4x_driver = {
456 	.chiptype = CHIP_G4X,
457 	.gen = 5,
458 	.busdma_addr_mask_sz = 36,
459 	.res_spec = agp_i965_res_spec,
460 	.check_active = agp_i915_check_active,
461 	.set_desc = agp_i810_set_desc,
462 	.dump_regs = agp_i965_dump_regs,
463 	.get_stolen_size = agp_i915_get_stolen_size,
464 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
465 	.get_gtt_total_entries = agp_gen5_get_gtt_total_entries,
466 	.install_gatt = agp_i830_install_gatt,
467 	.deinstall_gatt = agp_i830_deinstall_gatt,
468 	.write_gtt = agp_g4x_write_gtt,
469 	.install_gtt_pte = agp_g4x_install_gtt_pte,
470 	.read_gtt_pte = agp_g4x_read_gtt_pte,
471 	.read_gtt_pte_paddr = agp_i915_read_gtt_pte_paddr,
472 	.set_aperture = agp_i915_set_aperture,
473 	.chipset_flush_setup = agp_i965_chipset_flush_setup,
474 	.chipset_flush_teardown = agp_i965_chipset_flush_teardown,
475 	.chipset_flush = agp_i915_chipset_flush,
476 };
477 
478 static const struct agp_i810_driver agp_i810_sb_driver = {
479 	.chiptype = CHIP_SB,
480 	.gen = 6,
481 	.busdma_addr_mask_sz = 40,
482 	.res_spec = agp_g4x_res_spec,
483 	.check_active = agp_sb_check_active,
484 	.set_desc = agp_i810_set_desc,
485 	.dump_regs = agp_sb_dump_regs,
486 	.get_stolen_size = agp_sb_get_stolen_size,
487 	.get_gtt_mappable_entries = agp_i915_get_gtt_mappable_entries,
488 	.get_gtt_total_entries = agp_sb_get_gtt_total_entries,
489 	.install_gatt = agp_i830_install_gatt,
490 	.deinstall_gatt = agp_i830_deinstall_gatt,
491 	.write_gtt = agp_sb_write_gtt,
492 	.install_gtt_pte = agp_sb_install_gtt_pte,
493 	.read_gtt_pte = agp_g4x_read_gtt_pte,
494 	.read_gtt_pte_paddr = agp_sb_read_gtt_pte_paddr,
495 	.set_aperture = agp_i915_set_aperture,
496 	.chipset_flush_setup = agp_i810_chipset_flush_setup,
497 	.chipset_flush_teardown = agp_i810_chipset_flush_teardown,
498 	.chipset_flush = agp_i810_chipset_flush,
499 };
500 
501 /* For adding new devices, devid is the id of the graphics controller
502  * (pci:0:2:0, for example).  The placeholder (usually at pci:0:2:1) for the
503  * second head should never be added.  The bridge_offset is the offset to
504  * subtract from devid to get the id of the hostb that the device is on.
505  */
506 static const struct agp_i810_match {
507 	int devid;
508 	char *name;
509 	const struct agp_i810_driver *driver;
510 } agp_i810_matches[] = {
511 	{
512 		.devid = 0x71218086,
513 		.name = "Intel 82810 (i810 GMCH) SVGA controller",
514 		.driver = &agp_i810_i810_driver
515 	},
516 	{
517 		.devid = 0x71238086,
518 		.name = "Intel 82810-DC100 (i810-DC100 GMCH) SVGA controller",
519 		.driver = &agp_i810_i810_driver
520 	},
521 	{
522 		.devid = 0x71258086,
523 		.name = "Intel 82810E (i810E GMCH) SVGA controller",
524 		.driver = &agp_i810_i810_driver
525 	},
526 	{
527 		.devid = 0x11328086,
528 		.name = "Intel 82815 (i815 GMCH) SVGA controller",
529 		.driver = &agp_i810_i815_driver
530 	},
531 	{
532 		.devid = 0x35778086,
533 		.name = "Intel 82830M (830M GMCH) SVGA controller",
534 		.driver = &agp_i810_i830_driver
535 	},
536 	{
537 		.devid = 0x25628086,
538 		.name = "Intel 82845M (845M GMCH) SVGA controller",
539 		.driver = &agp_i810_i830_driver
540 	},
541 	{
542 		.devid = 0x35828086,
543 		.name = "Intel 82852/855GM SVGA controller",
544 		.driver = &agp_i810_i855_driver
545 	},
546 	{
547 		.devid = 0x25728086,
548 		.name = "Intel 82865G (865G GMCH) SVGA controller",
549 		.driver = &agp_i810_i865_driver
550 	},
551 	{
552 		.devid = 0x25828086,
553 		.name = "Intel 82915G (915G GMCH) SVGA controller",
554 		.driver = &agp_i810_i915_driver
555 	},
556 	{
557 		.devid = 0x258A8086,
558 		.name = "Intel E7221 SVGA controller",
559 		.driver = &agp_i810_i915_driver
560 	},
561 	{
562 		.devid = 0x25928086,
563 		.name = "Intel 82915GM (915GM GMCH) SVGA controller",
564 		.driver = &agp_i810_i915_driver
565 	},
566 	{
567 		.devid = 0x27728086,
568 		.name = "Intel 82945G (945G GMCH) SVGA controller",
569 		.driver = &agp_i810_i915_driver
570 	},
571 	{
572 		.devid = 0x27A28086,
573 		.name = "Intel 82945GM (945GM GMCH) SVGA controller",
574 		.driver = &agp_i810_i915_driver
575 	},
576 	{
577 		.devid = 0x27AE8086,
578 		.name = "Intel 945GME SVGA controller",
579 		.driver = &agp_i810_i915_driver
580 	},
581 	{
582 		.devid = 0x29728086,
583 		.name = "Intel 946GZ SVGA controller",
584 		.driver = &agp_i810_g965_driver
585 	},
586 	{
587 		.devid = 0x29828086,
588 		.name = "Intel G965 SVGA controller",
589 		.driver = &agp_i810_g965_driver
590 	},
591 	{
592 		.devid = 0x29928086,
593 		.name = "Intel Q965 SVGA controller",
594 		.driver = &agp_i810_g965_driver
595 	},
596 	{
597 		.devid = 0x29A28086,
598 		.name = "Intel G965 SVGA controller",
599 		.driver = &agp_i810_g965_driver
600 	},
601 	{
602 		.devid = 0x29B28086,
603 		.name = "Intel Q35 SVGA controller",
604 		.driver = &agp_i810_g33_driver
605 	},
606 	{
607 		.devid = 0x29C28086,
608 		.name = "Intel G33 SVGA controller",
609 		.driver = &agp_i810_g33_driver
610 	},
611 	{
612 		.devid = 0x29D28086,
613 		.name = "Intel Q33 SVGA controller",
614 		.driver = &agp_i810_g33_driver
615 	},
616 	{
617 		.devid = 0xA0018086,
618 		.name = "Intel Pineview SVGA controller",
619 		.driver = &agp_i810_igd_driver
620 	},
621 	{
622 		.devid = 0xA0118086,
623 		.name = "Intel Pineview (M) SVGA controller",
624 		.driver = &agp_i810_igd_driver
625 	},
626 	{
627 		.devid = 0x2A028086,
628 		.name = "Intel GM965 SVGA controller",
629 		.driver = &agp_i810_g965_driver
630 	},
631 	{
632 		.devid = 0x2A128086,
633 		.name = "Intel GME965 SVGA controller",
634 		.driver = &agp_i810_g965_driver
635 	},
636 	{
637 		.devid = 0x2A428086,
638 		.name = "Intel GM45 SVGA controller",
639 		.driver = &agp_i810_g4x_driver
640 	},
641 	{
642 		.devid = 0x2E028086,
643 		.name = "Intel Eaglelake SVGA controller",
644 		.driver = &agp_i810_g4x_driver
645 	},
646 	{
647 		.devid = 0x2E128086,
648 		.name = "Intel Q45 SVGA controller",
649 		.driver = &agp_i810_g4x_driver
650 	},
651 	{
652 		.devid = 0x2E228086,
653 		.name = "Intel G45 SVGA controller",
654 		.driver = &agp_i810_g4x_driver
655 	},
656 	{
657 		.devid = 0x2E328086,
658 		.name = "Intel G41 SVGA controller",
659 		.driver = &agp_i810_g4x_driver
660 	},
661 	{
662 		.devid = 0x00428086,
663 		.name = "Intel Ironlake (D) SVGA controller",
664 		.driver = &agp_i810_g4x_driver
665 	},
666 	{
667 		.devid = 0x00468086,
668 		.name = "Intel Ironlake (M) SVGA controller",
669 		.driver = &agp_i810_g4x_driver
670 	},
671 	{
672 		.devid = 0x01028086,
673 		.name = "SandyBridge desktop GT1 IG",
674 		.driver = &agp_i810_sb_driver
675 	},
676 	{
677 		.devid = 0x01128086,
678 		.name = "SandyBridge desktop GT2 IG",
679 		.driver = &agp_i810_sb_driver
680 	},
681 	{
682 		.devid = 0x01228086,
683 		.name = "SandyBridge desktop GT2+ IG",
684 		.driver = &agp_i810_sb_driver
685 	},
686 	{
687 		.devid = 0x01068086,
688 		.name = "SandyBridge mobile GT1 IG",
689 		.driver = &agp_i810_sb_driver
690 	},
691 	{
692 		.devid = 0x01168086,
693 		.name = "SandyBridge mobile GT2 IG",
694 		.driver = &agp_i810_sb_driver
695 	},
696 	{
697 		.devid = 0x01268086,
698 		.name = "SandyBridge mobile GT2+ IG",
699 		.driver = &agp_i810_sb_driver
700 	},
701 	{
702 		.devid = 0x010a8086,
703 		.name = "SandyBridge server IG",
704 		.driver = &agp_i810_sb_driver
705 	},
706 	{
707 		.devid = 0x01528086,
708 		.name = "IvyBridge desktop GT1 IG",
709 		.driver = &agp_i810_sb_driver
710 	},
711 	{
712 		.devid = 0x01628086,
713 		.name = "IvyBridge desktop GT2 IG",
714 		.driver = &agp_i810_sb_driver
715 	},
716 	{
717 		.devid = 0x01568086,
718 		.name = "IvyBridge mobile GT1 IG",
719 		.driver = &agp_i810_sb_driver
720 	},
721 	{
722 		.devid = 0x01668086,
723 		.name = "IvyBridge mobile GT2 IG",
724 		.driver = &agp_i810_sb_driver
725 	},
726 	{
727 		.devid = 0x015a8086,
728 		.name = "IvyBridge server GT1 IG",
729 		.driver = &agp_i810_sb_driver
730 	},
731 	{
732 		.devid = 0,
733 	}
734 };
735 
736 static const struct agp_i810_match*
737 agp_i810_match(device_t dev)
738 {
739 	int i, devid;
740 
741 	if (pci_get_class(dev) != PCIC_DISPLAY
742 	    || pci_get_subclass(dev) != PCIS_DISPLAY_VGA)
743 		return (NULL);
744 
745 	devid = pci_get_devid(dev);
746 	for (i = 0; agp_i810_matches[i].devid != 0; i++) {
747 		if (agp_i810_matches[i].devid == devid)
748 			break;
749 	}
750 	if (agp_i810_matches[i].devid == 0)
751 		return (NULL);
752 	else
753 		return (&agp_i810_matches[i]);
754 }
755 
756 /*
757  * Find bridge device.
758  */
759 static device_t
760 agp_i810_find_bridge(device_t dev)
761 {
762 
763 	return (pci_find_dbsf(0, 0, 0, 0));
764 }
765 
766 static void
767 agp_i810_identify(driver_t *driver, device_t parent)
768 {
769 
770 	if (device_find_child(parent, "agp", -1) == NULL &&
771 	    agp_i810_match(parent))
772 		device_add_child(parent, "agp", -1);
773 }
774 
775 static int
776 agp_i810_check_active(device_t bridge_dev)
777 {
778 	u_int8_t smram;
779 
780 	smram = pci_read_config(bridge_dev, AGP_I810_SMRAM, 1);
781 	if ((smram & AGP_I810_SMRAM_GMS) == AGP_I810_SMRAM_GMS_DISABLED)
782 		return (ENXIO);
783 	return (0);
784 }
785 
786 static int
787 agp_i830_check_active(device_t bridge_dev)
788 {
789 	int gcc1;
790 
791 	gcc1 = pci_read_config(bridge_dev, AGP_I830_GCC1, 1);
792 	if ((gcc1 & AGP_I830_GCC1_DEV2) == AGP_I830_GCC1_DEV2_DISABLED)
793 		return (ENXIO);
794 	return (0);
795 }
796 
797 static int
798 agp_i915_check_active(device_t bridge_dev)
799 {
800 	int deven;
801 
802 	deven = pci_read_config(bridge_dev, AGP_I915_DEVEN, 4);
803 	if ((deven & AGP_I915_DEVEN_D2F0) == AGP_I915_DEVEN_D2F0_DISABLED)
804 		return (ENXIO);
805 	return (0);
806 }
807 
808 static int
809 agp_sb_check_active(device_t bridge_dev)
810 {
811 	int deven;
812 
813 	deven = pci_read_config(bridge_dev, AGP_I915_DEVEN, 4);
814 	if ((deven & AGP_SB_DEVEN_D2EN) == AGP_SB_DEVEN_D2EN_DISABLED)
815 		return (ENXIO);
816 	return (0);
817 }
818 
819 static void
820 agp_82852_set_desc(device_t dev, const struct agp_i810_match *match)
821 {
822 
823 	switch (pci_read_config(dev, AGP_I85X_CAPID, 1)) {
824 	case AGP_I855_GME:
825 		device_set_desc(dev,
826 		    "Intel 82855GME (855GME GMCH) SVGA controller");
827 		break;
828 	case AGP_I855_GM:
829 		device_set_desc(dev,
830 		    "Intel 82855GM (855GM GMCH) SVGA controller");
831 		break;
832 	case AGP_I852_GME:
833 		device_set_desc(dev,
834 		    "Intel 82852GME (852GME GMCH) SVGA controller");
835 		break;
836 	case AGP_I852_GM:
837 		device_set_desc(dev,
838 		    "Intel 82852GM (852GM GMCH) SVGA controller");
839 		break;
840 	default:
841 		device_set_desc(dev,
842 		    "Intel 8285xM (85xGM GMCH) SVGA controller");
843 		break;
844 	}
845 }
846 
847 static void
848 agp_i810_set_desc(device_t dev, const struct agp_i810_match *match)
849 {
850 
851 	device_set_desc(dev, match->name);
852 }
853 
854 static int
855 agp_i810_probe(device_t dev)
856 {
857 	device_t bdev;
858 	const struct agp_i810_match *match;
859 	int err;
860 
861 	if (resource_disabled("agp", device_get_unit(dev)))
862 		return (ENXIO);
863 	match = agp_i810_match(dev);
864 	if (match == NULL)
865 		return (ENXIO);
866 
867 	bdev = agp_i810_find_bridge(dev);
868 	if (bdev == NULL) {
869 		if (bootverbose)
870 			printf("I810: can't find bridge device\n");
871 		return (ENXIO);
872 	}
873 
874 	/*
875 	 * checking whether internal graphics device has been activated.
876 	 */
877 	err = match->driver->check_active(bdev);
878 	if (err != 0) {
879 		if (bootverbose)
880 			printf("i810: disabled, not probing\n");
881 		return (err);
882 	}
883 
884 	match->driver->set_desc(dev, match);
885 	return (BUS_PROBE_DEFAULT);
886 }
887 
888 static void
889 agp_i810_dump_regs(device_t dev)
890 {
891 	struct agp_i810_softc *sc = device_get_softc(dev);
892 
893 	device_printf(dev, "AGP_I810_PGTBL_CTL: %08x\n",
894 	    bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL));
895 	device_printf(dev, "AGP_I810_MISCC: 0x%04x\n",
896 	    pci_read_config(sc->bdev, AGP_I810_MISCC, 2));
897 }
898 
899 static void
900 agp_i830_dump_regs(device_t dev)
901 {
902 	struct agp_i810_softc *sc = device_get_softc(dev);
903 
904 	device_printf(dev, "AGP_I810_PGTBL_CTL: %08x\n",
905 	    bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL));
906 	device_printf(dev, "AGP_I830_GCC1: 0x%02x\n",
907 	    pci_read_config(sc->bdev, AGP_I830_GCC1, 1));
908 }
909 
910 static void
911 agp_i855_dump_regs(device_t dev)
912 {
913 	struct agp_i810_softc *sc = device_get_softc(dev);
914 
915 	device_printf(dev, "AGP_I810_PGTBL_CTL: %08x\n",
916 	    bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL));
917 	device_printf(dev, "AGP_I855_GCC1: 0x%02x\n",
918 	    pci_read_config(sc->bdev, AGP_I855_GCC1, 1));
919 }
920 
921 static void
922 agp_i915_dump_regs(device_t dev)
923 {
924 	struct agp_i810_softc *sc = device_get_softc(dev);
925 
926 	device_printf(dev, "AGP_I810_PGTBL_CTL: %08x\n",
927 	    bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL));
928 	device_printf(dev, "AGP_I855_GCC1: 0x%02x\n",
929 	    pci_read_config(sc->bdev, AGP_I855_GCC1, 1));
930 	device_printf(dev, "AGP_I915_MSAC: 0x%02x\n",
931 	    pci_read_config(sc->bdev, AGP_I915_MSAC, 1));
932 }
933 
934 static void
935 agp_i965_dump_regs(device_t dev)
936 {
937 	struct agp_i810_softc *sc = device_get_softc(dev);
938 
939 	device_printf(dev, "AGP_I965_PGTBL_CTL2: %08x\n",
940 	    bus_read_4(sc->sc_res[0], AGP_I965_PGTBL_CTL2));
941 	device_printf(dev, "AGP_I855_GCC1: 0x%02x\n",
942 	    pci_read_config(sc->bdev, AGP_I855_GCC1, 1));
943 	device_printf(dev, "AGP_I965_MSAC: 0x%02x\n",
944 	    pci_read_config(sc->bdev, AGP_I965_MSAC, 1));
945 }
946 
947 static void
948 agp_sb_dump_regs(device_t dev)
949 {
950 	struct agp_i810_softc *sc = device_get_softc(dev);
951 
952 	device_printf(dev, "AGP_SNB_GFX_MODE: %08x\n",
953 	    bus_read_4(sc->sc_res[0], AGP_SNB_GFX_MODE));
954 	device_printf(dev, "AGP_SNB_GCC1: 0x%04x\n",
955 	    pci_read_config(sc->bdev, AGP_SNB_GCC1, 2));
956 }
957 
958 static int
959 agp_i810_get_stolen_size(device_t dev)
960 {
961 	struct agp_i810_softc *sc;
962 
963 	sc = device_get_softc(dev);
964 	sc->stolen = 0;
965 	sc->stolen_size = 0;
966 	return (0);
967 }
968 
969 static int
970 agp_i830_get_stolen_size(device_t dev)
971 {
972 	struct agp_i810_softc *sc;
973 	unsigned int gcc1;
974 
975 	sc = device_get_softc(dev);
976 
977 	gcc1 = pci_read_config(sc->bdev, AGP_I830_GCC1, 1);
978 	switch (gcc1 & AGP_I830_GCC1_GMS) {
979 	case AGP_I830_GCC1_GMS_STOLEN_512:
980 		sc->stolen = (512 - 132) * 1024 / 4096;
981 		sc->stolen_size = 512 * 1024;
982 		break;
983 	case AGP_I830_GCC1_GMS_STOLEN_1024:
984 		sc->stolen = (1024 - 132) * 1024 / 4096;
985 		sc->stolen_size = 1024 * 1024;
986 		break;
987 	case AGP_I830_GCC1_GMS_STOLEN_8192:
988 		sc->stolen = (8192 - 132) * 1024 / 4096;
989 		sc->stolen_size = 8192 * 1024;
990 		break;
991 	default:
992 		sc->stolen = 0;
993 		device_printf(dev,
994 		    "unknown memory configuration, disabling (GCC1 %x)\n",
995 		    gcc1);
996 		return (EINVAL);
997 	}
998 	return (0);
999 }
1000 
1001 static int
1002 agp_i915_get_stolen_size(device_t dev)
1003 {
1004 	struct agp_i810_softc *sc;
1005 	unsigned int gcc1, stolen, gtt_size;
1006 
1007 	sc = device_get_softc(dev);
1008 
1009 	/*
1010 	 * Stolen memory is set up at the beginning of the aperture by
1011 	 * the BIOS, consisting of the GATT followed by 4kb for the
1012 	 * BIOS display.
1013 	 */
1014 	switch (sc->match->driver->chiptype) {
1015 	case CHIP_I855:
1016 		gtt_size = 128;
1017 		break;
1018 	case CHIP_I915:
1019 		gtt_size = 256;
1020 		break;
1021 	case CHIP_I965:
1022 		switch (bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL) &
1023 			AGP_I810_PGTBL_SIZE_MASK) {
1024 		case AGP_I810_PGTBL_SIZE_128KB:
1025 			gtt_size = 128;
1026 			break;
1027 		case AGP_I810_PGTBL_SIZE_256KB:
1028 			gtt_size = 256;
1029 			break;
1030 		case AGP_I810_PGTBL_SIZE_512KB:
1031 			gtt_size = 512;
1032 			break;
1033 		case AGP_I965_PGTBL_SIZE_1MB:
1034 			gtt_size = 1024;
1035 			break;
1036 		case AGP_I965_PGTBL_SIZE_2MB:
1037 			gtt_size = 2048;
1038 			break;
1039 		case AGP_I965_PGTBL_SIZE_1_5MB:
1040 			gtt_size = 1024 + 512;
1041 			break;
1042 		default:
1043 			device_printf(dev, "Bad PGTBL size\n");
1044 			return (EINVAL);
1045 		}
1046 		break;
1047 	case CHIP_G33:
1048 		gcc1 = pci_read_config(sc->bdev, AGP_I855_GCC1, 2);
1049 		switch (gcc1 & AGP_G33_MGGC_GGMS_MASK) {
1050 		case AGP_G33_MGGC_GGMS_SIZE_1M:
1051 			gtt_size = 1024;
1052 			break;
1053 		case AGP_G33_MGGC_GGMS_SIZE_2M:
1054 			gtt_size = 2048;
1055 			break;
1056 		default:
1057 			device_printf(dev, "Bad PGTBL size\n");
1058 			return (EINVAL);
1059 		}
1060 		break;
1061 	case CHIP_IGD:
1062 	case CHIP_G4X:
1063 		gtt_size = 0;
1064 		break;
1065 	default:
1066 		device_printf(dev, "Bad chiptype\n");
1067 		return (EINVAL);
1068 	}
1069 
1070 	/* GCC1 is called MGGC on i915+ */
1071 	gcc1 = pci_read_config(sc->bdev, AGP_I855_GCC1, 1);
1072 	switch (gcc1 & AGP_I855_GCC1_GMS) {
1073 	case AGP_I855_GCC1_GMS_STOLEN_1M:
1074 		stolen = 1024;
1075 		break;
1076 	case AGP_I855_GCC1_GMS_STOLEN_4M:
1077 		stolen = 4 * 1024;
1078 		break;
1079 	case AGP_I855_GCC1_GMS_STOLEN_8M:
1080 		stolen = 8 * 1024;
1081 		break;
1082 	case AGP_I855_GCC1_GMS_STOLEN_16M:
1083 		stolen = 16 * 1024;
1084 		break;
1085 	case AGP_I855_GCC1_GMS_STOLEN_32M:
1086 		stolen = 32 * 1024;
1087 		break;
1088 	case AGP_I915_GCC1_GMS_STOLEN_48M:
1089 		stolen = sc->match->driver->gen > 2 ? 48 * 1024 : 0;
1090 		break;
1091 	case AGP_I915_GCC1_GMS_STOLEN_64M:
1092 		stolen = sc->match->driver->gen > 2 ? 64 * 1024 : 0;
1093 		break;
1094 	case AGP_G33_GCC1_GMS_STOLEN_128M:
1095 		stolen = sc->match->driver->gen > 2 ? 128 * 1024 : 0;
1096 		break;
1097 	case AGP_G33_GCC1_GMS_STOLEN_256M:
1098 		stolen = sc->match->driver->gen > 2 ? 256 * 1024 : 0;
1099 		break;
1100 	case AGP_G4X_GCC1_GMS_STOLEN_96M:
1101 		if (sc->match->driver->chiptype == CHIP_I965 ||
1102 		    sc->match->driver->chiptype == CHIP_G4X)
1103 			stolen = 96 * 1024;
1104 		else
1105 			stolen = 0;
1106 		break;
1107 	case AGP_G4X_GCC1_GMS_STOLEN_160M:
1108 		if (sc->match->driver->chiptype == CHIP_I965 ||
1109 		    sc->match->driver->chiptype == CHIP_G4X)
1110 			stolen = 160 * 1024;
1111 		else
1112 			stolen = 0;
1113 		break;
1114 	case AGP_G4X_GCC1_GMS_STOLEN_224M:
1115 		if (sc->match->driver->chiptype == CHIP_I965 ||
1116 		    sc->match->driver->chiptype == CHIP_G4X)
1117 			stolen = 224 * 1024;
1118 		else
1119 			stolen = 0;
1120 		break;
1121 	case AGP_G4X_GCC1_GMS_STOLEN_352M:
1122 		if (sc->match->driver->chiptype == CHIP_I965 ||
1123 		    sc->match->driver->chiptype == CHIP_G4X)
1124 			stolen = 352 * 1024;
1125 		else
1126 			stolen = 0;
1127 		break;
1128 	default:
1129 		device_printf(dev,
1130 		    "unknown memory configuration, disabling (GCC1 %x)\n",
1131 		    gcc1);
1132 		return (EINVAL);
1133 	}
1134 
1135 	gtt_size += 4;
1136 	sc->stolen_size = stolen * 1024;
1137 	sc->stolen = (stolen - gtt_size) * 1024 / 4096;
1138 
1139 	return (0);
1140 }
1141 
1142 static int
1143 agp_sb_get_stolen_size(device_t dev)
1144 {
1145 	struct agp_i810_softc *sc;
1146 	uint16_t gmch_ctl;
1147 
1148 	sc = device_get_softc(dev);
1149 	gmch_ctl = pci_read_config(sc->bdev, AGP_SNB_GCC1, 2);
1150 	switch (gmch_ctl & AGP_SNB_GMCH_GMS_STOLEN_MASK) {
1151 	case AGP_SNB_GMCH_GMS_STOLEN_32M:
1152 		sc->stolen_size = 32 * 1024 * 1024;
1153 		break;
1154 	case AGP_SNB_GMCH_GMS_STOLEN_64M:
1155 		sc->stolen_size = 64 * 1024 * 1024;
1156 		break;
1157 	case AGP_SNB_GMCH_GMS_STOLEN_96M:
1158 		sc->stolen_size = 96 * 1024 * 1024;
1159 		break;
1160 	case AGP_SNB_GMCH_GMS_STOLEN_128M:
1161 		sc->stolen_size = 128 * 1024 * 1024;
1162 		break;
1163 	case AGP_SNB_GMCH_GMS_STOLEN_160M:
1164 		sc->stolen_size = 160 * 1024 * 1024;
1165 		break;
1166 	case AGP_SNB_GMCH_GMS_STOLEN_192M:
1167 		sc->stolen_size = 192 * 1024 * 1024;
1168 		break;
1169 	case AGP_SNB_GMCH_GMS_STOLEN_224M:
1170 		sc->stolen_size = 224 * 1024 * 1024;
1171 		break;
1172 	case AGP_SNB_GMCH_GMS_STOLEN_256M:
1173 		sc->stolen_size = 256 * 1024 * 1024;
1174 		break;
1175 	case AGP_SNB_GMCH_GMS_STOLEN_288M:
1176 		sc->stolen_size = 288 * 1024 * 1024;
1177 		break;
1178 	case AGP_SNB_GMCH_GMS_STOLEN_320M:
1179 		sc->stolen_size = 320 * 1024 * 1024;
1180 		break;
1181 	case AGP_SNB_GMCH_GMS_STOLEN_352M:
1182 		sc->stolen_size = 352 * 1024 * 1024;
1183 		break;
1184 	case AGP_SNB_GMCH_GMS_STOLEN_384M:
1185 		sc->stolen_size = 384 * 1024 * 1024;
1186 		break;
1187 	case AGP_SNB_GMCH_GMS_STOLEN_416M:
1188 		sc->stolen_size = 416 * 1024 * 1024;
1189 		break;
1190 	case AGP_SNB_GMCH_GMS_STOLEN_448M:
1191 		sc->stolen_size = 448 * 1024 * 1024;
1192 		break;
1193 	case AGP_SNB_GMCH_GMS_STOLEN_480M:
1194 		sc->stolen_size = 480 * 1024 * 1024;
1195 		break;
1196 	case AGP_SNB_GMCH_GMS_STOLEN_512M:
1197 		sc->stolen_size = 512 * 1024 * 1024;
1198 		break;
1199 	}
1200 	sc->stolen = (sc->stolen_size - 4) / 4096;
1201 	return (0);
1202 }
1203 
1204 static int
1205 agp_i810_get_gtt_mappable_entries(device_t dev)
1206 {
1207 	struct agp_i810_softc *sc;
1208 	uint32_t ap;
1209 	uint16_t miscc;
1210 
1211 	sc = device_get_softc(dev);
1212 	miscc = pci_read_config(sc->bdev, AGP_I810_MISCC, 2);
1213 	if ((miscc & AGP_I810_MISCC_WINSIZE) == AGP_I810_MISCC_WINSIZE_32)
1214 		ap = 32;
1215 	else
1216 		ap = 64;
1217 	sc->gtt_mappable_entries = (ap * 1024 * 1024) >> AGP_PAGE_SHIFT;
1218 	return (0);
1219 }
1220 
1221 static int
1222 agp_i830_get_gtt_mappable_entries(device_t dev)
1223 {
1224 	struct agp_i810_softc *sc;
1225 	uint32_t ap;
1226 	uint16_t gmch_ctl;
1227 
1228 	sc = device_get_softc(dev);
1229 	gmch_ctl = pci_read_config(sc->bdev, AGP_I830_GCC1, 2);
1230 	if ((gmch_ctl & AGP_I830_GCC1_GMASIZE) == AGP_I830_GCC1_GMASIZE_64)
1231 		ap = 64;
1232 	else
1233 		ap = 128;
1234 	sc->gtt_mappable_entries = (ap * 1024 * 1024) >> AGP_PAGE_SHIFT;
1235 	return (0);
1236 }
1237 
1238 static int
1239 agp_i915_get_gtt_mappable_entries(device_t dev)
1240 {
1241 	struct agp_i810_softc *sc;
1242 	uint32_t ap;
1243 
1244 	sc = device_get_softc(dev);
1245 	ap = AGP_GET_APERTURE(dev);
1246 	sc->gtt_mappable_entries = ap >> AGP_PAGE_SHIFT;
1247 	return (0);
1248 }
1249 
1250 static int
1251 agp_i810_get_gtt_total_entries(device_t dev)
1252 {
1253 	struct agp_i810_softc *sc;
1254 
1255 	sc = device_get_softc(dev);
1256 	sc->gtt_total_entries = sc->gtt_mappable_entries;
1257 	return (0);
1258 }
1259 
1260 static int
1261 agp_i965_get_gtt_total_entries(device_t dev)
1262 {
1263 	struct agp_i810_softc *sc;
1264 	uint32_t pgetbl_ctl;
1265 	int error;
1266 
1267 	sc = device_get_softc(dev);
1268 	error = 0;
1269 	pgetbl_ctl = bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL);
1270 	switch (pgetbl_ctl & AGP_I810_PGTBL_SIZE_MASK) {
1271 	case AGP_I810_PGTBL_SIZE_128KB:
1272 		sc->gtt_total_entries = 128 * 1024 / 4;
1273 		break;
1274 	case AGP_I810_PGTBL_SIZE_256KB:
1275 		sc->gtt_total_entries = 256 * 1024 / 4;
1276 		break;
1277 	case AGP_I810_PGTBL_SIZE_512KB:
1278 		sc->gtt_total_entries = 512 * 1024 / 4;
1279 		break;
1280 	/* GTT pagetable sizes bigger than 512KB are not possible on G33! */
1281 	case AGP_I810_PGTBL_SIZE_1MB:
1282 		sc->gtt_total_entries = 1024 * 1024 / 4;
1283 		break;
1284 	case AGP_I810_PGTBL_SIZE_2MB:
1285 		sc->gtt_total_entries = 2 * 1024 * 1024 / 4;
1286 		break;
1287 	case AGP_I810_PGTBL_SIZE_1_5MB:
1288 		sc->gtt_total_entries = (1024 + 512) * 1024 / 4;
1289 		break;
1290 	default:
1291 		device_printf(dev, "Unknown page table size\n");
1292 		error = ENXIO;
1293 	}
1294 	return (error);
1295 }
1296 
1297 static void
1298 agp_gen5_adjust_pgtbl_size(device_t dev, uint32_t sz)
1299 {
1300 	struct agp_i810_softc *sc;
1301 	uint32_t pgetbl_ctl, pgetbl_ctl2;
1302 
1303 	sc = device_get_softc(dev);
1304 
1305 	/* Disable per-process page table. */
1306 	pgetbl_ctl2 = bus_read_4(sc->sc_res[0], AGP_I965_PGTBL_CTL2);
1307 	pgetbl_ctl2 &= ~AGP_I810_PGTBL_ENABLED;
1308 	bus_write_4(sc->sc_res[0], AGP_I965_PGTBL_CTL2, pgetbl_ctl2);
1309 
1310 	/* Write the new ggtt size. */
1311 	pgetbl_ctl = bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL);
1312 	pgetbl_ctl &= ~AGP_I810_PGTBL_SIZE_MASK;
1313 	pgetbl_ctl |= sz;
1314 	bus_write_4(sc->sc_res[0], AGP_I810_PGTBL_CTL, pgetbl_ctl);
1315 }
1316 
1317 static int
1318 agp_gen5_get_gtt_total_entries(device_t dev)
1319 {
1320 	struct agp_i810_softc *sc;
1321 	uint16_t gcc1;
1322 
1323 	sc = device_get_softc(dev);
1324 
1325 	gcc1 = pci_read_config(sc->bdev, AGP_I830_GCC1, 2);
1326 	switch (gcc1 & AGP_G4x_GCC1_SIZE_MASK) {
1327 	case AGP_G4x_GCC1_SIZE_1M:
1328 	case AGP_G4x_GCC1_SIZE_VT_1M:
1329 		agp_gen5_adjust_pgtbl_size(dev, AGP_I810_PGTBL_SIZE_1MB);
1330 		break;
1331 	case AGP_G4x_GCC1_SIZE_VT_1_5M:
1332 		agp_gen5_adjust_pgtbl_size(dev, AGP_I810_PGTBL_SIZE_1_5MB);
1333 		break;
1334 	case AGP_G4x_GCC1_SIZE_2M:
1335 	case AGP_G4x_GCC1_SIZE_VT_2M:
1336 		agp_gen5_adjust_pgtbl_size(dev, AGP_I810_PGTBL_SIZE_2MB);
1337 		break;
1338 	default:
1339 		device_printf(dev, "Unknown page table size\n");
1340 		return (ENXIO);
1341 	}
1342 
1343 	return (agp_i965_get_gtt_total_entries(dev));
1344 }
1345 
1346 static int
1347 agp_sb_get_gtt_total_entries(device_t dev)
1348 {
1349 	struct agp_i810_softc *sc;
1350 	uint16_t gcc1;
1351 
1352 	sc = device_get_softc(dev);
1353 
1354 	gcc1 = pci_read_config(sc->bdev, AGP_SNB_GCC1, 2);
1355 	switch (gcc1 & AGP_SNB_GTT_SIZE_MASK) {
1356 	default:
1357 	case AGP_SNB_GTT_SIZE_0M:
1358 		printf("Bad GTT size mask: 0x%04x\n", gcc1);
1359 		return (ENXIO);
1360 	case AGP_SNB_GTT_SIZE_1M:
1361 		sc->gtt_total_entries = 1024 * 1024 / 4;
1362 		break;
1363 	case AGP_SNB_GTT_SIZE_2M:
1364 		sc->gtt_total_entries = 2 * 1024 * 1024 / 4;
1365 		break;
1366 	}
1367 	return (0);
1368 }
1369 
1370 static int
1371 agp_i810_install_gatt(device_t dev)
1372 {
1373 	struct agp_i810_softc *sc;
1374 
1375 	sc = device_get_softc(dev);
1376 
1377 	/* Some i810s have on-chip memory called dcache. */
1378 	if ((bus_read_1(sc->sc_res[0], AGP_I810_DRT) & AGP_I810_DRT_POPULATED)
1379 	    != 0)
1380 		sc->dcache_size = 4 * 1024 * 1024;
1381 	else
1382 		sc->dcache_size = 0;
1383 
1384 	/* According to the specs the gatt on the i810 must be 64k. */
1385 	sc->gatt->ag_virtual = contigmalloc(64 * 1024, M_AGP, 0, 0, ~0,
1386 	    PAGE_SIZE, 0);
1387 	if (sc->gatt->ag_virtual == NULL) {
1388 		if (bootverbose)
1389 			device_printf(dev, "contiguous allocation failed\n");
1390 		return (ENOMEM);
1391 	}
1392 
1393 	bzero(sc->gatt->ag_virtual, sc->gatt->ag_entries * sizeof(u_int32_t));
1394 	sc->gatt->ag_physical = vtophys((vm_offset_t)sc->gatt->ag_virtual);
1395 	agp_flush_cache();
1396 	/* Install the GATT. */
1397 	bus_write_4(sc->sc_res[0], AGP_I810_PGTBL_CTL,
1398 	    sc->gatt->ag_physical | 1);
1399 	return (0);
1400 }
1401 
1402 static int
1403 agp_i830_install_gatt(device_t dev)
1404 {
1405 	struct agp_i810_softc *sc;
1406 	uint32_t pgtblctl;
1407 
1408 	sc = device_get_softc(dev);
1409 
1410 	/*
1411 	 * The i830 automatically initializes the 128k gatt on boot.
1412 	 * GATT address is already in there, make sure it's enabled.
1413 	 */
1414 	pgtblctl = bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL);
1415 	pgtblctl |= 1;
1416 	bus_write_4(sc->sc_res[0], AGP_I810_PGTBL_CTL, pgtblctl);
1417 
1418 	sc->gatt->ag_physical = pgtblctl & ~1;
1419 	return (0);
1420 }
1421 
1422 static int
1423 agp_i810_attach(device_t dev)
1424 {
1425 	struct agp_i810_softc *sc;
1426 	int error;
1427 
1428 	sc = device_get_softc(dev);
1429 	sc->bdev = agp_i810_find_bridge(dev);
1430 	if (sc->bdev == NULL)
1431 		return (ENOENT);
1432 
1433 	sc->match = agp_i810_match(dev);
1434 
1435 	agp_set_aperture_resource(dev, sc->match->driver->gen <= 2 ?
1436 	    AGP_APBASE : AGP_I915_GMADR);
1437 	error = agp_generic_attach(dev);
1438 	if (error)
1439 		return (error);
1440 
1441 	if (ptoa((vm_paddr_t)Maxmem) >
1442 	    (1ULL << sc->match->driver->busdma_addr_mask_sz) - 1) {
1443 		device_printf(dev, "agp_i810 does not support physical "
1444 		    "memory above %ju.\n", (uintmax_t)(1ULL <<
1445 		    sc->match->driver->busdma_addr_mask_sz) - 1);
1446 		return (ENOENT);
1447 	}
1448 
1449 	if (bus_alloc_resources(dev, sc->match->driver->res_spec, sc->sc_res)) {
1450 		agp_generic_detach(dev);
1451 		return (ENODEV);
1452 	}
1453 
1454 	sc->initial_aperture = AGP_GET_APERTURE(dev);
1455 	sc->gatt = malloc(sizeof(struct agp_gatt), M_AGP, M_WAITOK);
1456 	sc->gatt->ag_entries = AGP_GET_APERTURE(dev) >> AGP_PAGE_SHIFT;
1457 
1458 	if ((error = sc->match->driver->get_stolen_size(dev)) != 0 ||
1459 	    (error = sc->match->driver->install_gatt(dev)) != 0 ||
1460 	    (error = sc->match->driver->get_gtt_mappable_entries(dev)) != 0 ||
1461 	    (error = sc->match->driver->get_gtt_total_entries(dev)) != 0 ||
1462 	    (error = sc->match->driver->chipset_flush_setup(dev)) != 0) {
1463 		bus_release_resources(dev, sc->match->driver->res_spec,
1464 		    sc->sc_res);
1465 		free(sc->gatt, M_AGP);
1466 		agp_generic_detach(dev);
1467 		return (error);
1468 	}
1469 
1470 	intel_agp = dev;
1471 	device_printf(dev, "aperture size is %dM",
1472 	    sc->initial_aperture / 1024 / 1024);
1473 	if (sc->stolen > 0)
1474 		printf(", detected %dk stolen memory\n", sc->stolen * 4);
1475 	else
1476 		printf("\n");
1477 	if (bootverbose) {
1478 		sc->match->driver->dump_regs(dev);
1479 		device_printf(dev, "Mappable GTT entries: %d\n",
1480 		    sc->gtt_mappable_entries);
1481 		device_printf(dev, "Total GTT entries: %d\n",
1482 		    sc->gtt_total_entries);
1483 	}
1484 	return (0);
1485 }
1486 
1487 static void
1488 agp_i810_deinstall_gatt(device_t dev)
1489 {
1490 	struct agp_i810_softc *sc;
1491 
1492 	sc = device_get_softc(dev);
1493 	bus_write_4(sc->sc_res[0], AGP_I810_PGTBL_CTL, 0);
1494 	contigfree(sc->gatt->ag_virtual, 64 * 1024, M_AGP);
1495 }
1496 
1497 static void
1498 agp_i830_deinstall_gatt(device_t dev)
1499 {
1500 	struct agp_i810_softc *sc;
1501 	unsigned int pgtblctl;
1502 
1503 	sc = device_get_softc(dev);
1504 	pgtblctl = bus_read_4(sc->sc_res[0], AGP_I810_PGTBL_CTL);
1505 	pgtblctl &= ~1;
1506 	bus_write_4(sc->sc_res[0], AGP_I810_PGTBL_CTL, pgtblctl);
1507 }
1508 
1509 static int
1510 agp_i810_detach(device_t dev)
1511 {
1512 	struct agp_i810_softc *sc;
1513 
1514 	sc = device_get_softc(dev);
1515 	agp_free_cdev(dev);
1516 
1517 	/* Clear the GATT base. */
1518 	sc->match->driver->deinstall_gatt(dev);
1519 
1520 	sc->match->driver->chipset_flush_teardown(dev);
1521 
1522 	/* Put the aperture back the way it started. */
1523 	AGP_SET_APERTURE(dev, sc->initial_aperture);
1524 
1525 	free(sc->gatt, M_AGP);
1526 	bus_release_resources(dev, sc->match->driver->res_spec, sc->sc_res);
1527 	agp_free_res(dev);
1528 
1529 	return (0);
1530 }
1531 
1532 static int
1533 agp_i810_resume(device_t dev)
1534 {
1535 	struct agp_i810_softc *sc;
1536 	sc = device_get_softc(dev);
1537 
1538 	AGP_SET_APERTURE(dev, sc->initial_aperture);
1539 
1540 	/* Install the GATT. */
1541 	bus_write_4(sc->sc_res[0], AGP_I810_PGTBL_CTL,
1542 	sc->gatt->ag_physical | 1);
1543 
1544 	return (bus_generic_resume(dev));
1545 }
1546 
1547 /**
1548  * Sets the PCI resource size of the aperture on i830-class and below chipsets,
1549  * while returning failure on later chipsets when an actual change is
1550  * requested.
1551  *
1552  * This whole function is likely bogus, as the kernel would probably need to
1553  * reconfigure the placement of the AGP aperture if a larger size is requested,
1554  * which doesn't happen currently.
1555  */
1556 static int
1557 agp_i810_set_aperture(device_t dev, u_int32_t aperture)
1558 {
1559 	struct agp_i810_softc *sc;
1560 	u_int16_t miscc;
1561 
1562 	sc = device_get_softc(dev);
1563 	/*
1564 	 * Double check for sanity.
1565 	 */
1566 	if (aperture != 32 * 1024 * 1024 && aperture != 64 * 1024 * 1024) {
1567 		device_printf(dev, "bad aperture size %d\n", aperture);
1568 		return (EINVAL);
1569 	}
1570 
1571 	miscc = pci_read_config(sc->bdev, AGP_I810_MISCC, 2);
1572 	miscc &= ~AGP_I810_MISCC_WINSIZE;
1573 	if (aperture == 32 * 1024 * 1024)
1574 		miscc |= AGP_I810_MISCC_WINSIZE_32;
1575 	else
1576 		miscc |= AGP_I810_MISCC_WINSIZE_64;
1577 
1578 	pci_write_config(sc->bdev, AGP_I810_MISCC, miscc, 2);
1579 	return (0);
1580 }
1581 
1582 static int
1583 agp_i830_set_aperture(device_t dev, u_int32_t aperture)
1584 {
1585 	struct agp_i810_softc *sc;
1586 	u_int16_t gcc1;
1587 
1588 	sc = device_get_softc(dev);
1589 
1590 	if (aperture != 64 * 1024 * 1024 &&
1591 	    aperture != 128 * 1024 * 1024) {
1592 		device_printf(dev, "bad aperture size %d\n", aperture);
1593 		return (EINVAL);
1594 	}
1595 	gcc1 = pci_read_config(sc->bdev, AGP_I830_GCC1, 2);
1596 	gcc1 &= ~AGP_I830_GCC1_GMASIZE;
1597 	if (aperture == 64 * 1024 * 1024)
1598 		gcc1 |= AGP_I830_GCC1_GMASIZE_64;
1599 	else
1600 		gcc1 |= AGP_I830_GCC1_GMASIZE_128;
1601 
1602 	pci_write_config(sc->bdev, AGP_I830_GCC1, gcc1, 2);
1603 	return (0);
1604 }
1605 
1606 static int
1607 agp_i915_set_aperture(device_t dev, u_int32_t aperture)
1608 {
1609 
1610 	return (agp_generic_set_aperture(dev, aperture));
1611 }
1612 
1613 static int
1614 agp_i810_method_set_aperture(device_t dev, u_int32_t aperture)
1615 {
1616 	struct agp_i810_softc *sc;
1617 
1618 	sc = device_get_softc(dev);
1619 	return (sc->match->driver->set_aperture(dev, aperture));
1620 }
1621 
1622 /**
1623  * Writes a GTT entry mapping the page at the given offset from the
1624  * beginning of the aperture to the given physical address.  Setup the
1625  * caching mode according to flags.
1626  *
1627  * For gen 1, 2 and 3, GTT start is located at AGP_I810_GTT offset
1628  * from corresponding BAR start. For gen 4, offset is 512KB +
1629  * AGP_I810_GTT, for gen 5 and 6 it is 2MB + AGP_I810_GTT.
1630  *
1631  * Also, the bits of the physical page address above 4GB needs to be
1632  * placed into bits 40-32 of PTE.
1633  */
1634 static void
1635 agp_i810_install_gtt_pte(device_t dev, u_int index, vm_offset_t physical,
1636     int flags)
1637 {
1638 	uint32_t pte;
1639 
1640 	pte = (u_int32_t)physical | I810_PTE_VALID;
1641 	if (flags == AGP_DCACHE_MEMORY)
1642 		pte |= I810_PTE_LOCAL;
1643 	else if (flags == AGP_USER_CACHED_MEMORY)
1644 		pte |= I830_PTE_SYSTEM_CACHED;
1645 	agp_i810_write_gtt(dev, index, pte);
1646 }
1647 
1648 static void
1649 agp_i810_write_gtt(device_t dev, u_int index, uint32_t pte)
1650 {
1651 	struct agp_i810_softc *sc;
1652 
1653 	sc = device_get_softc(dev);
1654 	bus_write_4(sc->sc_res[0], AGP_I810_GTT + index * 4, pte);
1655 	CTR2(KTR_AGP_I810, "810_pte %x %x", index, pte);
1656 }
1657 
1658 static void
1659 agp_i830_install_gtt_pte(device_t dev, u_int index, vm_offset_t physical,
1660     int flags)
1661 {
1662 	uint32_t pte;
1663 
1664 	pte = (u_int32_t)physical | I810_PTE_VALID;
1665 	if (flags == AGP_USER_CACHED_MEMORY)
1666 		pte |= I830_PTE_SYSTEM_CACHED;
1667 	agp_i810_write_gtt(dev, index, pte);
1668 }
1669 
1670 static void
1671 agp_i915_install_gtt_pte(device_t dev, u_int index, vm_offset_t physical,
1672     int flags)
1673 {
1674 	uint32_t pte;
1675 
1676 	pte = (u_int32_t)physical | I810_PTE_VALID;
1677 	if (flags == AGP_USER_CACHED_MEMORY)
1678 		pte |= I830_PTE_SYSTEM_CACHED;
1679 	pte |= (physical & 0x0000000f00000000ull) >> 28;
1680 	agp_i915_write_gtt(dev, index, pte);
1681 }
1682 
1683 static void
1684 agp_i915_write_gtt(device_t dev, u_int index, uint32_t pte)
1685 {
1686 	struct agp_i810_softc *sc;
1687 
1688 	sc = device_get_softc(dev);
1689 	bus_write_4(sc->sc_res[1], index * 4, pte);
1690 	CTR2(KTR_AGP_I810, "915_pte %x %x", index, pte);
1691 }
1692 
1693 static void
1694 agp_i965_install_gtt_pte(device_t dev, u_int index, vm_offset_t physical,
1695     int flags)
1696 {
1697 	uint32_t pte;
1698 
1699 	pte = (u_int32_t)physical | I810_PTE_VALID;
1700 	if (flags == AGP_USER_CACHED_MEMORY)
1701 		pte |= I830_PTE_SYSTEM_CACHED;
1702 	pte |= (physical & 0x0000000f00000000ull) >> 28;
1703 	agp_i965_write_gtt(dev, index, pte);
1704 }
1705 
1706 static void
1707 agp_i965_write_gtt(device_t dev, u_int index, uint32_t pte)
1708 {
1709 	struct agp_i810_softc *sc;
1710 
1711 	sc = device_get_softc(dev);
1712 	bus_write_4(sc->sc_res[0], index * 4 + (512 * 1024), pte);
1713 	CTR2(KTR_AGP_I810, "965_pte %x %x", index, pte);
1714 }
1715 
1716 static void
1717 agp_g4x_install_gtt_pte(device_t dev, u_int index, vm_offset_t physical,
1718     int flags)
1719 {
1720 	uint32_t pte;
1721 
1722 	pte = (u_int32_t)physical | I810_PTE_VALID;
1723 	if (flags == AGP_USER_CACHED_MEMORY)
1724 		pte |= I830_PTE_SYSTEM_CACHED;
1725 	pte |= (physical & 0x0000000f00000000ull) >> 28;
1726 	agp_g4x_write_gtt(dev, index, pte);
1727 }
1728 
1729 static void
1730 agp_g4x_write_gtt(device_t dev, u_int index, uint32_t pte)
1731 {
1732 	struct agp_i810_softc *sc;
1733 
1734 	sc = device_get_softc(dev);
1735 	bus_write_4(sc->sc_res[0], index * 4 + (2 * 1024 * 1024), pte);
1736 	CTR2(KTR_AGP_I810, "g4x_pte %x %x", index, pte);
1737 }
1738 
1739 static void
1740 agp_sb_install_gtt_pte(device_t dev, u_int index, vm_offset_t physical,
1741     int flags)
1742 {
1743 	int type_mask, gfdt;
1744 	uint32_t pte;
1745 
1746 	pte = (u_int32_t)physical | I810_PTE_VALID;
1747 	type_mask = flags & ~AGP_USER_CACHED_MEMORY_GFDT;
1748 	gfdt = (flags & AGP_USER_CACHED_MEMORY_GFDT) != 0 ? GEN6_PTE_GFDT : 0;
1749 
1750 	if (type_mask == AGP_USER_MEMORY)
1751 		pte |= GEN6_PTE_UNCACHED;
1752 	else if (type_mask == AGP_USER_CACHED_MEMORY_LLC_MLC)
1753 		pte |= GEN6_PTE_LLC_MLC | gfdt;
1754 	else
1755 		pte |= GEN6_PTE_LLC | gfdt;
1756 
1757 	pte |= (physical & 0x000000ff00000000ull) >> 28;
1758 	agp_sb_write_gtt(dev, index, pte);
1759 }
1760 
1761 static void
1762 agp_sb_write_gtt(device_t dev, u_int index, uint32_t pte)
1763 {
1764 	struct agp_i810_softc *sc;
1765 
1766 	sc = device_get_softc(dev);
1767 	bus_write_4(sc->sc_res[0], index * 4 + (2 * 1024 * 1024), pte);
1768 	CTR2(KTR_AGP_I810, "sb_pte %x %x", index, pte);
1769 }
1770 
1771 static int
1772 agp_i810_bind_page(device_t dev, vm_offset_t offset, vm_offset_t physical)
1773 {
1774 	struct agp_i810_softc *sc = device_get_softc(dev);
1775 	u_int index;
1776 
1777 	if (offset >= (sc->gatt->ag_entries << AGP_PAGE_SHIFT)) {
1778 		device_printf(dev, "failed: offset is 0x%08jx, "
1779 		    "shift is %d, entries is %d\n", (intmax_t)offset,
1780 		    AGP_PAGE_SHIFT, sc->gatt->ag_entries);
1781 		return (EINVAL);
1782 	}
1783 	index = offset >> AGP_PAGE_SHIFT;
1784 	if (sc->stolen != 0 && index < sc->stolen) {
1785 		device_printf(dev, "trying to bind into stolen memory\n");
1786 		return (EINVAL);
1787 	}
1788 	sc->match->driver->install_gtt_pte(dev, index, physical, 0);
1789 	return (0);
1790 }
1791 
1792 static int
1793 agp_i810_unbind_page(device_t dev, vm_offset_t offset)
1794 {
1795 	struct agp_i810_softc *sc;
1796 	u_int index;
1797 
1798 	sc = device_get_softc(dev);
1799 	if (offset >= (sc->gatt->ag_entries << AGP_PAGE_SHIFT))
1800 		return (EINVAL);
1801 	index = offset >> AGP_PAGE_SHIFT;
1802 	if (sc->stolen != 0 && index < sc->stolen) {
1803 		device_printf(dev, "trying to unbind from stolen memory\n");
1804 		return (EINVAL);
1805 	}
1806 	sc->match->driver->install_gtt_pte(dev, index, 0, 0);
1807 	return (0);
1808 }
1809 
1810 static u_int32_t
1811 agp_i810_read_gtt_pte(device_t dev, u_int index)
1812 {
1813 	struct agp_i810_softc *sc;
1814 	u_int32_t pte;
1815 
1816 	sc = device_get_softc(dev);
1817 	pte = bus_read_4(sc->sc_res[0], AGP_I810_GTT + index * 4);
1818 	return (pte);
1819 }
1820 
1821 static u_int32_t
1822 agp_i915_read_gtt_pte(device_t dev, u_int index)
1823 {
1824 	struct agp_i810_softc *sc;
1825 	u_int32_t pte;
1826 
1827 	sc = device_get_softc(dev);
1828 	pte = bus_read_4(sc->sc_res[1], index * 4);
1829 	return (pte);
1830 }
1831 
1832 static u_int32_t
1833 agp_i965_read_gtt_pte(device_t dev, u_int index)
1834 {
1835 	struct agp_i810_softc *sc;
1836 	u_int32_t pte;
1837 
1838 	sc = device_get_softc(dev);
1839 	pte = bus_read_4(sc->sc_res[0], index * 4 + (512 * 1024));
1840 	return (pte);
1841 }
1842 
1843 static u_int32_t
1844 agp_g4x_read_gtt_pte(device_t dev, u_int index)
1845 {
1846 	struct agp_i810_softc *sc;
1847 	u_int32_t pte;
1848 
1849 	sc = device_get_softc(dev);
1850 	pte = bus_read_4(sc->sc_res[0], index * 4 + (2 * 1024 * 1024));
1851 	return (pte);
1852 }
1853 
1854 static vm_paddr_t
1855 agp_i810_read_gtt_pte_paddr(device_t dev, u_int index)
1856 {
1857 	struct agp_i810_softc *sc;
1858 	u_int32_t pte;
1859 	vm_paddr_t res;
1860 
1861 	sc = device_get_softc(dev);
1862 	pte = sc->match->driver->read_gtt_pte(dev, index);
1863 	res = pte & ~PAGE_MASK;
1864 	return (res);
1865 }
1866 
1867 static vm_paddr_t
1868 agp_i915_read_gtt_pte_paddr(device_t dev, u_int index)
1869 {
1870 	struct agp_i810_softc *sc;
1871 	u_int32_t pte;
1872 	vm_paddr_t res;
1873 
1874 	sc = device_get_softc(dev);
1875 	pte = sc->match->driver->read_gtt_pte(dev, index);
1876 	res = (pte & ~PAGE_MASK) | ((pte & 0xf0) << 28);
1877 	return (res);
1878 }
1879 
1880 static vm_paddr_t
1881 agp_sb_read_gtt_pte_paddr(device_t dev, u_int index)
1882 {
1883 	struct agp_i810_softc *sc;
1884 	u_int32_t pte;
1885 	vm_paddr_t res;
1886 
1887 	sc = device_get_softc(dev);
1888 	pte = sc->match->driver->read_gtt_pte(dev, index);
1889 	res = (pte & ~PAGE_MASK) | ((pte & 0xff0) << 28);
1890 	return (res);
1891 }
1892 
1893 /*
1894  * Writing via memory mapped registers already flushes all TLBs.
1895  */
1896 static void
1897 agp_i810_flush_tlb(device_t dev)
1898 {
1899 }
1900 
1901 static int
1902 agp_i810_enable(device_t dev, u_int32_t mode)
1903 {
1904 
1905 	return (0);
1906 }
1907 
1908 static struct agp_memory *
1909 agp_i810_alloc_memory(device_t dev, int type, vm_size_t size)
1910 {
1911 	struct agp_i810_softc *sc;
1912 	struct agp_memory *mem;
1913 	vm_page_t m;
1914 
1915 	sc = device_get_softc(dev);
1916 
1917 	if ((size & (AGP_PAGE_SIZE - 1)) != 0 ||
1918 	    sc->agp.as_allocated + size > sc->agp.as_maxmem)
1919 		return (0);
1920 
1921 	if (type == 1) {
1922 		/*
1923 		 * Mapping local DRAM into GATT.
1924 		 */
1925 		if (sc->match->driver->chiptype != CHIP_I810)
1926 			return (0);
1927 		if (size != sc->dcache_size)
1928 			return (0);
1929 	} else if (type == 2) {
1930 		/*
1931 		 * Type 2 is the contiguous physical memory type, that hands
1932 		 * back a physical address.  This is used for cursors on i810.
1933 		 * Hand back as many single pages with physical as the user
1934 		 * wants, but only allow one larger allocation (ARGB cursor)
1935 		 * for simplicity.
1936 		 */
1937 		if (size != AGP_PAGE_SIZE) {
1938 			if (sc->argb_cursor != NULL)
1939 				return (0);
1940 
1941 			/* Allocate memory for ARGB cursor, if we can. */
1942 			sc->argb_cursor = contigmalloc(size, M_AGP,
1943 			   0, 0, ~0, PAGE_SIZE, 0);
1944 			if (sc->argb_cursor == NULL)
1945 				return (0);
1946 		}
1947 	}
1948 
1949 	mem = malloc(sizeof *mem, M_AGP, M_WAITOK);
1950 	mem->am_id = sc->agp.as_nextid++;
1951 	mem->am_size = size;
1952 	mem->am_type = type;
1953 	if (type != 1 && (type != 2 || size == AGP_PAGE_SIZE))
1954 		mem->am_obj = vm_object_allocate(OBJT_DEFAULT,
1955 		    atop(round_page(size)));
1956 	else
1957 		mem->am_obj = 0;
1958 
1959 	if (type == 2) {
1960 		if (size == AGP_PAGE_SIZE) {
1961 			/*
1962 			 * Allocate and wire down the page now so that we can
1963 			 * get its physical address.
1964 			 */
1965 			VM_OBJECT_LOCK(mem->am_obj);
1966 			m = vm_page_grab(mem->am_obj, 0, VM_ALLOC_NOBUSY |
1967 			    VM_ALLOC_WIRED | VM_ALLOC_ZERO | VM_ALLOC_RETRY);
1968 			VM_OBJECT_UNLOCK(mem->am_obj);
1969 			mem->am_physical = VM_PAGE_TO_PHYS(m);
1970 		} else {
1971 			/* Our allocation is already nicely wired down for us.
1972 			 * Just grab the physical address.
1973 			 */
1974 			mem->am_physical = vtophys(sc->argb_cursor);
1975 		}
1976 	} else
1977 		mem->am_physical = 0;
1978 
1979 	mem->am_offset = 0;
1980 	mem->am_is_bound = 0;
1981 	TAILQ_INSERT_TAIL(&sc->agp.as_memory, mem, am_link);
1982 	sc->agp.as_allocated += size;
1983 
1984 	return (mem);
1985 }
1986 
1987 static int
1988 agp_i810_free_memory(device_t dev, struct agp_memory *mem)
1989 {
1990 	struct agp_i810_softc *sc;
1991 	vm_page_t m;
1992 
1993 	if (mem->am_is_bound)
1994 		return (EBUSY);
1995 
1996 	sc = device_get_softc(dev);
1997 
1998 	if (mem->am_type == 2) {
1999 		if (mem->am_size == AGP_PAGE_SIZE) {
2000 			/*
2001 			 * Unwire the page which we wired in alloc_memory.
2002 			 */
2003 			VM_OBJECT_LOCK(mem->am_obj);
2004 			m = vm_page_lookup(mem->am_obj, 0);
2005 			vm_page_lock(m);
2006 			vm_page_unwire(m, 0);
2007 			vm_page_unlock(m);
2008 			VM_OBJECT_UNLOCK(mem->am_obj);
2009 		} else {
2010 			contigfree(sc->argb_cursor, mem->am_size, M_AGP);
2011 			sc->argb_cursor = NULL;
2012 		}
2013 	}
2014 
2015 	sc->agp.as_allocated -= mem->am_size;
2016 	TAILQ_REMOVE(&sc->agp.as_memory, mem, am_link);
2017 	if (mem->am_obj)
2018 		vm_object_deallocate(mem->am_obj);
2019 	free(mem, M_AGP);
2020 	return (0);
2021 }
2022 
2023 static int
2024 agp_i810_bind_memory(device_t dev, struct agp_memory *mem, vm_offset_t offset)
2025 {
2026 	struct agp_i810_softc *sc;
2027 	vm_offset_t i;
2028 
2029 	/* Do some sanity checks first. */
2030 	if ((offset & (AGP_PAGE_SIZE - 1)) != 0 ||
2031 	    offset + mem->am_size > AGP_GET_APERTURE(dev)) {
2032 		device_printf(dev, "binding memory at bad offset %#x\n",
2033 		    (int)offset);
2034 		return (EINVAL);
2035 	}
2036 
2037 	sc = device_get_softc(dev);
2038 	if (mem->am_type == 2 && mem->am_size != AGP_PAGE_SIZE) {
2039 		mtx_lock(&sc->agp.as_lock);
2040 		if (mem->am_is_bound) {
2041 			mtx_unlock(&sc->agp.as_lock);
2042 			return (EINVAL);
2043 		}
2044 		/* The memory's already wired down, just stick it in the GTT. */
2045 		for (i = 0; i < mem->am_size; i += AGP_PAGE_SIZE) {
2046 			sc->match->driver->install_gtt_pte(dev, (offset + i) >>
2047 			    AGP_PAGE_SHIFT, mem->am_physical + i, 0);
2048 		}
2049 		agp_flush_cache();
2050 		mem->am_offset = offset;
2051 		mem->am_is_bound = 1;
2052 		mtx_unlock(&sc->agp.as_lock);
2053 		return (0);
2054 	}
2055 
2056 	if (mem->am_type != 1)
2057 		return (agp_generic_bind_memory(dev, mem, offset));
2058 
2059 	/*
2060 	 * Mapping local DRAM into GATT.
2061 	 */
2062 	if (sc->match->driver->chiptype != CHIP_I810)
2063 		return (EINVAL);
2064 	for (i = 0; i < mem->am_size; i += AGP_PAGE_SIZE)
2065 		bus_write_4(sc->sc_res[0],
2066 		    AGP_I810_GTT + (i >> AGP_PAGE_SHIFT) * 4, i | 3);
2067 
2068 	return (0);
2069 }
2070 
2071 static int
2072 agp_i810_unbind_memory(device_t dev, struct agp_memory *mem)
2073 {
2074 	struct agp_i810_softc *sc;
2075 	vm_offset_t i;
2076 
2077 	sc = device_get_softc(dev);
2078 
2079 	if (mem->am_type == 2 && mem->am_size != AGP_PAGE_SIZE) {
2080 		mtx_lock(&sc->agp.as_lock);
2081 		if (!mem->am_is_bound) {
2082 			mtx_unlock(&sc->agp.as_lock);
2083 			return (EINVAL);
2084 		}
2085 
2086 		for (i = 0; i < mem->am_size; i += AGP_PAGE_SIZE) {
2087 			sc->match->driver->install_gtt_pte(dev,
2088 			    (mem->am_offset + i) >> AGP_PAGE_SHIFT, 0, 0);
2089 		}
2090 		agp_flush_cache();
2091 		mem->am_is_bound = 0;
2092 		mtx_unlock(&sc->agp.as_lock);
2093 		return (0);
2094 	}
2095 
2096 	if (mem->am_type != 1)
2097 		return (agp_generic_unbind_memory(dev, mem));
2098 
2099 	if (sc->match->driver->chiptype != CHIP_I810)
2100 		return (EINVAL);
2101 	for (i = 0; i < mem->am_size; i += AGP_PAGE_SIZE) {
2102 		sc->match->driver->install_gtt_pte(dev, i >> AGP_PAGE_SHIFT,
2103 		    0, 0);
2104 	}
2105 	return (0);
2106 }
2107 
2108 static device_method_t agp_i810_methods[] = {
2109 	/* Device interface */
2110 	DEVMETHOD(device_identify,	agp_i810_identify),
2111 	DEVMETHOD(device_probe,		agp_i810_probe),
2112 	DEVMETHOD(device_attach,	agp_i810_attach),
2113 	DEVMETHOD(device_detach,	agp_i810_detach),
2114 	DEVMETHOD(device_suspend,	bus_generic_suspend),
2115 	DEVMETHOD(device_resume,	agp_i810_resume),
2116 
2117 	/* AGP interface */
2118 	DEVMETHOD(agp_get_aperture,	agp_generic_get_aperture),
2119 	DEVMETHOD(agp_set_aperture,	agp_i810_method_set_aperture),
2120 	DEVMETHOD(agp_bind_page,	agp_i810_bind_page),
2121 	DEVMETHOD(agp_unbind_page,	agp_i810_unbind_page),
2122 	DEVMETHOD(agp_flush_tlb,	agp_i810_flush_tlb),
2123 	DEVMETHOD(agp_enable,		agp_i810_enable),
2124 	DEVMETHOD(agp_alloc_memory,	agp_i810_alloc_memory),
2125 	DEVMETHOD(agp_free_memory,	agp_i810_free_memory),
2126 	DEVMETHOD(agp_bind_memory,	agp_i810_bind_memory),
2127 	DEVMETHOD(agp_unbind_memory,	agp_i810_unbind_memory),
2128 	DEVMETHOD(agp_chipset_flush,	agp_intel_gtt_chipset_flush),
2129 
2130 	{ 0, 0 }
2131 };
2132 
2133 static driver_t agp_i810_driver = {
2134 	"agp",
2135 	agp_i810_methods,
2136 	sizeof(struct agp_i810_softc),
2137 };
2138 
2139 static devclass_t agp_devclass;
2140 
2141 DRIVER_MODULE(agp_i810, vgapci, agp_i810_driver, agp_devclass, 0, 0);
2142 MODULE_DEPEND(agp_i810, agp, 1, 1, 1);
2143 MODULE_DEPEND(agp_i810, pci, 1, 1, 1);
2144 
2145 extern vm_page_t bogus_page;
2146 
2147 void
2148 agp_intel_gtt_clear_range(device_t dev, u_int first_entry, u_int num_entries)
2149 {
2150 	struct agp_i810_softc *sc;
2151 	u_int i;
2152 
2153 	sc = device_get_softc(dev);
2154 	for (i = 0; i < num_entries; i++)
2155 		sc->match->driver->install_gtt_pte(dev, first_entry + i,
2156 		    VM_PAGE_TO_PHYS(bogus_page), 0);
2157 	sc->match->driver->read_gtt_pte(dev, first_entry + num_entries - 1);
2158 }
2159 
2160 void
2161 agp_intel_gtt_insert_pages(device_t dev, u_int first_entry, u_int num_entries,
2162     vm_page_t *pages, u_int flags)
2163 {
2164 	struct agp_i810_softc *sc;
2165 	u_int i;
2166 
2167 	sc = device_get_softc(dev);
2168 	for (i = 0; i < num_entries; i++) {
2169 		MPASS(pages[i]->valid == VM_PAGE_BITS_ALL);
2170 		MPASS(pages[i]->wire_count > 0);
2171 		sc->match->driver->install_gtt_pte(dev, first_entry + i,
2172 		    VM_PAGE_TO_PHYS(pages[i]), flags);
2173 	}
2174 	sc->match->driver->read_gtt_pte(dev, first_entry + num_entries - 1);
2175 }
2176 
2177 struct intel_gtt
2178 agp_intel_gtt_get(device_t dev)
2179 {
2180 	struct agp_i810_softc *sc;
2181 	struct intel_gtt res;
2182 
2183 	sc = device_get_softc(dev);
2184 	res.stolen_size = sc->stolen_size;
2185 	res.gtt_total_entries = sc->gtt_total_entries;
2186 	res.gtt_mappable_entries = sc->gtt_mappable_entries;
2187 	res.do_idle_maps = 0;
2188 	res.scratch_page_dma = VM_PAGE_TO_PHYS(bogus_page);
2189 	return (res);
2190 }
2191 
2192 static int
2193 agp_i810_chipset_flush_setup(device_t dev)
2194 {
2195 
2196 	return (0);
2197 }
2198 
2199 static void
2200 agp_i810_chipset_flush_teardown(device_t dev)
2201 {
2202 
2203 	/* Nothing to do. */
2204 }
2205 
2206 static void
2207 agp_i810_chipset_flush(device_t dev)
2208 {
2209 
2210 	/* Nothing to do. */
2211 }
2212 
2213 static void
2214 agp_i830_chipset_flush(device_t dev)
2215 {
2216 	struct agp_i810_softc *sc;
2217 	uint32_t hic;
2218 	int i;
2219 
2220 	sc = device_get_softc(dev);
2221 	pmap_invalidate_cache();
2222 	hic = bus_read_4(sc->sc_res[0], AGP_I830_HIC);
2223 	bus_write_4(sc->sc_res[0], AGP_I830_HIC, hic | (1 << 31));
2224 	for (i = 0; i < 20000 /* 1 sec */; i++) {
2225 		hic = bus_read_4(sc->sc_res[0], AGP_I830_HIC);
2226 		if ((hic & (1 << 31)) != 0)
2227 			break;
2228 		DELAY(50);
2229 	}
2230 }
2231 
2232 static int
2233 agp_i915_chipset_flush_alloc_page(device_t dev, uint64_t start, uint64_t end)
2234 {
2235 	struct agp_i810_softc *sc;
2236 	device_t vga;
2237 
2238 	sc = device_get_softc(dev);
2239 	vga = device_get_parent(dev);
2240 	sc->sc_flush_page_rid = 100;
2241 	sc->sc_flush_page_res = BUS_ALLOC_RESOURCE(device_get_parent(vga), dev,
2242 	    SYS_RES_MEMORY, &sc->sc_flush_page_rid, start, end, PAGE_SIZE,
2243 	    RF_ACTIVE);
2244 	if (sc->sc_flush_page_res == NULL) {
2245 		device_printf(dev, "Failed to allocate flush page at 0x%jx\n",
2246 		    (uintmax_t)start);
2247 		return (EINVAL);
2248 	}
2249 	sc->sc_flush_page_vaddr = rman_get_virtual(sc->sc_flush_page_res);
2250 	if (bootverbose) {
2251 		device_printf(dev, "Allocated flush page phys 0x%jx virt %p\n",
2252 		    (uintmax_t)rman_get_start(sc->sc_flush_page_res),
2253 		    sc->sc_flush_page_vaddr);
2254 	}
2255 	return (0);
2256 }
2257 
2258 static void
2259 agp_i915_chipset_flush_free_page(device_t dev)
2260 {
2261 	struct agp_i810_softc *sc;
2262 	device_t vga;
2263 
2264 	sc = device_get_softc(dev);
2265 	vga = device_get_parent(dev);
2266 	if (sc->sc_flush_page_res == NULL)
2267 		return;
2268 	BUS_DEACTIVATE_RESOURCE(device_get_parent(vga), dev, SYS_RES_MEMORY,
2269 	    sc->sc_flush_page_rid, sc->sc_flush_page_res);
2270 	BUS_RELEASE_RESOURCE(device_get_parent(vga), dev, SYS_RES_MEMORY,
2271 	    sc->sc_flush_page_rid, sc->sc_flush_page_res);
2272 }
2273 
2274 static int
2275 agp_i915_chipset_flush_setup(device_t dev)
2276 {
2277 	struct agp_i810_softc *sc;
2278 	uint32_t temp;
2279 	int error;
2280 
2281 	sc = device_get_softc(dev);
2282 	temp = pci_read_config(sc->bdev, AGP_I915_IFPADDR, 4);
2283 	if ((temp & 1) != 0) {
2284 		temp &= ~1;
2285 		if (bootverbose)
2286 			device_printf(dev,
2287 			    "Found already configured flush page at 0x%jx\n",
2288 			    (uintmax_t)temp);
2289 		sc->sc_bios_allocated_flush_page = 1;
2290 		/*
2291 		 * In the case BIOS initialized the flush pointer (?)
2292 		 * register, expect that BIOS also set up the resource
2293 		 * for the page.
2294 		 */
2295 		error = agp_i915_chipset_flush_alloc_page(dev, temp,
2296 		    temp + PAGE_SIZE - 1);
2297 		if (error != 0)
2298 			return (error);
2299 	} else {
2300 		sc->sc_bios_allocated_flush_page = 0;
2301 		error = agp_i915_chipset_flush_alloc_page(dev, 0, 0xffffffff);
2302 		if (error != 0)
2303 			return (error);
2304 		temp = rman_get_start(sc->sc_flush_page_res);
2305 		pci_write_config(sc->bdev, AGP_I915_IFPADDR, temp | 1, 4);
2306 	}
2307 	return (0);
2308 }
2309 
2310 static void
2311 agp_i915_chipset_flush_teardown(device_t dev)
2312 {
2313 	struct agp_i810_softc *sc;
2314 	uint32_t temp;
2315 
2316 	sc = device_get_softc(dev);
2317 	if (sc->sc_flush_page_res == NULL)
2318 		return;
2319 	if (!sc->sc_bios_allocated_flush_page) {
2320 		temp = pci_read_config(sc->bdev, AGP_I915_IFPADDR, 4);
2321 		temp &= ~1;
2322 		pci_write_config(sc->bdev, AGP_I915_IFPADDR, temp, 4);
2323 	}
2324 	agp_i915_chipset_flush_free_page(dev);
2325 }
2326 
2327 static int
2328 agp_i965_chipset_flush_setup(device_t dev)
2329 {
2330 	struct agp_i810_softc *sc;
2331 	uint64_t temp;
2332 	uint32_t temp_hi, temp_lo;
2333 	int error;
2334 
2335 	sc = device_get_softc(dev);
2336 
2337 	temp_hi = pci_read_config(sc->bdev, AGP_I965_IFPADDR + 4, 4);
2338 	temp_lo = pci_read_config(sc->bdev, AGP_I965_IFPADDR, 4);
2339 
2340 	if ((temp_lo & 1) != 0) {
2341 		temp = ((uint64_t)temp_hi << 32) | (temp_lo & ~1);
2342 		if (bootverbose)
2343 			device_printf(dev,
2344 			    "Found already configured flush page at 0x%jx\n",
2345 			    (uintmax_t)temp);
2346 		sc->sc_bios_allocated_flush_page = 1;
2347 		/*
2348 		 * In the case BIOS initialized the flush pointer (?)
2349 		 * register, expect that BIOS also set up the resource
2350 		 * for the page.
2351 		 */
2352 		error = agp_i915_chipset_flush_alloc_page(dev, temp,
2353 		    temp + PAGE_SIZE - 1);
2354 		if (error != 0)
2355 			return (error);
2356 	} else {
2357 		sc->sc_bios_allocated_flush_page = 0;
2358 		error = agp_i915_chipset_flush_alloc_page(dev, 0, ~0);
2359 		if (error != 0)
2360 			return (error);
2361 		temp = rman_get_start(sc->sc_flush_page_res);
2362 		pci_write_config(sc->bdev, AGP_I965_IFPADDR + 4,
2363 		    (temp >> 32) & UINT32_MAX, 4);
2364 		pci_write_config(sc->bdev, AGP_I965_IFPADDR,
2365 		    (temp & UINT32_MAX) | 1, 4);
2366 	}
2367 	return (0);
2368 }
2369 
2370 static void
2371 agp_i965_chipset_flush_teardown(device_t dev)
2372 {
2373 	struct agp_i810_softc *sc;
2374 	uint32_t temp_lo;
2375 
2376 	sc = device_get_softc(dev);
2377 	if (sc->sc_flush_page_res == NULL)
2378 		return;
2379 	if (!sc->sc_bios_allocated_flush_page) {
2380 		temp_lo = pci_read_config(sc->bdev, AGP_I965_IFPADDR, 4);
2381 		temp_lo &= ~1;
2382 		pci_write_config(sc->bdev, AGP_I965_IFPADDR, temp_lo, 4);
2383 	}
2384 	agp_i915_chipset_flush_free_page(dev);
2385 }
2386 
2387 static void
2388 agp_i915_chipset_flush(device_t dev)
2389 {
2390 	struct agp_i810_softc *sc;
2391 
2392 	sc = device_get_softc(dev);
2393 	*(uint32_t *)sc->sc_flush_page_vaddr = 1;
2394 }
2395 
2396 int
2397 agp_intel_gtt_chipset_flush(device_t dev)
2398 {
2399 	struct agp_i810_softc *sc;
2400 
2401 	sc = device_get_softc(dev);
2402 	sc->match->driver->chipset_flush(dev);
2403 	return (0);
2404 }
2405 
2406 void
2407 agp_intel_gtt_unmap_memory(device_t dev, struct sglist *sg_list)
2408 {
2409 }
2410 
2411 int
2412 agp_intel_gtt_map_memory(device_t dev, vm_page_t *pages, u_int num_entries,
2413     struct sglist **sg_list)
2414 {
2415 	struct agp_i810_softc *sc;
2416 	struct sglist *sg;
2417 	int i;
2418 #if 0
2419 	int error;
2420 	bus_dma_tag_t dmat;
2421 #endif
2422 
2423 	if (*sg_list != NULL)
2424 		return (0);
2425 	sc = device_get_softc(dev);
2426 	sg = sglist_alloc(num_entries, M_WAITOK /* XXXKIB */);
2427 	for (i = 0; i < num_entries; i++) {
2428 		sg->sg_segs[i].ss_paddr = VM_PAGE_TO_PHYS(pages[i]);
2429 		sg->sg_segs[i].ss_len = PAGE_SIZE;
2430 	}
2431 
2432 #if 0
2433 	error = bus_dma_tag_create(bus_get_dma_tag(dev),
2434 	    1 /* alignment */, 0 /* boundary */,
2435 	    1ULL << sc->match->busdma_addr_mask_sz /* lowaddr */,
2436 	    BUS_SPACE_MAXADDR /* highaddr */,
2437             NULL /* filtfunc */, NULL /* filtfuncarg */,
2438 	    BUS_SPACE_MAXADDR /* maxsize */,
2439 	    BUS_SPACE_UNRESTRICTED /* nsegments */,
2440 	    BUS_SPACE_MAXADDR /* maxsegsz */,
2441 	    0 /* flags */, NULL /* lockfunc */, NULL /* lockfuncarg */,
2442 	    &dmat);
2443 	if (error != 0) {
2444 		sglist_free(sg);
2445 		return (error);
2446 	}
2447 	/* XXXKIB */
2448 #endif
2449 	*sg_list = sg;
2450 	return (0);
2451 }
2452 
2453 void
2454 agp_intel_gtt_insert_sg_entries(device_t dev, struct sglist *sg_list,
2455     u_int first_entry, u_int flags)
2456 {
2457 	struct agp_i810_softc *sc;
2458 	vm_paddr_t spaddr;
2459 	size_t slen;
2460 	u_int i, j;
2461 
2462 	sc = device_get_softc(dev);
2463 	for (i = j = 0; j < sg_list->sg_nseg; j++) {
2464 		spaddr = sg_list->sg_segs[i].ss_paddr;
2465 		slen = sg_list->sg_segs[i].ss_len;
2466 		for (; slen > 0; i++) {
2467 			sc->match->driver->install_gtt_pte(dev, first_entry + i,
2468 			    spaddr, flags);
2469 			spaddr += AGP_PAGE_SIZE;
2470 			slen -= AGP_PAGE_SIZE;
2471 		}
2472 	}
2473 	sc->match->driver->read_gtt_pte(dev, first_entry + i - 1);
2474 }
2475 
2476 void
2477 intel_gtt_clear_range(u_int first_entry, u_int num_entries)
2478 {
2479 
2480 	agp_intel_gtt_clear_range(intel_agp, first_entry, num_entries);
2481 }
2482 
2483 void
2484 intel_gtt_insert_pages(u_int first_entry, u_int num_entries, vm_page_t *pages,
2485     u_int flags)
2486 {
2487 
2488 	agp_intel_gtt_insert_pages(intel_agp, first_entry, num_entries,
2489 	    pages, flags);
2490 }
2491 
2492 struct intel_gtt
2493 intel_gtt_get(void)
2494 {
2495 
2496 	return (agp_intel_gtt_get(intel_agp));
2497 }
2498 
2499 int
2500 intel_gtt_chipset_flush(void)
2501 {
2502 
2503 	return (agp_intel_gtt_chipset_flush(intel_agp));
2504 }
2505 
2506 void
2507 intel_gtt_unmap_memory(struct sglist *sg_list)
2508 {
2509 
2510 	agp_intel_gtt_unmap_memory(intel_agp, sg_list);
2511 }
2512 
2513 int
2514 intel_gtt_map_memory(vm_page_t *pages, u_int num_entries,
2515     struct sglist **sg_list)
2516 {
2517 
2518 	return (agp_intel_gtt_map_memory(intel_agp, pages, num_entries,
2519 	    sg_list));
2520 }
2521 
2522 void
2523 intel_gtt_insert_sg_entries(struct sglist *sg_list, u_int first_entry,
2524     u_int flags)
2525 {
2526 
2527 	agp_intel_gtt_insert_sg_entries(intel_agp, sg_list, first_entry, flags);
2528 }
2529 
2530 device_t
2531 intel_gtt_get_bridge_device(void)
2532 {
2533 	struct agp_i810_softc *sc;
2534 
2535 	sc = device_get_softc(intel_agp);
2536 	return (sc->bdev);
2537 }
2538 
2539 vm_paddr_t
2540 intel_gtt_read_pte_paddr(u_int entry)
2541 {
2542 	struct agp_i810_softc *sc;
2543 
2544 	sc = device_get_softc(intel_agp);
2545 	return (sc->match->driver->read_gtt_pte_paddr(intel_agp, entry));
2546 }
2547 
2548 u_int32_t
2549 intel_gtt_read_pte(u_int entry)
2550 {
2551 	struct agp_i810_softc *sc;
2552 
2553 	sc = device_get_softc(intel_agp);
2554 	return (sc->match->driver->read_gtt_pte(intel_agp, entry));
2555 }
2556 
2557 void
2558 intel_gtt_write(u_int entry, uint32_t val)
2559 {
2560 	struct agp_i810_softc *sc;
2561 
2562 	sc = device_get_softc(intel_agp);
2563 	return (sc->match->driver->write_gtt(intel_agp, entry, val));
2564 }
2565