# ATI Radeon driver finally working with SIS chipsets !!

## sim0nx

Oliver Heilmann made a patch for the 2.6 series kernel, which fixes some problems in the sis-agp driver.

afer applying that patch, the ati-drivers work perfectly  :Smile: !

check this site for the original post:

http://www.rage3d.com/board/showthread.php?s=&threadid=33734122&perpage=30&pagenumber=2

here the patch:

<patch>

diff -uprN --new-file linuxpp/drivers/char/agp/Makefile linux-2.6.1-mm1/drivers/char/agp/Makefile

--- linuxpp/drivers/char/agp/Makefile	2004-01-16 08:19:17.000000000 +0100

+++ linux-2.6.1-mm1/drivers/char/agp/Makefile	2004-01-16 09:31:29.000000000 +0100

@@ -1,4 +1,4 @@

-agpgart-y := backend.o frontend.o generic.o isoch.o

+agpgart-y := backend.o frontend.o generic.o generic-agp3.o isoch.o

 obj-$(CONFIG_AGP)		+= agpgart.o

 obj-$(CONFIG_AGP_ALI)		+= ali-agp.o

diff -uprN --new-file linuxpp/drivers/char/agp/Makefile.orig linux-2.6.1-mm1/drivers/char/agp/Makefile.orig

--- linuxpp/drivers/char/agp/Makefile.orig	1970-01-01 01:00:00.000000000 +0100

+++ linux-2.6.1-mm1/drivers/char/agp/Makefile.orig	2004-01-16 09:28:11.000000000 +0100

@@ -0,0 +1,17 @@

+agpgart-y := backend.o frontend.o generic.o isoch.o

+

+obj-$(CONFIG_AGP)		+= agpgart.o

+obj-$(CONFIG_AGP_ALI)		+= ali-agp.o

+obj-$(CONFIG_AGP_ATI)		+= ati-agp.o

+obj-$(CONFIG_AGP_AMD)		+= amd-k7-agp.o

+obj-$(CONFIG_AGP_AMD64)		+= amd64-agp.o

+obj-$(CONFIG_AGP_ALPHA_CORE)	+= alpha-agp.o

+obj-$(CONFIG_AGP_HP_ZX1)	+= hp-agp.o

+obj-$(CONFIG_AGP_I460)		+= i460-agp.o

+obj-$(CONFIG_AGP_INTEL)		+= intel-agp.o

+obj-$(CONFIG_AGP_NVIDIA)	+= nvidia-agp.o

+obj-$(CONFIG_AGP_SIS)		+= sis-agp.o

+obj-$(CONFIG_AGP_SWORKS)	+= sworks-agp.o

+obj-$(CONFIG_AGP_UNINORTH)	+= uninorth-agp.o

+obj-$(CONFIG_AGP_VIA)		+= via-agp.o

+

diff -uprN --new-file linuxpp/drivers/char/agp/agp.h linux-2.6.1-mm1/drivers/char/agp/agp.h

--- linuxpp/drivers/char/agp/agp.h	2004-01-16 08:19:17.000000000 +0100

+++ linux-2.6.1-mm1/drivers/char/agp/agp.h	2004-01-16 16:23:38.000000000 +0100

@@ -402,6 +402,17 @@ void global_cache_flush(void);

 void get_agp_version(struct agp_bridge_data *bridge);

 unsigned long agp_generic_mask_memory(unsigned long addr, int type);

+/* generic routines for agp>=3 */

+int agp3_generic_fetch_size(void);

+void agp3_generic_tlbflush(struct agp_memory *mem);

+int agp3_generic_configure(void);

+void agp3_generic_cleanup(void);

+

+/* aperture sizes have been standardised since v3 */

+#define AGP_GENERIC_SIZES_ENTRIES 11

+extern struct aper_size_info_16 agp3_generic_sizes[];

+

+

 extern int agp_off;

 extern int agp_try_unsupported_boot;

@@ -410,7 +421,10 @@ extern int agp_try_unsupported_boot;

 #define AGPCMD			0x8

 #define AGPNISTAT		0xc

 #define AGPCTRL                 0x10

+#define AGPAPSIZE               0x14

 #define AGPNEPG			0x16

+#define AGPGARTLO               0x18

+#define AGPGARTHI               0x1c

 #define AGPNICMD		0x20

 #define AGP_MAJOR_VERSION_SHIFT	(20)

@@ -431,6 +445,11 @@ extern int agp_try_unsupported_boot;

 #define AGPSTAT2_2X		(1<<1)

 #define AGPSTAT2_4X		(1<<2)

+#define AGPCTRL_APERENB         (1<< :Cool: 

+#define AGPCTRL_GTLBEN          (1<<7)

+

+

+

 #define AGPSTAT3_RSVD		(1<<2)

 #define AGPSTAT3_8X		(1<<1)

 #define AGPSTAT3_4X		(1)

diff -uprN --new-file linuxpp/drivers/char/agp/agp.h.orig linux-2.6.1-mm1/drivers/char/agp/agp.h.orig

--- linuxpp/drivers/char/agp/agp.h.orig	1970-01-01 01:00:00.000000000 +0100

+++ linux-2.6.1-mm1/drivers/char/agp/agp.h.orig	2004-01-16 09:28:11.000000000 +0100

@@ -0,0 +1,438 @@

+/*

+ * AGPGART

+ * Copyright (C) 2002-2003 Dave Jones

+ * Copyright (C) 1999 Jeff Hartmann

+ * Copyright (C) 1999 Precision Insight, Inc.

+ * Copyright (C) 1999 Xi Graphics, Inc.

+ *

+ * Permission is hereby granted, free of charge, to any person obtaining a

+ * copy of this software and associated documentation files (the "Software"),

+ * to deal in the Software without restriction, including without limitation

+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,

+ * and/or sell copies of the Software, and to permit persons to whom the

+ * Software is furnished to do so, subject to the following conditions:

+ *

+ * The above copyright notice and this permission notice shall be included

+ * in all copies or substantial portions of the Software.

+ *

+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS

+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,

+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL

+ * JEFF HARTMANN, OR ANY OTHER CONTRIBUTORS BE LIABLE FOR ANY CLAIM, 

+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 

+ * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE 

+ * OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

+ *

+ */

+

+#ifndef _AGP_BACKEND_PRIV_H

+#define _AGP_BACKEND_PRIV_H 1

+

+#include <asm/agp.h>	/* for flush_agp_cache() */

+

+#define PFX "agpgart: "

+

+//#define AGP_DEBUG 1

+#ifdef AGP_DEBUG

+#define DBG(x,y...) printk (KERN_DEBUG PFX "%s: " x "\n", __FUNCTION__ , ## y)

+#else

+#define DBG(x,y...) do { } while (0)

+#endif

+

+extern struct agp_bridge_data *agp_bridge;

+

+enum aper_size_type {

+	U8_APER_SIZE,

+	U16_APER_SIZE,

+	U32_APER_SIZE,

+	LVL2_APER_SIZE,

+	FIXED_APER_SIZE

+};

+

+struct gatt_mask {

+	unsigned long mask;

+	u32 type;

+	/* totally device specific, for integrated chipsets that 

+	 * might have different types of memory masks.  For other

+	 * devices this will probably be ignored */

+};

+

+struct aper_size_info_8 {

+	int size;

+	int num_entries;

+	int page_order;

+	u8 size_value;

+};

+

+struct aper_size_info_16 {

+	int size;

+	int num_entries;

+	int page_order;

+	u16 size_value;

+};

+

+struct aper_size_info_32 {

+	int size;

+	int num_entries;

+	int page_order;

+	u32 size_value;

+};

+

+struct aper_size_info_lvl2 {

+	int size;

+	int num_entries;

+	u32 size_value;

+};

+

+struct aper_size_info_fixed {

+	int size;

+	int num_entries;

+	int page_order;

+};

+

+struct agp_bridge_driver {

+	struct module *owner;

+	void *aperture_sizes;

+	int num_aperture_sizes;

+	enum aper_size_type size_type;

+	int cant_use_aperture;

+	int needs_scratch_page;

+	struct gatt_mask *masks;

+	int (*fetch_size)(void);

+	int (*configure)(void);

+	void (*agp_enable)(u32);

+	void (*cleanup)(void);

+	void (*tlb_flush)(struct agp_memory *);

+	unsigned long (*mask_memory)(unsigned long, int);

+	void (*cache_flush)(void);

+	int (*create_gatt_table)(void);

+	int (*free_gatt_table)(void);

+	int (*insert_memory)(struct agp_memory *, off_t, int);

+	int (*remove_memory)(struct agp_memory *, off_t, int);

+	struct agp_memory *(*alloc_by_type) (size_t, int);

+	void (*free_by_type)(struct agp_memory *);

+	void *(*agp_alloc_page)(void);

+	void (*agp_destroy_page)(void *);

+};

+

+struct agp_bridge_data {

+	struct agp_version *version;

+	struct agp_bridge_driver *driver;

+	struct vm_operations_struct *vm_ops;

+	void *previous_size;

+	void *current_size;

+	void *dev_private_data;

+	struct pci_dev *dev;

+	u32 *gatt_table;

+	u32 *gatt_table_real;

+	unsigned long scratch_page;

+	unsigned long scratch_page_real;

+	unsigned long gart_bus_addr;

+	unsigned long gatt_bus_addr;

+	u32 mode;

+	enum chipset_type type;

+	unsigned long *key_list;

+	atomic_t current_memory_agp;

+	atomic_t agp_in_use;

+	int max_memory_agp;	/* in number of pages */

+	int aperture_size_idx;

+	int capndx;

+	char major_version;

+	char minor_version;

+};

+

+#define OUTREG64(mmap, addr, val)	__raw_writeq((val), (mmap)+(addr))

+#define OUTREG32(mmap, addr, val)	__raw_writel((val), (mmap)+(addr))

+#define OUTREG16(mmap, addr, val)	__raw_writew((val), (mmap)+(addr))

+#define OUTREG8(mmap, addr, val)	__raw_writeb((val), (mmap)+(addr))

+

+#define INREG64(mmap, addr)		__raw_readq((mmap)+(addr))

+#define INREG32(mmap, addr)		__raw_readl((mmap)+(addr))

+#define INREG16(mmap, addr)		__raw_readw((mmap)+(addr))

+#define INREG8(mmap, addr)		__raw_readb((mmap)+(addr))

+

+#define KB(x)	((x) * 1024)

+#define MB(x)	(KB (KB (x)))

+#define GB(x)	(MB (KB (x)))

+

+#define A_SIZE_8(x)	((struct aper_size_info_8 *) x)

+#define A_SIZE_16(x)	((struct aper_size_info_16 *) x)

+#define A_SIZE_32(x)	((struct aper_size_info_32 *) x)

+#define A_SIZE_LVL2(x)	((struct aper_size_info_lvl2 *) x)

+#define A_SIZE_FIX(x)	((struct aper_size_info_fixed *) x)

+#define A_IDX8(bridge)	(A_SIZE_8((bridge)->driver->aperture_sizes) + i)

+#define A_IDX16(bridge)	(A_SIZE_16((bridge)->driver->aperture_sizes) + i)

+#define A_IDX32(bridge)	(A_SIZE_32((bridge)->driver->aperture_sizes) + i)

+#define MAXKEY		(4096 * 32)

+

+#define PGE_EMPTY(b, p)	(!(p) || (p) == (unsigned long) (b)->scratch_page)

+

+/* Chipset independant registers (from AGP Spec) */

+#define AGP_APBASE	0x10

+

+/* Intel registers */

+#define INTEL_APSIZE	0xb4

+#define INTEL_ATTBASE	0xb8

+#define INTEL_AGPCTRL	0xb0

+#define INTEL_NBXCFG	0x50

+#define INTEL_ERRSTS	0x91

+

+/* Intel 460GX Registers */

+#define INTEL_I460_BAPBASE		0x98

+#define INTEL_I460_GXBCTL		0xa0

+#define INTEL_I460_AGPSIZ		0xa2

+#define INTEL_I460_ATTBASE		0xfe200000

+#define INTEL_I460_GATT_VALID		(1UL << 24)

+#define INTEL_I460_GATT_COHERENT	(1UL << 25)

+

+/* Intel i830 registers */

+#define I830_GMCH_CTRL			0x52

+#define I830_GMCH_ENABLED		0x4

+#define I830_GMCH_MEM_MASK		0x1

+#define I830_GMCH_MEM_64M		0x1

+#define I830_GMCH_MEM_128M		0

+#define I830_GMCH_GMS_MASK		0x70

+#define I830_GMCH_GMS_DISABLED		0x00

+#define I830_GMCH_GMS_LOCAL		0x10

+#define I830_GMCH_GMS_STOLEN_512	0x20

+#define I830_GMCH_GMS_STOLEN_1024	0x30

+#define I830_GMCH_GMS_STOLEN_8192	0x40

+#define I830_RDRAM_CHANNEL_TYPE		0x03010

+#define I830_RDRAM_ND(x)		(((x) & 0x20) >> 5)

+#define I830_RDRAM_DDT(x)		(((x) & 0x18) >> 3)

+

+/* This one is for I830MP w. an external graphic card */

+#define INTEL_I830_ERRSTS	0x92

+

+/* Intel 855GM/852GM registers */

+#define I855_GMCH_GMS_STOLEN_0M		0x0

+#define I855_GMCH_GMS_STOLEN_1M		(0x1 << 4)

+#define I855_GMCH_GMS_STOLEN_4M		(0x2 << 4)

+#define I855_GMCH_GMS_STOLEN_8M		(0x3 << 4)

+#define I855_GMCH_GMS_STOLEN_16M	(0x4 << 4)

+#define I855_GMCH_GMS_STOLEN_32M	(0x5 << 4)

+#define I85X_CAPID			0x44

+#define I85X_VARIANT_MASK		0x7

+#define I85X_VARIANT_SHIFT		5

+#define I855_GME			0x0

+#define I855_GM				0x4

+#define I852_GME			0x2

+#define I852_GM				0x5

+

+/* Intel 815 register */

+#define INTEL_815_APCONT	0x51

+#define INTEL_815_ATTBASE_MASK	~0x1FFFFFFF

+

+/* Intel i820 registers */

+#define INTEL_I820_RDCR		0x51

+#define INTEL_I820_ERRSTS	0xc8

+

+/* Intel i840 registers */

+#define INTEL_I840_MCHCFG	0x50

+#define INTEL_I840_ERRSTS	0xc8

+ 

+/* Intel i845 registers */

+#define INTEL_I845_AGPM		0x51

+#define INTEL_I845_ERRSTS	0xc8

+

+/* Intel i850 registers */

+#define INTEL_I850_MCHCFG	0x50

+#define INTEL_I850_ERRSTS	0xc8

+

+/* Intel i860 registers */

+#define INTEL_I860_MCHCFG	0x50

+#define INTEL_I860_ERRSTS	0xc8

+

+/* Intel i810 registers */

+#define I810_GMADDR		0x10

+#define I810_MMADDR		0x14

+#define I810_PTE_BASE		0x10000

+#define I810_PTE_MAIN_UNCACHED	0x00000000

+#define I810_PTE_LOCAL		0x00000002

+#define I810_PTE_VALID		0x00000001

+#define I810_SMRAM_MISCC	0x70

+#define I810_GFX_MEM_WIN_SIZE	0x00010000

+#define I810_GFX_MEM_WIN_32M	0x00010000

+#define I810_GMS		0x000000c0

+#define I810_GMS_DISABLE	0x00000000

+#define I810_PGETBL_CTL		0x2020

+#define I810_PGETBL_ENABLED	0x00000001

+#define I810_DRAM_CTL		0x3000

+#define I810_DRAM_ROW_0		0x00000001

+#define I810_DRAM_ROW_0_SDRAM	0x00000001

+

+/* Intel 7505 registers */

+#define INTEL_I7505_APSIZE	0x74

+#define INTEL_I7505_NCAPID	0x60

+#define INTEL_I7505_NISTAT	0x6c

+#define INTEL_I7505_ATTBASE	0x78

+#define INTEL_I7505_ERRSTS	0x42

+#define INTEL_I7505_AGPCTRL	0x70

+#define INTEL_I7505_MCHCFG	0x50

+

+/* VIA register */

+#define VIA_GARTCTRL	0x80

+#define VIA_APSIZE	0x84

+#define VIA_ATTBASE	0x88

+

+/* VIA KT400 */

+#define VIA_AGP3_GARTCTRL	0x90

+#define VIA_AGP3_APSIZE		0x94

+#define VIA_AGP3_ATTBASE	0x98

+#define VIA_AGPSEL		0xfd

+

+/* SiS registers */

+#define SIS_ATTBASE	0x90

+#define SIS_APSIZE	0x94

+#define SIS_TLBCNTRL	0x97

+#define SIS_TLBFLUSH	0x98

+

+/* AMD registers */

+#define AMD_MMBASE	0x14

+#define AMD_APSIZE	0xac

+#define AMD_MODECNTL	0xb0

+#define AMD_MODECNTL2	0xb2

+#define AMD_GARTENABLE	0x02	/* In mmio region (16-bit register) */

+#define AMD_ATTBASE	0x04	/* In mmio region (32-bit register) */

+#define AMD_TLBFLUSH	0x0c	/* In mmio region (32-bit register) */

+#define AMD_CACHEENTRY	0x10	/* In mmio region (32-bit register) */

+

+/* AMD64 registers */

+#define AMD64_GARTAPERTURECTL	0x90

+#define AMD64_GARTAPERTUREBASE	0x94

+#define AMD64_GARTTABLEBASE	0x98

+#define AMD64_GARTCACHECTL		0x9c

+#define AMD64_GARTEN		(1<<0)

+

+/* ALi registers */

+#define ALI_AGPCTRL			0xb8

+#define ALI_ATTBASE			0xbc

+#define ALI_TLBCTRL			0xc0

+#define ALI_TAGCTRL			0xc4

+#define ALI_CACHE_FLUSH_CTRL		0xD0

+#define ALI_CACHE_FLUSH_ADDR_MASK	0xFFFFF000

+#define ALI_CACHE_FLUSH_EN		0x100

+

+/* ATI register */

+#define ATI_GART_MMBASE_ADDR	0x14

+#define ATI_RS100_APSIZE	0xac

+#define ATI_RS300_APSIZE	0xf8

+#define ATI_RS100_IG_AGPMODE	0xb0

+#define ATI_RS300_IG_AGPMODE	0xfc

+

+#define ATI_GART_FEATURE_ID		0x00

+#define ATI_GART_BASE			0x04

+#define ATI_GART_CACHE_SZBASE		0x08

+#define ATI_GART_CACHE_CNTRL		0x0c

+#define ATI_GART_CACHE_ENTRY_CNTRL	0x10

+

+/* Serverworks Registers */

+#define SVWRKS_APSIZE		0x10

+#define SVWRKS_SIZE_MASK	0xfe000000

+

+#define SVWRKS_MMBASE		0x14

+#define SVWRKS_CACHING		0x4b

+#define SVWRKS_FEATURE		0x68

+

+/* func 1 registers */

+#define SVWRKS_AGP_ENABLE	0x60

+#define SVWRKS_COMMAND		0x04

+

+/* Memory mapped registers */

+#define SVWRKS_GART_CACHE	0x02

+#define SVWRKS_GATTBASE		0x04

+#define SVWRKS_TLBFLUSH		0x10

+#define SVWRKS_POSTFLUSH	0x14

+#define SVWRKS_DIRFLUSH		0x0c

+

+/* HP ZX1 SBA registers */

+#define HP_ZX1_CTRL		0x200

+#define HP_ZX1_IBASE		0x300

+#define HP_ZX1_IMASK		0x308

+#define HP_ZX1_PCOM		0x310

+#define HP_ZX1_TCNFG		0x318

+#define HP_ZX1_PDIR_BASE	0x320

+#define HP_ZX1_CACHE_FLUSH	0x428

+

+/* NVIDIA registers */

+#define NVIDIA_0_APSIZE		0x80

+#define NVIDIA_1_WBC		0xf0

+#define NVIDIA_2_GARTCTRL	0xd0

+#define NVIDIA_2_APBASE		0xd8

+#define NVIDIA_2_APLIMIT	0xdc

+#define NVIDIA_2_ATTBASE(i)	(0xe0 + (i) * 4)

+#define NVIDIA_3_APBASE		0x50

+#define NVIDIA_3_APLIMIT	0x54

+

+

+struct agp_device_ids {

+	unsigned short device_id; /* first, to make table easier to read */

+	enum chipset_type chipset;

+	const char *chipset_name;

+	int (*chipset_setup) (struct pci_dev *pdev);	/* used to override generic */

+};

+

+/* Driver registration */

+struct agp_bridge_data *agp_alloc_bridge(void);

+void agp_put_bridge(struct agp_bridge_data *bridge);

+int agp_add_bridge(struct agp_bridge_data *bridge);

+void agp_remove_bridge(struct agp_bridge_data *bridge);

+

+/* Frontend routines. */

+int agp_frontend_initialize(void);

+void agp_frontend_cleanup(void);

+

+/* Generic routines. */

+void agp_generic_enable(u32 mode);

+int agp_generic_create_gatt_table(void);

+int agp_generic_free_gatt_table(void);

+struct agp_memory *agp_create_memory(int scratch_pages);

+int agp_generic_insert_memory(struct agp_memory *mem, off_t pg_start, int type);

+int agp_generic_remove_memory(struct agp_memory *mem, off_t pg_start, int type);

+struct agp_memory *agp_generic_alloc_by_type(size_t page_count, int type);

+void agp_generic_free_by_type(struct agp_memory *curr);

+void *agp_generic_alloc_page(void);

+void agp_generic_destroy_page(void *addr);

+void agp_free_key(int key);

+int agp_num_entries(void);

+u32 agp_collect_device_status(u32 mode, u32 command);

+void agp_device_command(u32 command, int agp_v3);

+int agp_3_5_enable(struct agp_bridge_data *bridge);

+void global_cache_flush(void);

+void get_agp_version(struct agp_bridge_data *bridge);

+unsigned long agp_generic_mask_memory(unsigned long addr, int type);

+

+extern int agp_off;

+extern int agp_try_unsupported_boot;

+

+/* Standard agp registers */

+#define AGPSTAT			0x4

+#define AGPCMD			0x8

+#define AGPNISTAT		0xc

+#define AGPCTRL                 0x10

+#define AGPNEPG			0x16

+#define AGPNICMD		0x20

+

+#define AGP_MAJOR_VERSION_SHIFT	(20)

+#define AGP_MINOR_VERSION_SHIFT	(16)

+

+#define AGPSTAT_RQ_DEPTH	(0xff000000)

+

+#define AGPSTAT_CAL_MASK	(1<<12|1<<11|1<<10)

+#define AGPSTAT_ARQSZ		(1<<15|1<<14|1<<13)

+#define AGPSTAT_ARQSZ_SHIFT	13

+

+#define AGPSTAT_SBA		(1<<9)

+#define AGPSTAT_AGP_ENABLE	(1<< :Cool: 

+#define AGPSTAT_FW		(1<<4)

+#define AGPSTAT_MODE_3_0	(1<<3)

+

+#define AGPSTAT2_1X		(1<<0)

+#define AGPSTAT2_2X		(1<<1)

+#define AGPSTAT2_4X		(1<<2)

+

+#define AGPSTAT3_RSVD		(1<<2)

+#define AGPSTAT3_8X		(1<<1)

+#define AGPSTAT3_4X		(1)

+

+#endif				/* _AGP_BACKEND_PRIV_H */

diff -uprN --new-file linuxpp/drivers/char/agp/generic-agp3.c linux-2.6.1-mm1/drivers/char/agp/generic-agp3.c

--- linuxpp/drivers/char/agp/generic-agp3.c	1970-01-01 01:00:00.000000000 +0100

+++ linux-2.6.1-mm1/drivers/char/agp/generic-agp3.c	2004-01-16 16:28:46.000000000 +0100

@@ -0,0 +1,109 @@

+/*

+* AGPGART driver.

+ * Copyright (C) 2002-2003 Dave Jones.

+ * Copyright (C) 1999 Jeff Hartmann.

+ * Copyright (C) 1999 Precision Insight, Inc.

+ * Copyright (C) 1999 Xi Graphics, Inc.

+ *

+ * Permission is hereby granted, free of charge, to any person

+ * copy of this software and associated documentation files (the

+ * to deal in the Software without restriction, including without

+ * the rights to use, copy, modify, merge, publish, distribute,

+ * and/or sell copies of the Software, and to permit persons to whom

+ * Software is furnished to do so, subject to the following conditions:

+ *

+ * The above copyright notice and this permission notice shall be

+ * in all copies or substantial portions of the Software.

+ *

+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,

+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF

+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT

+ * JEFF HARTMANN, OR ANY OTHER CONTRIBUTORS BE LIABLE FOR ANY CLAIM,

+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT

+ * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE

+ * OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

+ *

+ */

+

+

+#include <linux/pci.h>

+#include <linux/agp_backend.h>

+#include "agp.h"

+

+

+int agp3_generic_fetch_size(void)

+{

+       u16 temp_size;

+        int i;

+        struct aper_size_info_16 *values;

+

+       pci_read_config_word(agp_bridge->dev,agp_bridge->capndx+AGPAPSIZE, &temp_size);

+       values = A_SIZE_16(agp_bridge->driver->aperture_sizes);

+

+       for (i = 0; i < agp_bridge->driver->num_aperture_sizes; i++) {

+            if (temp_size == values[i].size_value) {

+                agp_bridge->previous_size =

+                       agp_bridge->current_size = (void *) (values +i);

+

+               agp_bridge->aperture_size_idx = i;

+               return values[i].size;

+            }

+       }

+       return 0;

+}

+EXPORT_SYMBOL(agp3_generic_fetch_size);

+

+void agp3_generic_tlbflush(struct agp_memory *mem)

+{

+       u32 ctrl;

+       pci_read_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPCTRL, &ctrl);

+       pci_write_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPCTRL, ctrl & ~AGPCTRL_GTLBEN);

+}

+EXPORT_SYMBOL(agp3_generic_tlbflush);

+

+int agp3_generic_configure(void)

+{

+       u32 temp;

+

+       struct aper_size_info_16 *current_size;

+       current_size = A_SIZE_16(agp_bridge->current_size);

+

+       pci_read_config_dword(agp_bridge->dev, AGP_APBASE, &temp);

+       agp_bridge->gart_bus_addr = (temp & PCI_BASE_ADDRESS_MEM_MASK);

+

+       // set aperture size

+       pci_write_config_word(agp_bridge->dev,agp_bridge->capndx+AGPAPSIZE, current_size->size_value);

+       // set gart pointer

+       pci_write_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPGARTLO, agp_bridge->gatt_bus_addr);

+

+       // enable aperture and GTLB

+       pci_read_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPCTRL, &temp);

+       pci_write_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPCTRL, temp | AGPCTRL_APERENB | AGPCTRL_GTLBEN);

+

+       return 0;

+}

+EXPORT_SYMBOL(agp3_generic_configure);

+

+void agp3_generic_cleanup(void)

+{

+       u32 ctrl;

+       pci_read_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPCTRL, &ctrl);

+       pci_write_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPCTRL, ctrl & ~AGPCTRL_APERENB);

+}

+EXPORT_SYMBOL(agp3_generic_cleanup);

+

+struct aper_size_info_16 agp3_generic_sizes[AGP_GENERIC_SIZES_ENTRIES]=

+{

+        {4096, 1048576, 10,0x000},

+        {2048,  524288, 9, 0x800},

+        {1024,  262144, 8, 0xc00},

+        { 512,  131072, 7, 0xe00},

+       { 256,   65536, 6, 0xf00},

+     { 128,   32768, 5, 0xf20},

+       {  64,   16384, 4, 0xf30},

+       {  32,    8192, 3, 0xf38},

+       {  16,    4096, 2, 0xf3c},

+       {   8,    2048, 1, 0xf3e},

+       {   4,    1024, 0, 0xf3f}

+};

+EXPORT_SYMBOL(agp3_generic_sizes);

diff -uprN --new-file linuxpp/drivers/char/agp/sis-agp.c linux-2.6.1-mm1/drivers/char/agp/sis-agp.c

--- linuxpp/drivers/char/agp/sis-agp.c	2004-01-16 08:19:18.000000000 +0100

+++ linux-2.6.1-mm1/drivers/char/agp/sis-agp.c	2004-01-16 16:19:33.000000000 +0100

@@ -61,7 +61,55 @@ static void sis_cleanup(void)

 			      (previous_size->size_value & ~(0x03)));

 }

-static struct aper_size_info_8 sis_generic_sizes[7] =

+static void sis648_enable(u32 mode)

+{

+       // find the master, this needs to be better

+       struct pci_dev *master = NULL;

+       u8 mcapndx=0;

+

+       while ((master = pci_find_class(PCI_CLASS_DISPLAY_VGA<<8,master)) != NULL) {

+         mcapndx = pci_find_capability(master, PCI_CAP_ID_AGP);

+         printk ("Found AGP device. %x:%x \n", master->vendor,master->device);

+         break;

+       }

+       if(!mcapndx)

+               return;

+

+       u32 tStatus;

+       u32 mStatus;

+       pci_read_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPSTAT, &tStatus);

+       pci_read_config_dword(master, mcapndx+AGPSTAT, &mStatus);

+

+       int tcc=(tStatus>>10)&3;

+       int mcc=(mStatus>>10)&3;

+       int calcycl=(tcc<mcc) ? tcc : mcc;

+       int sba=(tStatus & AGPSTAT_SBA) && (mStatus & AGPSTAT_SBA);

+       int agp_enable=1;

+       int gart64b=0;

+       int over4g=0;

+       int fw=(tStatus & AGPSTAT_FW) && (mStatus & AGPSTAT_FW);

+       int rate=(tStatus & 2) && (tStatus & 2) ? 2 : 1;

+

+       // init target (bridge)

+       u32 tcmd=(calcycl<<10)|(sba<<9)|(agp_enable<< :Cool: |(gart64b<<7)|(over4g<<5)|(fw<<4)|rate;

+       printk("tcmd=%x\n",tcmd);

+       pci_write_config_dword(agp_bridge->dev,agp_bridge->capndx+AGPCMD, tcmd);

+

+       // weird: on my 648fx chipset any rate change in the target command register

+       // triggers a 5ms screwup during which the master cannot be configured

+       set_current_state(TASK_INTERRUPTIBLE);

+       schedule_timeout (1+(HZ*5)/1000);

+

+       // init master (card)

+       int prq=(mStatus>>24)&0xff;

+       int parqsz=(tStatus>>AGPSTAT_ARQSZ_SHIFT) & 3;

+       u32 mcmd=(prq<<24)|(parqsz<<13)|(sba<<9)|(agp_enable<< :Cool: |(over4g<<5)|(fw<<4)|rate;

+       printk("mcmd=%x\n",mcmd);

+

+       pci_write_config_dword(master, mcapndx+AGPCMD, mcmd);

+}

+

+static struct aper_size_info_8 sis_generic_sizes[] =

 {

 	{256, 65536, 6, 99},

 	{128, 32768, 5, 83},

@@ -95,6 +143,30 @@ struct agp_bridge_driver sis_driver = {

 	.agp_destroy_page	= agp_generic_destroy_page,

 };

+struct agp_bridge_driver sis648_driver = {

+       .owner                  = THIS_MODULE,

+       .aperture_sizes         = agp3_generic_sizes,

+       .size_type              = U16_APER_SIZE,

+       .num_aperture_sizes     = AGP_GENERIC_SIZES_ENTRIES,

+       .configure              = agp3_generic_configure,

+       .fetch_size             = agp3_generic_fetch_size,

+       .cleanup                = agp3_generic_cleanup,

+       .tlb_flush              = agp3_generic_tlbflush,

+       .mask_memory            = agp_generic_mask_memory,

+       .masks                  = NULL,

+       .agp_enable             = sis648_enable,

+       .cache_flush            = global_cache_flush,

+       .create_gatt_table      = agp_generic_create_gatt_table,

+       .free_gatt_table        = agp_generic_free_gatt_table,

+       .insert_memory          = agp_generic_insert_memory,

+       .remove_memory          = agp_generic_remove_memory,

+       .alloc_by_type          = agp_generic_alloc_by_type,

+       .free_by_type           = agp_generic_free_by_type,

+       .agp_alloc_page         = agp_generic_alloc_page,

+       .agp_destroy_page       = agp_generic_destroy_page

+};

+

+

 static struct agp_device_ids sis_agp_device_ids[] __devinitdata =

 {

 	{

@@ -206,7 +278,10 @@ found:

 	if (!bridge)

 		return -ENOMEM;

-	bridge->driver = &sis_driver;

+       if(pdev->device==PCI_DEVICE_ID_SI_648)

+               bridge->driver = &sis648_driver;

+       else

+               bridge->driver = &sis_driver;

 	bridge->dev = pdev;

 	bridge->capndx = cap_ptr;

</patch>

----------

## secondshadow

AAAAAAAAAAAAAAAAHHHHHHHHHHHHHHHHHHHHHHH! If this works I'm gonna freak! I JUST finished building my non-nptl system because the fglrx drivers didn't seem to work properly.....ARG! Actually I really hope it works....now heres a really noob question:

How to I apply this????? And I'm assuming that it would be w/ vanilla sources correct?

And of course I'll be testing this with my non-nptl 2.6 kernel before I junk everything. I guess its a good thing that I partimaged my nptl partition before I scrapped it.  :Smile: 

----------

## secondshadow

I just noticed that that patch you posted doesn't look the same as the one in the forum you linked to. At least it doesn't appear to end the same. I think I'll use the one in the other forum, just to be safe?  :Wink: 

EDIT: Still not sure how to apply it though....I'll try and figure it out   :Twisted Evil: 

----------

## sim0nx

belive me....it does work and it rulez!  :Very Happy: 

copy everything between <patch></patch>, and save it to a file.

link your source tree to linux-2.6.1-mm1

do: patch -p0 < patch-filename

remove the link, enter the source tree, make all, copy the new bzimage to /boot etc etc.... reboot

opengl-update xfree

emerge the ati-drivers-3.7.0

opengl-update ati

depmod -a

modprobe fglrx

be sure to either compile agpgart+sis-agp into the kernel, or load them BEFORE the fglrx module and BEFORE starting X

you should be able to apply that patch to any kernel from 2.6.0-2.6.1-mm4

and any other 2.6 series kernel which hasn't updated it's agp drivers since 2.6.0

--> there's still a little problem.... when you restart X, 3D accel is gone, you need to reboot to have it back. but, your machine won't crash anymore, when you restart X

----------

## sim0nx

the patch in that other forum is screwed...

i mailed the guy who posted it, to send me the original email form oliver with the patch.

i posted the orig patch...

you can find the patch mirrored on my hp:

http://simon.trypill.org/SIS648FX.patch

----------

## secondshadow

I have a little problem...when I do patch -p0 SIS648FX.patch it just sits there. After reviewing the patch man page I tried 'patch -p0 -i SIS648FX.patch'... This gives me the following:

weakest-link linux # patch -p0 SIS648FX.patch

weakest-link linux # patch -p0 -i SIS648FX.patch

can't find file to patch at input line 4

Perhaps you used the wrong -p or --strip option?

The text leading up to this was:

--------------------------

|diff -uprN --new-file linuxpp/drivers/char/agp/Makefile linux-2.6.1-mm1/drivers/char/agp/Makefile

|--- linuxpp/drivers/char/agp/Makefile  2004-01-16 08:19:17.000000000 +0100

|+++ linux-2.6.1-mm1/drivers/char/agp/Makefile  2004-01-16 09:31:29.000000000 +0100

--------------------------

File to patch:

I've never patched anything before so forgive me if I seem incredably noobish....Did I do something wrong??

UPDATE: I used -p1 instead (after more reading) and it patched them  :Smile: 

----------

## sim0nx

the problem is that you shouldn't have entered the kernel source tree, but should have stayed at its parent dir.

i.e., your kernel tree is at /usr/src/linux

then you should have done this for patching it:

cd /usr/src

ln -s linux linux-2.6.1-mm1

patch -p0 < patch-file

rm linux-2.6.1-mm1

cd linux

make all

etc...

supposing you have a kernel tree different from 2.6.1-mm1 (if you have that one, you would have left the "ln" and "rm" part out of course)

----------

## secondshadow

ooooooooooooohhhhhhhhhhhhhhhhhhh....... well....it worked none the less. Well, it patched successfully I should say. It didn't work. Aparently this isn't my issue. Oh well. Back to 2.4.20-r7 for me.

----------

## R!tman

I will test this when I install gentoo on a friend's notebook. Thanks sim0nx!

----------

## schoett

I have applied Oliver Heilmann's patch from the Linux kernel mailing list to mm-sources 2.6.1-r5 and to development-sources 2.6.1, and in both cases inserting the sis-agp module (which pulls in the agpgart module) fails: 

```
Linux agpgart interface v0.100 (c) Dave Jones

agpgart: Detected SiS 648 chipset

agpgart: Maximum main memory to use for agp memory: 439M

agpgart: unable to determine aperture size.

agpgart: agp_backend_initialize() failed.

agpgart-sis: probe of 0000:00:00.0 failed with error -22
```

Without the patch, I could insert the sis-agp module ok

```
Linux agpgart interface v0.100 (c) Dave Jones

agpgart: Detected SiS 648 chipset

agpgart: Maximum main memory to use for agp memory: 439M

agpgart: AGP aperture is 128M @ 0xd0000000

```

 but (ever since 2.6.0-test7) I would then get a complete system hang (everything frozen except SysRq) when fglrx was used with this external agpgart.

My hardware is the Medion Titanium 8008 sold in Germany by ALDI in March 2003.  AGP mode ist set to Auto, aperture to 128M in the BIOS. 

```
# lspci -vvv

00:00.0 Host bridge: Silicon Integrated Systems [SiS] SiS 645xx (rev 03)

        Subsystem: Silicon Integrated Systems [SiS] SiS 645xx

        Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV- VGASnoop- ParErr- Stepping- SERR- FastB2B-

        Status: Cap+ 66Mhz- UDF- FastB2B- ParErr- DEVSEL=medium >TAbort- <TAbort- <MAbort+ >SERR- <PERR-

        Latency: 32

        Region 0: Memory at d0000000 (32-bit, non-prefetchable) [size=128M]

        Capabilities: [c0] AGP version 3.0

                Status: RQ=32 Iso- ArqSz=2 Cal=3 SBA+ ITACoh- GART64- HTrans- 64bit- FW- AGP3+ Rate=x4,x8

                Command: RQ=1 ArqSz=0 Cal=0 SBA- AGP- GART64- 64bit- FW- Rate=<none>

00:01.0 PCI bridge: Silicon Integrated Systems [SiS] SG86C202 (prog-if 00 [Normal decode])

        Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV- VGASnoop- ParErr- Stepping- SERR+ FastB2B-

        Status: Cap- 66Mhz- UDF- FastB2B- ParErr- DEVSEL=fast >TAbort- <TAbort- <MAbort- >SERR- <PERR-

        Latency: 64

        Bus: primary=00, secondary=01, subordinate=01, sec-latency=32

        I/O behind bridge: 0000c000-0000cfff

        Memory behind bridge: e8400000-e84fffff

        Prefetchable memory behind bridge: d8000000-e7ffffff

        BridgeCtl: Parity- SERR+ NoISA+ VGA+ MAbort- >Reset- FastB2B-

[...]

01:00.0 VGA compatible controller: ATI Technologies Inc Radeon R300 NF [Radeon 9700] (prog-if 00 [VGA])

        Subsystem: Hightech Information System Ltd.: Unknown device 8486

        Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV- VGASnoop- ParErr- Stepping+ SERR- FastB2B-

        Status: Cap+ 66Mhz+ UDF- FastB2B+ ParErr- DEVSEL=medium >TAbort- <TAbort- <MAbort- >SERR- <PERR-

        Latency: 255 (2000ns min), cache line size 08

        Interrupt: pin A routed to IRQ 11

        Region 0: Memory at d8000000 (32-bit, prefetchable) [size=128M]

        Region 1: I/O ports at c000 [size=256]

        Region 2: Memory at e8420000 (32-bit, non-prefetchable) [size=64K]

        Expansion ROM at <unassigned> [disabled] [size=128K]

        Capabilities: [58] AGP version 3.0

                Status: RQ=256 Iso- ArqSz=0 Cal=0 SBA+ ITACoh- GART64- HTrans- 64bit- FW+ AGP3+ Rate=x4,x8

                Command: RQ=1 ArqSz=0 Cal=0 SBA+ AGP- GART64- 64bit- FW- Rate=<none>

        Capabilities: [50] Power Management version 2

                Flags: PMEClk- DSI- D1+ D2+ AuxCurrent=0mA PME(D0-,D1-,D2-,D3hot-,D3cold-)

                Status: D0 PME-Enable- DSel=0 DScale=0 PME-

01:00.1 Display controller: ATI Technologies Inc Radeon R300 [Radeon 9700] (Secondary)

        Subsystem: Hightech Information System Ltd.: Unknown device 8487

        Control: I/O- Mem- BusMaster- SpecCycle- MemWINV- VGASnoop- ParErr- Stepping+ SERR- FastB2B-

        Status: Cap+ 66Mhz+ UDF- FastB2B+ ParErr- DEVSEL=medium >TAbort- <TAbort- <MAbort- >SERR- <PERR-

        Region 0: Memory at e0000000 (32-bit, prefetchable) [disabled] [size=128M]

        Region 1: Memory at e8430000 (32-bit, non-prefetchable) [disabled] [size=64K]

        Capabilities: [50] Power Management version 2

                Flags: PMEClk- DSI- D1+ D2+ AuxCurrent=0mA PME(D0-,D1-,D2-,D3hot-,D3cold-)

                Status: D0 PME-Enable- DSel=0 DScale=0 PME-

```

----------

## schoett

There is a new version of the SIS648 patch by Oliver Heilmann on the Linux-Kernel mailing list.  Can't test it myself until tomorrow night   :Rolling Eyes: 

I enclose it here because the archive above seems to have clobbered the spacing.

```
Path: main.gmane.org!not-for-mail

From: "Heilmann, Oliver" <Oliver.Heilmann@drkw.com>

Newsgroups: gmane.linux.kernel

Subject: [PATCH] AGPGART preliminary SiS648 support - fixed and shrunk

Date: Mon, 26 Jan 2004 09:46:24 +0000

Lines: 263

Sender: linux-kernel-owner@vger.kernel.org

Approved: news@gmane.org

Message-ID: <1075110384.566.6.camel@cobra>

NNTP-Posting-Host: deer.gmane.org

Mime-Version: 1.0

Content-Type: text/plain

Content-Transfer-Encoding: 7bit

X-Trace: sea.gmane.org 1075111021 8994 80.91.224.253 (26 Jan 2004 09:57:01 GMT)

X-Complaints-To: usenet@sea.gmane.org

NNTP-Posting-Date: Mon, 26 Jan 2004 09:57:01 +0000 (UTC)

Original-X-From: linux-kernel-owner+linux-kernel=40quimby.gnus.org@vger.kernel.org Mon Jan 26 10:56:51 2004

Return-path: <linux-kernel-owner+linux-kernel=40quimby.gnus.org@vger.kernel.org>

Original-Received: from quimby.gnus.org ([80.91.224.244])

   by deer.gmane.org with esmtp (Exim 3.35 #1 (Debian))

   id 1Al3UA-000593-00

   for <linux-kernel@deer.gmane.org>; Mon, 26 Jan 2004 10:56:50 +0100

Original-Received: from vger.kernel.org ([67.72.78.212])

   by quimby.gnus.org with esmtp (Exim 3.35 #1 (Debian))

   id 1Al3UA-0001D5-00

   for <linux-kernel@quimby.gnus.org>; Mon, 26 Jan 2004 10:56:50 +0100

Original-Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand

   id S263014AbUAZJqP (ORCPT <rfc822;linux-kernel@quimby.gnus.org>);

   Mon, 26 Jan 2004 04:46:15 -0500

Original-Received: (majordomo@vger.kernel.org) by vger.kernel.org id S264229AbUAZJqP

   (ORCPT <rfc822;linux-kernel-outgoing>);

   Mon, 26 Jan 2004 04:46:15 -0500

Original-Received: from mail1.drkw.com ([62.129.121.35]:57279 "EHLO mail1.drkw.com")

   by vger.kernel.org with ESMTP id S263014AbUAZJqA (ORCPT

   <rfc822;linux-kernel@vger.kernel.org>);

   Mon, 26 Jan 2004 04:46:00 -0500

Original-To: linux-kernel@vger.kernel.org

X-SA-Exim-Mail-From: Oliver.Heilmann@drkw.com

Precedence: bulk

X-Mailing-List: linux-kernel@vger.kernel.org

Xref: main.gmane.org gmane.linux.kernel:177324

X-Report-Spam: http://spam.gmane.org/gmane.linux.kernel:177324

* fixed a major bug where the request size had accidentally been take from the master's status reg instead of the target's.

* got rid of the extra file it's all in generic.c and sis-agp.c now

Any feedback is greatly appreciated. 

patch is vs 2.6.1

Oliver 

diff -urN -X dontdiff linux-2.6.1/drivers/char/agp/agp.h linux-2.6.1.agp648/drivers/char/agp/agp.h

--- linux-2.6.1/drivers/char/agp/agp.h   2004-01-09 06:59:26.000000000 +0000

+++ linux-2.6.1.agp648/drivers/char/agp/agp.h   2004-01-24 23:58:38.000000000 +0000

@@ -402,6 +402,16 @@

 void get_agp_version(struct agp_bridge_data *bridge);

 unsigned long agp_generic_mask_memory(unsigned long addr, int type);

 

+/* generic routines for agp>=3 */

+int agp3_generic_fetch_size(void);

+void agp3_generic_tlbflush(struct agp_memory *mem);

+int agp3_generic_configure(void);

+void agp3_generic_cleanup(void);

+

+/* aperture sizes have been standardised since v3 */

+#define AGP_GENERIC_SIZES_ENTRIES 11

+extern struct aper_size_info_16 agp3_generic_sizes[];

+

 extern int agp_off;

 extern int agp_try_unsupported_boot;

 

@@ -410,13 +420,17 @@

 #define AGPCMD         0x8

 #define AGPNISTAT      0xc

 #define AGPCTRL                 0x10

+#define AGPAPSIZE               0x14

 #define AGPNEPG         0x16

+#define AGPGARTLO               0x18

+#define AGPGARTHI               0x1c

 #define AGPNICMD      0x20

 

 #define AGP_MAJOR_VERSION_SHIFT   (20)

 #define AGP_MINOR_VERSION_SHIFT   (16)

 

 #define AGPSTAT_RQ_DEPTH   (0xff000000)

+#define AGPSTAT_RQ_DEPTH_SHIFT  24

 

 #define AGPSTAT_CAL_MASK   (1<<12|1<<11|1<<10)

 #define AGPSTAT_ARQSZ      (1<<15|1<<14|1<<13)

@@ -435,4 +449,7 @@

 #define AGPSTAT3_8X      (1<<1)

 #define AGPSTAT3_4X      (1)

 

+#define AGPCTRL_APERENB         (1<<8)

+#define AGPCTRL_GTLBEN          (1<<7)

+

 #endif            /* _AGP_BACKEND_PRIV_H */

diff -urN -X dontdiff linux-2.6.1/drivers/char/agp/generic.c linux-2.6.1.agp648/drivers/char/agp/generic.c

--- linux-2.6.1/drivers/char/agp/generic.c   2004-01-09 06:59:26.000000000 +0000

+++ linux-2.6.1.agp648/drivers/char/agp/generic.c   2004-01-24 23:02:37.000000000 +0000

@@ -956,3 +956,86 @@

 }

 EXPORT_SYMBOL(agp_generic_mask_memory);

 

+/*

+ * These functions are implemented according to the agpV3 spec,

+ * which covers implementation details that had previously been

+ * left open.

+ */

+

+int agp3_generic_fetch_size(void)

+{

+   u16 temp_size;

+        int i;

+        struct aper_size_info_16 *values;

+ 

+   pci_read_config_word(agp_bridge->dev, agp_bridge->capndx+AGPAPSIZE, &temp_size);

+   values = A_SIZE_16(agp_bridge->driver->aperture_sizes);

+

+   for (i = 0; i < agp_bridge->driver->num_aperture_sizes; i++) {

+      if (temp_size == values[i].size_value) {

+         agp_bridge->previous_size =

+            agp_bridge->current_size = (void *) (values + i);

+         

+         agp_bridge->aperture_size_idx = i;

+         return values[i].size;

+      }

+   }

+   return 0;

+}

+EXPORT_SYMBOL(agp3_generic_fetch_size);

+

+void agp3_generic_tlbflush(struct agp_memory *mem)

+{

+   u32 ctrl;

+   pci_read_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCTRL, &ctrl);

+   pci_write_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCTRL, ctrl & ~AGPCTRL_GTLBEN);

+   pci_write_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCTRL, ctrl);

+}

+EXPORT_SYMBOL(agp3_generic_tlbflush);

+

+int agp3_generic_configure(void)

+{

+   u32 temp;

+   

+   struct aper_size_info_16 *current_size;

+   current_size = A_SIZE_16(agp_bridge->current_size);

+   

+   pci_read_config_dword(agp_bridge->dev, AGP_APBASE, &temp);

+   agp_bridge->gart_bus_addr = (temp & PCI_BASE_ADDRESS_MEM_MASK);

+   

+   // set aperture size

+   pci_write_config_word(agp_bridge->dev, agp_bridge->capndx+AGPAPSIZE, current_size->size_value);

+   // set gart pointer

+   pci_write_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPGARTLO, agp_bridge->gatt_bus_addr);

+   

+   // enable aperture and GTLB

+   pci_read_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCTRL, &temp);

+   pci_write_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCTRL, temp | AGPCTRL_APERENB | AGPCTRL_GTLBEN);

+

+   return 0;

+}

+EXPORT_SYMBOL(agp3_generic_configure);

+

+void agp3_generic_cleanup(void)

+{

+   u32 ctrl;

+   pci_read_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCTRL, &ctrl);

+   pci_write_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCTRL, ctrl & ~AGPCTRL_APERENB);

+}

+EXPORT_SYMBOL(agp3_generic_cleanup);

+

+struct aper_size_info_16 agp3_generic_sizes[AGP_GENERIC_SIZES_ENTRIES]=

+{

+        {4096, 1048576, 10,0x000},

+        {2048,  524288, 9, 0x800},

+        {1024,  262144, 8, 0xc00},

+        { 512,  131072, 7, 0xe00},

+   { 256,   65536, 6, 0xf00},

+   { 128,   32768, 5, 0xf20},

+   {  64,   16384, 4, 0xf30},

+   {  32,    8192, 3, 0xf38},

+   {  16,    4096, 2, 0xf3c},

+   {   8,    2048, 1, 0xf3e},

+   {   4,    1024, 0, 0xf3f}

+};

+EXPORT_SYMBOL(agp3_generic_sizes);

diff -urN -X dontdiff linux-2.6.1/drivers/char/agp/sis-agp.c linux-2.6.1.agp648/drivers/char/agp/sis-agp.c

--- linux-2.6.1/drivers/char/agp/sis-agp.c   2004-01-09 06:59:06.000000000 +0000

+++ linux-2.6.1.agp648/drivers/char/agp/sis-agp.c   2004-01-25 17:26:15.000000000 +0000

@@ -95,6 +95,88 @@

    .agp_destroy_page   = agp_generic_destroy_page,

 };

 

+// sis-648 specific routines + driver

+static void sis648_enable(u32 mode)

+{

+   // find the master, this needs to be better

+   struct pci_dev *master = NULL;

+   u8 mcapndx=0;

+

+   while ((master = pci_find_class(PCI_CLASS_DISPLAY_VGA<<8, master)) != NULL) {

+      mcapndx = pci_find_capability(master, PCI_CAP_ID_AGP);

+      printk (KERN_INFO PFX "Found AGP master. %x:%x \n", master->vendor, master->device);

+      break;

+   }

+   if(!mcapndx)

+      return;

+   

+   u32 tStatus;

+   u32 mStatus;

+   pci_read_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPSTAT, &tStatus);

+   pci_read_config_dword(master, mcapndx+AGPSTAT, &mStatus);

+   

+   printk(KERN_INFO PFX "target status %x\n", tStatus);

+   printk(KERN_INFO PFX "master status %x\n", mStatus);

+   

+   int tcc=tStatus & AGPSTAT_CAL_MASK;

+   int mcc=mStatus & AGPSTAT_CAL_MASK;

+   int calcycl=(tcc<mcc) ? tcc : mcc;

+   int rate=(tStatus & tStatus &  AGPSTAT3_8X) ? 2 : 1;

+

+   u32 tcmd=tStatus & mStatus & (AGPSTAT_SBA|AGPSTAT_FW);

+   u32 mcmd=tcmd;

+   tcmd|=calcycl|AGPSTAT_AGP_ENABLE|rate;

+   mcmd|=(tStatus & AGPSTAT_RQ_DEPTH)|(tStatus & AGPSTAT_ARQSZ)|AGPSTAT_AGP_ENABLE|rate;

+

+   printk(KERN_INFO PFX "tcmd=%x\n",tcmd);

+   printk(KERN_INFO PFX "mcmd=%x\n",mcmd);

+

+   // init target (bridge)

+   pci_write_config_dword(agp_bridge->dev, agp_bridge->capndx+AGPCMD, tcmd);

+   

+   u8 mcaptest = pci_find_capability(master, PCI_CAP_ID_AGP);

+   if(mcaptest!=mcapndx)

+   {

+      printk(KERN_INFO PFX "master capndx screwed ... waiting 10ms\n");

+      // weird: on 648fx chipsets any rate change in the target command register

+      // triggers a 5ms screwup during which the master cannot be configured

+      set_current_state(TASK_INTERRUPTIBLE);

+      schedule_timeout (1+(HZ*10)/1000);  

+   }

+   else

+   {

+      printk(KERN_INFO PFX "bridge is up and master seems okay");

+   }

+   

+   // init master (card)

+   pci_write_config_dword(master, mcapndx+AGPCMD, mcmd);

+}

+

+struct agp_bridge_driver sis648_driver = {

+   .owner         = THIS_MODULE,

+   .aperture_sizes    = agp3_generic_sizes,

+   .size_type      = U16_APER_SIZE,

+   .num_aperture_sizes   = AGP_GENERIC_SIZES_ENTRIES,

+   .configure      = agp3_generic_configure,

+   .fetch_size      = agp3_generic_fetch_size,

+   .cleanup      = agp3_generic_cleanup,

+   .tlb_flush      = agp3_generic_tlbflush,

+   .mask_memory      = agp_generic_mask_memory,

+   .masks         = NULL,

+   .agp_enable      = sis648_enable,

+   .cache_flush      = global_cache_flush,

+   .create_gatt_table   = agp_generic_create_gatt_table,

+   .free_gatt_table   = agp_generic_free_gatt_table,

+   .insert_memory      = agp_generic_insert_memory,

+   .remove_memory      = agp_generic_remove_memory,

+   .alloc_by_type      = agp_generic_alloc_by_type,

+   .free_by_type      = agp_generic_free_by_type,

+   .agp_alloc_page      = agp_generic_alloc_page,

+   .agp_destroy_page   = agp_generic_destroy_page

+};

+// sis-648 end

+

+

 static struct agp_device_ids sis_agp_device_ids[] __devinitdata =

 {

    {

@@ -206,7 +288,11 @@

    if (!bridge)

       return -ENOMEM;

 

-   bridge->driver = &sis_driver;

+

+   if(pdev->device==PCI_DEVICE_ID_SI_648)

+      bridge->driver = &sis648_driver;

+   else

+      bridge->driver = &sis_driver;

    bridge->dev = pdev;

    bridge->capndx = cap_ptr;

--------------------------------------------------------------------------------

The information contained herein is confidential and is intended solely for the

addressee. Access by any other party is unauthorised without the express

written permission of the sender. If you are not the intended recipient, please

contact the sender either via the company switchboard on +44 (0)20 7623 8000, or

via e-mail return. If you have received this e-mail in error or wish to read our

e-mail disclaimer statement and monitoring policy, please refer to 

http://www.drkw.com/disc/email/ or contact the sender.

--------------------------------------------------------------------------------

```

----------

## schoett

 *schoett wrote:*   

> There is a new version of the SIS648 patch by Oliver Heilmann on the Linux-Kernel mailing list.  Can't test it myself until tomorrow night  

 

Well that patch did not work for me either, but after some mail exchange, Oliver Heilmann sent me a simple patch which works for me in the following form (applied to an unpatched 2.6.1 kernel):

```
--- linux-2.6.1/drivers/char/agp/generic.c.dist 2004-01-28 22:28:03.000000000 +0100

+++ linux-2.6.1/drivers/char/agp/generic.c      2004-01-28 23:17:19.000000000 +0100

@@ -524,6 +524,9 @@

                printk(KERN_INFO PFX "Putting AGP V%d device at %s into %dx mode\n",

                                agp_v3 ? 3 : 2, pci_name(device), mode);

                pci_write_config_dword(device, agp + PCI_AGP_COMMAND, command);

+               /* work around suspected SIS648 flakiness and delay a bit */

+               set_current_state(TASK_INTERRUPTIBLE);

+               schedule_timeout (1+(HZ/50)); /* 1/50th of a second */

        }

 }

 EXPORT_SYMBOL(agp_device_command);
```

The patch he posted on the LKML was designed to work for the SIS648FX chipset, while my chipset has the same PCI ID 0x0648 but dates before that and apparently must be initialised in a completely different way.  But what the chipsets seem to have in common is that they need this kind of delay   :Smile:   Presumably there will be a consolidated patch soon.

----------

## R!tman

Does this patch work with my SiS630 graphiccard?

----------

## schoett

 *R!tman wrote:*   

> Does this patch work with my SiS630 graphiccard?

 

It is not related to your graphics card, but to the "North Bridge" Chip on your motherboard.  Oliver Heilmann's posted patch is for the SiS648FX chip; the quick hack I posted (which is also due to Oliver Heilmann) is for the SiS648 chip.  Both chips identify themselves as "0x0648", but I think that Oliver Heilmann has found a way to tell them apart.  So it should be possible to wrap this all up in a proper patch to the kernel agpgart module that makes it work also for these two types of "North Bridge" chips.

----------

## schoett

 *schoett wrote:*   

> So it should be possible to wrap this all up in a proper patch to the kernel agpgart module that makes it work also for these two types of "North Bridge" chips.

 

Here is the new patch that is supposed to work for SiS648 as well as SiS648FX "North Bridge" Chips.

It works fine for my SiS648 chip (changes the machine from reliably wedging on X start with fglrx to reliably working)   :Very Happy: 

----------

## Yasir

Hey,

	I tried applying the last patch that schoett mentioned.  I encountered som problems while implementing it.

	I have put in a file SIS648.patch that I put in my /usr/src folder.  Since I use the 2.6.4-rc1 kernel i did

```

cd /usr/src

ln -s linux linux-2.6.2

patch -p0 > SIS648.patch

```

I get the following error:

```

patching file linux-2.6.2/drivers/char/agp/agp.h

patch: **** malformed patch at line 5: void get_agp_version(struct agp_bridge_data *bridge);

```

Any clues on how to deal with that (noob here   :Embarassed:  )

Thanks

UPDATEL: I have tried the -p1 option instead of -p0.  I get :

```
 can't find file to patch at input line 4

Perhaps you used the wrong -p or --strip option?

The text leading up to this was:

--------------------------

|diff -uprN -X dontdiff linux-2.6.2/drivers/char/agp/agp.h linux-2.6.2.lastmod/drivers/char/agp/agp.h

|--- linux-2.6.2/drivers/char/agp/agp.h 2004-02-04 03:43:43.000000000 +0000

|+++ linux-2.6.2.lastmod/drivers/char/agp/agp.h 2004-02-09 13:01:46.000000000 +0000

--------------------------

File to patch:
```

???

----------

## Yasir

Thanks sim0nx,

The patch seems to have worked fine.  I still have some problems with my lcd though.   Xfree log seems fine and X is responsive to ctrl-alt-backspace but screen is black and white patches of liquid cristal start to appear.

Any ideas?

----------

## X-Ryl669

Could you post Sim0nx answer here , so that everyone could apply the patch ?

Concerning your LCD problem, it is normal, as you don't have any window manager active. Try typing startx instead of Xfree86, or emerge kahakai, fluxbox, any wm.

Goodluck ( => twm might work too, even if it is very ugly)

----------

## reemi

I get the following error too:

Code:

```

patching file linux-2.6.2/drivers/char/agp/agp.h

patch: **** malformed patch at line 5: void get_agp_version(struct agp_bridge_data *bridge);

```

----------

## reemi

http://www.filoseta.org/et/forums/viewtopic.php?p=7816#7816

check this to correct your problem.

----------

