The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/dev/agp/agp_i810.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

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

Cache object: c7b229cd81e61843f3cb33eb0fc829ba


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.