All of lore.kernel.org
 help / color / mirror / Atom feed
From: Nicolas Aspert <Nicolas.Aspert@epfl.ch>
To: Didier Moens <moensd@xs4all.be>
Cc: Robert Love <rml@tech9.net>,
	skraw@ithnet.com, linux-kernel <linux-kernel@vger.kernel.org>
Subject: Re: [Fwd: Re: OOPS in agpgart (2.4.13, 2.4.15pre7)]
Date: Tue, 27 Nov 2001 08:57:17 +0100	[thread overview]
Message-ID: <3C03475D.6090303@epfl.ch> (raw)
In-Reply-To: <linux.kernel.3C021570.4000603@dmb.rug.ac.be> <3C022BB4.7080707@epfl.ch> <1006808870.817.0.camel@phantasy> <3C02BF41.1010303@xs4all.be>

[-- Attachment #1: Type: text/plain, Size: 1765 bytes --]

Didier Moens wrote:

 > Dear Robert, Nicolas, Stephan,   :)
 >
 >
 > I got two patches :
 >
 >
 > 1. From Stephan, to test whether my assumption about the secondary
 > device was right :
 >
 > Stephan wrote :
 >
 > But if you want you can check that out pretty simple: just add a "break"
 > right
 > after the case :
 >
 >                 case PCI_DEVICE_ID_INTEL_830_M_0:
 > ---> break;
 >
 >                         i810_dev = pci_find_device(PCI_VENDOR_ID_INTEL,
 >


What is the result if you place the 'break' a few lines below, just
before the 'agp_bridge.type = NOT_SUPPORTED;' ? Does the module still
loads ?


 > This patch left me with a loaded agpgart, and accelerated X (DRM/DRI).
 > The acceleration is still not up to par with an ATI Mobility-128 (30%
 > lower, while it should be at least 200% faster), but I suspect an X
 > CVS-problem here.
 >
 > Quitting and restarting X leaves me with a locked black screen.
 >


The origin of the problem is not obvious... as you said, it could be a
DRI/DRM/X related problem (-> hard to trace). In order to be sure AGP is 
functioning correctly, I suggest that you run this good old test program 
(attached) after loading the AGP module (but before starting X). I 
buried out this little fellow from the utah-glx project. All it does is 
trying to write some data to the agp memory. Try it with both flavors of 
the module (mine+your fix and the one from Stephan), and share the 
output with us ;-)

Good luck


 > Conclusion : Stephan's break-patch loads agpgart, loads X, and locks
 > when reloading X ; Nicolas' patch (when combined with Stephan's first
 > patch) loads agpgart and locks X hard.
 >



-- 
Nicolas Aspert      Signal Processing Laboratory (LTS)
Swiss Federal Institute of Technology (EPFL)


[-- Attachment #2: testgart.c --]
[-- Type: text/plain, Size: 6977 bytes --]

#include <stdio.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <fcntl.h>
#include <sys/mman.h>
#include <sys/time.h>
#include <linux/types.h>
#include <linux/agpgart.h>
#include <asm/mtrr.h>
#include <errno.h>

unsigned char *gart;
int gartfd;
int mtrr;

int usec( void ) {
  struct timeval tv;
  struct timezone tz;
  
  gettimeofday( &tv, &tz );
  return (tv.tv_sec & 2047) * 1000000 + tv.tv_usec;
}

int MemoryBenchmark( void *buffer, int dwords ) {
  int             i;
  int             start, end;
  int             mb;
  int             *base;
  
  base = (int *)buffer;
  start = usec();
  for ( i = 0 ; i < dwords ; i += 8 ) {
    base[i] =
      base[i+1] =
      base[i+2] =
      base[i+3] =
      base[i+4] =
      base[i+5] =
      base[i+6] =
      base[i+7] = 0x15151515;         /* dmapad nops */
  }
  end = usec();
  mb = ( (float)dwords / 0x40000 ) * 1000000 / (end - start);
  printf("MemoryBenchmark: %i mb/s\n", mb );
  return mb;
}

int insert_gart(int page, int size)
{
   agp_allocate entry;
   agp_bind bind;
   
   entry.type = 0;
   entry.pg_count = size;
#ifdef DEBUG
   printf("Using AGPIOC_ALLOCATE\n");
#endif
   if(ioctl(gartfd, AGPIOC_ALLOCATE, &entry) != 0)
    {
      perror("ioctl(AGPIOC_ALLOCATE)");
      exit(1);
    }
   
   bind.key = entry.key;
   bind.pg_start = page;
#ifdef DEBUG
   printf("Using AGPIOC_BIND\n");
#endif
   if(ioctl(gartfd, AGPIOC_BIND, &bind))
     {
	perror("ioctl(AGPIOC_BIND)");
	exit(1);
     }
   
   printf("entry.key : %i\n", entry.key);
   
   return(entry.key);
}

int unbind_gart(int key)
{
   agp_unbind unbind;
   
   unbind.key = key;
#ifdef DEBUG
   printf("Using AGPIOC_UNBIND\n");
#endif
   if(ioctl(gartfd, AGPIOC_UNBIND, &unbind) != 0)
     {
	perror("ioctl(AGPIOC_UNBIND)");
	exit(1);
     }
   
   return(0);
}

int bind_gart(int key, int page)
{
   agp_bind bind;
   
   bind.key = key;
   bind.pg_start = page;
#ifdef DEBUG
   printf("Using AGPIOC_BIND\n");
#endif
   if(ioctl(gartfd, AGPIOC_BIND, &bind) != 0)
     {
	perror("ioctl(AGPIOC_BIND)");
	exit(1);
     }
   
   return(0);
}

int remove_gart(int key)
{
#ifdef DEBUG
   printf("Using AGPIOC_DEALLOCATE\n");
#endif
  if(ioctl(gartfd, AGPIOC_DEALLOCATE, key) != 0)
    {
      perror("ioctl(GARTIOCREMOVE)");
      exit(1);
    }
   
   return(0);
}

void openmtrr(void) 
{
   if ((mtrr = open("/proc/mtrr", O_WRONLY, 0)) == -1) 
     {
	if (errno == ENOENT) {
	   perror("/proc/mtrr not found: MTRR not enabled\n");
	}  else {
	   perror("Error opening /proc/mtrr:");
	   perror("MTRR not enabled\n");
	   exit(1);
	}
	return;
     }
}

int CoverRangeWithMTRR( int base, int range, int type )
{
   int          count;   
      
   /* set it if we aren't just checking the number */
   if ( type != -1 ) {
      struct mtrr_sentry sentry;
      
      sentry.base = base;
      sentry.size = range;
      sentry.type = type;
      
      if ( ioctl(mtrr, MTRRIOC_ADD_ENTRY, &sentry) == -1 ) {
	 perror("mtrr");
	 exit(1);
      }
   }
   
}

int init_agp(void)
{
   agp_info info;
   agp_setup setup;

#ifdef DEBUG
   printf("Using AGPIOC_ACQUIRE\n");
#endif
   if(ioctl(gartfd, AGPIOC_ACQUIRE) != 0)
     {
	perror("ioctl(AGPIOC_ACQUIRE)");
	exit(1);
     }
#ifdef DEBUG
   printf("Using AGPIOC_INFO\n");
#endif
   if(ioctl(gartfd, AGPIOC_INFO, &info) != 0)
     {
	perror("ioctl(AGPIOC_INFO)");
	exit(1);
     }
   
   printf("version: %i.%i\n", info.version.major, info.version.minor);
   printf("bridge id: 0x%lx\n", info.bridge_id);
   printf("agp_mode: 0x%lx\n", info.agp_mode);
   printf("aper_base: 0x%lx\n", info.aper_base);
   printf("aper_size: %i\n", info.aper_size);
   printf("pg_total: %i\n", info.pg_total);
   printf("pg_system: %i\n", info.pg_system);
   printf("pg_used: %i\n", info.pg_used);

   openmtrr();
   if (mtrr != -1) { 
     CoverRangeWithMTRR(info.aper_base, info.aper_size * 0x100000, 
       MTRR_TYPE_WRCOMB);
   }

   gart = mmap(NULL, info.aper_size * 0x100000, PROT_READ | PROT_WRITE, MAP_SHARED, gartfd, 0);

   if(gart == (unsigned char *) 0xffffffff)
     {
	perror("mmap");
	close(gartfd);
	exit(1);
     }	
   
   setup.agp_mode = info.agp_mode;
#ifdef DEBUG
   printf("Using AGPIOC_SETUP\n");
#endif
   if(ioctl(gartfd, AGPIOC_SETUP, &setup) != 0)
     {
	perror("ioctl(AGPIOC_SETUP)");
	exit(1);
     }
   
   return(0);
}

int xchangeDummy;

void FlushWriteCombining( void ) {
	__asm__ volatile( " push %%eax ; xchg %%eax, %0 ; pop %%eax" : : "m" (xchangeDummy));
	__asm__ volatile( " push %%eax ; push %%ebx ; push %%ecx ; push %%edx ; movl $0,%%eax ; cpuid ; pop %%edx ; pop %%ecx ; pop %%ebx ; pop %%eax" : /* no outputs */ :  /* no inputs */ );
}

void BenchMark()
{
  int i, worked = 1;

  i = MemoryBenchmark(gart, (1024 * 1024 * 4) / 4) +
    MemoryBenchmark(gart, (1024 * 1024 * 4) / 4) +
    MemoryBenchmark(gart, (1024 * 1024 * 4) / 4);
  
  printf("Average speed: %i mb/s\n", i /3);
  
  printf("Testing data integrity (1st pass): ");
  fflush(stdout);
   
  FlushWriteCombining();
  
  for (i=0; i < 8 * 0x100000; i++)
    {
      gart[i] = i % 256;
    }
   
  FlushWriteCombining();
   
  
  for (i=0; i < 8 * 0x100000; i++)
    {
       if(!(gart[i] == i % 256))
	 {
#ifdef DEBUG
	    printf("failed on %i, gart[i] = %i\n", i, gart[i]);
#endif
	    worked = 0;
	 }
    }
  
  if (!worked)
    printf("failed on first pass!\n");
  else
    printf("passed on first pass.\n");
   
   unbind_gart(0);
   unbind_gart(1);
   bind_gart(0, 0);
   bind_gart(1, 1024);

   worked = 1;
   printf("Testing data integrity (2nd pass): ");
   fflush(stdout);
   
   for (i=0; i < 8 * 0x100000; i++)
    {
       if(!(gart[i] == i % 256))
	 {
#ifdef DEBUG
	    printf("failed on %i, gart[i] = %i\n", i, gart[i]);
#endif
	    worked = 0;
	 }
    }

   if (!worked)
    printf("failed on second pass!\n");
  else
    printf("passed on second pass.\n");
}

int main()
{
   int i;
   int key;
   int key2;
   agp_info info;
  
   gartfd = open("/dev/agpgart", O_RDWR);
   if (gartfd == -1)
     {	
	perror("open");
	exit(1);
     }
   
   init_agp();
   
   key = insert_gart(0, 1024);
   key2 = insert_gart(1024, 1024);
   
#ifdef DEBUG
   printf("Using AGPIOC_INFO\n");
   if(ioctl(gartfd, AGPIOC_INFO, &info) != 0)
     {
	perror("ioctl(AGPIOC_INFO)");
	exit(1);
     }
   
   printf("version: %i.%i\n", info.version.major, info.version.minor);
   printf("bridge id: 0x%lx\n", info.bridge_id);
   printf("agp_mode: 0x%lx\n", info.agp_mode);
   printf("aper_base: 0x%lx\n", info.aper_base);
   printf("aper_size: %i\n", info.aper_size);
   printf("pg_total: %i\n", info.pg_total);
   printf("pg_system: %i\n", info.pg_system);
   printf("pg_used: %i\n", info.pg_used);
#endif
   
   printf("Allocated 8 megs of GART memory\n");
   
   BenchMark();
   
   remove_gart(key);
   remove_gart(key2);

#ifdef DEBUG   
   printf("Using AGPIOC_RELEASE\n");
#endif
   if(ioctl(gartfd, AGPIOC_RELEASE) != 0)
     {
	perror("ioctl(AGPIOC_RELEASE)");
	exit(1);
     }
   
   close(gartfd);
}


  reply	other threads:[~2001-11-27  7:57 UTC|newest]

Thread overview: 15+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <linux.kernel.3C021570.4000603@dmb.rug.ac.be>
2001-11-26 11:47 ` [Fwd: Re: OOPS in agpgart (2.4.13, 2.4.15pre7)] Nicolas Aspert
2001-11-26 21:07   ` Robert Love
2001-11-26 22:16     ` Didier Moens
2001-11-27  7:57       ` Nicolas Aspert [this message]
     [not found]       ` <20011127101148.C5778@crystal.2d3d.co.za>
     [not found]         ` <3C034CAE.2090103@dmb.rug.ac.be>
2001-11-27  9:10           ` Abraham vd Merwe
2001-11-27  9:52             ` Didier Moens
2001-11-27 10:05               ` Nicolas Aspert
2001-11-27 10:48                 ` Didier Moens
2001-11-27 11:12                   ` Stephan von Krawczynski
2001-11-27 11:43                     ` Nicolas Aspert
2001-11-27 12:10                       ` Stephan von Krawczynski
2001-11-27 12:49                       ` Didier Moens
2001-11-27 10:51       ` Stephan von Krawczynski
2001-11-26 12:43 ` [PATCH]Re: " Nicolas Aspert
2001-11-26 10:12 Didier Moens

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=3C03475D.6090303@epfl.ch \
    --to=nicolas.aspert@epfl.ch \
    --cc=linux-kernel@vger.kernel.org \
    --cc=moensd@xs4all.be \
    --cc=rml@tech9.net \
    --cc=skraw@ithnet.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.