aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/char/agp/intel-agp.c108
1 files changed, 78 insertions, 30 deletions
diff --git a/drivers/char/agp/intel-agp.c b/drivers/char/agp/intel-agp.c
index 4d062fc3e825..ce75fa3a4723 100644
--- a/drivers/char/agp/intel-agp.c
+++ b/drivers/char/agp/intel-agp.c
@@ -117,7 +117,11 @@ static struct _intel_private {
117 * popup and for the GTT. 117 * popup and for the GTT.
118 */ 118 */
119 int gtt_entries; /* i830+ */ 119 int gtt_entries; /* i830+ */
120 void __iomem *flush_page; 120 union {
121 void __iomem *i9xx_flush_page;
122 void *i8xx_flush_page;
123 };
124 struct page *i8xx_page;
121 struct resource ifp_resource; 125 struct resource ifp_resource;
122} intel_private; 126} intel_private;
123 127
@@ -579,6 +583,44 @@ static void intel_i830_init_gtt_entries(void)
579 intel_private.gtt_entries = gtt_entries; 583 intel_private.gtt_entries = gtt_entries;
580} 584}
581 585
586static void intel_i830_fini_flush(void)
587{
588 kunmap(intel_private.i8xx_page);
589 intel_private.i8xx_flush_page = NULL;
590 unmap_page_from_agp(intel_private.i8xx_page);
591 flush_agp_mappings();
592
593 __free_page(intel_private.i8xx_page);
594}
595
596static void intel_i830_setup_flush(void)
597{
598
599 intel_private.i8xx_page = alloc_page(GFP_KERNEL | __GFP_ZERO | GFP_DMA32);
600 if (!intel_private.i8xx_page) {
601 return;
602 }
603
604 /* make page uncached */
605 map_page_into_agp(intel_private.i8xx_page);
606 flush_agp_mappings();
607
608 intel_private.i8xx_flush_page = kmap(intel_private.i8xx_page);
609 if (!intel_private.i8xx_flush_page)
610 intel_i830_fini_flush();
611}
612
613static void intel_i830_chipset_flush(struct agp_bridge_data *bridge)
614{
615 unsigned int *pg = intel_private.i8xx_flush_page;
616 int i;
617
618 for (i = 0; i < 256; i+=2)
619 *(pg + i) = i;
620
621 wmb();
622}
623
582/* The intel i830 automatically initializes the agp aperture during POST. 624/* The intel i830 automatically initializes the agp aperture during POST.
583 * Use the memory already set aside for in the GTT. 625 * Use the memory already set aside for in the GTT.
584 */ 626 */
@@ -679,6 +721,8 @@ static int intel_i830_configure(void)
679 } 721 }
680 722
681 global_cache_flush(); 723 global_cache_flush();
724
725 intel_i830_setup_flush();
682 return 0; 726 return 0;
683} 727}
684 728
@@ -778,11 +822,8 @@ static int intel_alloc_chipset_flush_resource(void)
778 ret = pci_bus_alloc_resource(agp_bridge->dev->bus, &intel_private.ifp_resource, PAGE_SIZE, 822 ret = pci_bus_alloc_resource(agp_bridge->dev->bus, &intel_private.ifp_resource, PAGE_SIZE,
779 PAGE_SIZE, PCIBIOS_MIN_MEM, 0, 823 PAGE_SIZE, PCIBIOS_MIN_MEM, 0,
780 pcibios_align_resource, agp_bridge->dev); 824 pcibios_align_resource, agp_bridge->dev);
781 if (ret != 0)
782 return ret;
783 825
784 printk("intel priv bus start %08lx\n", intel_private.ifp_resource.start); 826 return ret;
785 return 0;
786} 827}
787 828
788static void intel_i915_setup_chipset_flush(void) 829static void intel_i915_setup_chipset_flush(void)
@@ -822,7 +863,6 @@ static void intel_i965_g33_setup_chipset_flush(void)
822 863
823 pci_write_config_dword(agp_bridge->dev, I965_IFPADDR + 4, (intel_private.ifp_resource.start >> 32)); 864 pci_write_config_dword(agp_bridge->dev, I965_IFPADDR + 4, (intel_private.ifp_resource.start >> 32));
824 pci_write_config_dword(agp_bridge->dev, I965_IFPADDR, (intel_private.ifp_resource.start & 0xffffffff) | 0x1); 865 pci_write_config_dword(agp_bridge->dev, I965_IFPADDR, (intel_private.ifp_resource.start & 0xffffffff) | 0x1);
825 intel_private.flush_page = ioremap_nocache(intel_private.ifp_resource.start, PAGE_SIZE);
826 } else { 866 } else {
827 u64 l64; 867 u64 l64;
828 868
@@ -833,12 +873,33 @@ static void intel_i965_g33_setup_chipset_flush(void)
833 intel_private.ifp_resource.end = l64 + PAGE_SIZE; 873 intel_private.ifp_resource.end = l64 + PAGE_SIZE;
834 ret = request_resource(&iomem_resource, &intel_private.ifp_resource); 874 ret = request_resource(&iomem_resource, &intel_private.ifp_resource);
835 if (!ret) { 875 if (!ret) {
836 intel_private.ifp_resource.start = 0; 876 printk("Failed inserting resource into tree - continuing\n");
837 printk("Failed inserting resource into tree\n");
838 } 877 }
839 } 878 }
840} 879}
841 880
881static void intel_i9xx_setup_flush(void)
882{
883 /* setup a resource for this object */
884 memset(&intel_private.ifp_resource, 0, sizeof(intel_private.ifp_resource));
885
886 intel_private.ifp_resource.name = "Intel Flush Page";
887 intel_private.ifp_resource.flags = IORESOURCE_MEM;
888
889 /* Setup chipset flush for 915 */
890 if (IS_I965 || IS_G33) {
891 intel_i965_g33_setup_chipset_flush();
892 } else {
893 intel_i915_setup_chipset_flush();
894 }
895
896 if (intel_private.ifp_resource.start) {
897 intel_private.i9xx_flush_page = ioremap_nocache(intel_private.ifp_resource.start, PAGE_SIZE);
898 if (!intel_private.i9xx_flush_page)
899 printk("unable to ioremap flush page - no chipset flushing");
900 }
901}
902
842static int intel_i915_configure(void) 903static int intel_i915_configure(void)
843{ 904{
844 struct aper_size_info_fixed *current_size; 905 struct aper_size_info_fixed *current_size;
@@ -868,40 +929,23 @@ static int intel_i915_configure(void)
868 929
869 global_cache_flush(); 930 global_cache_flush();
870 931
871 /* setup a resource for this object */ 932 intel_i9xx_setup_flush();
872 memset(&intel_private.ifp_resource, 0, sizeof(intel_private.ifp_resource));
873
874 intel_private.ifp_resource.name = "Intel Flush Page";
875 intel_private.ifp_resource.flags = IORESOURCE_MEM;
876
877 /* Setup chipset flush for 915 */
878 if (IS_I965 || IS_G33) {
879 intel_i965_g33_setup_chipset_flush();
880 } else {
881 intel_i915_setup_chipset_flush();
882 }
883
884 if (intel_private.ifp_resource.start) {
885 intel_private.flush_page = ioremap_nocache(intel_private.ifp_resource.start, PAGE_SIZE);
886 if (!intel_private.flush_page)
887 printk("unable to ioremap flush page - no chipset flushing");
888 }
889 933
890 return 0; 934 return 0;
891} 935}
892 936
893static void intel_i915_cleanup(void) 937static void intel_i915_cleanup(void)
894{ 938{
895 if (intel_private.flush_page) 939 if (intel_private.i9xx_flush_page)
896 iounmap(intel_private.flush_page); 940 iounmap(intel_private.i9xx_flush_page);
897 iounmap(intel_private.gtt); 941 iounmap(intel_private.gtt);
898 iounmap(intel_private.registers); 942 iounmap(intel_private.registers);
899} 943}
900 944
901static void intel_i915_chipset_flush(struct agp_bridge_data *bridge) 945static void intel_i915_chipset_flush(struct agp_bridge_data *bridge)
902{ 946{
903 if (intel_private.flush_page) 947 if (intel_private.i9xx_flush_page)
904 writel(1, intel_private.flush_page); 948 writel(1, intel_private.i9xx_flush_page);
905} 949}
906 950
907static int intel_i915_insert_entries(struct agp_memory *mem,off_t pg_start, 951static int intel_i915_insert_entries(struct agp_memory *mem,off_t pg_start,
@@ -1395,6 +1439,8 @@ static int intel_845_configure(void)
1395 pci_write_config_byte(agp_bridge->dev, INTEL_I845_AGPM, temp2 | (1 << 1)); 1439 pci_write_config_byte(agp_bridge->dev, INTEL_I845_AGPM, temp2 | (1 << 1));
1396 /* clear any possible error conditions */ 1440 /* clear any possible error conditions */
1397 pci_write_config_word(agp_bridge->dev, INTEL_I845_ERRSTS, 0x001c); 1441 pci_write_config_word(agp_bridge->dev, INTEL_I845_ERRSTS, 0x001c);
1442
1443 intel_i830_setup_flush();
1398 return 0; 1444 return 0;
1399} 1445}
1400 1446
@@ -1651,6 +1697,7 @@ static const struct agp_bridge_driver intel_830_driver = {
1651 .agp_alloc_page = agp_generic_alloc_page, 1697 .agp_alloc_page = agp_generic_alloc_page,
1652 .agp_destroy_page = agp_generic_destroy_page, 1698 .agp_destroy_page = agp_generic_destroy_page,
1653 .agp_type_to_mask_type = intel_i830_type_to_mask_type, 1699 .agp_type_to_mask_type = intel_i830_type_to_mask_type,
1700 .chipset_flush = intel_i830_chipset_flush,
1654}; 1701};
1655 1702
1656static const struct agp_bridge_driver intel_820_driver = { 1703static const struct agp_bridge_driver intel_820_driver = {
@@ -1747,6 +1794,7 @@ static const struct agp_bridge_driver intel_845_driver = {
1747 .agp_alloc_page = agp_generic_alloc_page, 1794 .agp_alloc_page = agp_generic_alloc_page,
1748 .agp_destroy_page = agp_generic_destroy_page, 1795 .agp_destroy_page = agp_generic_destroy_page,
1749 .agp_type_to_mask_type = agp_generic_type_to_mask_type, 1796 .agp_type_to_mask_type = agp_generic_type_to_mask_type,
1797 .chipset_flush = intel_i830_chipset_flush,
1750}; 1798};
1751 1799
1752static const struct agp_bridge_driver intel_850_driver = { 1800static const struct agp_bridge_driver intel_850_driver = {