Author: aurel32
Date: 2011-03-26 18:50:00 +0000 (Sat, 26 Mar 2011)
New Revision: 4593

Added:
   glibc-package/branches/eglibc-2.13/debian/patches/i386/cvs-cacheinfo.diff
Modified:
   glibc-package/branches/eglibc-2.13/debian/changelog
   glibc-package/branches/eglibc-2.13/debian/patches/series
Log:
  * Add patches/i386/cvs-cacheinfo.diff to fix empty LEVEL*CACHE* getconf()
    entries for some CPU.  Closes: #609389.



Modified: glibc-package/branches/eglibc-2.13/debian/changelog
===================================================================
--- glibc-package/branches/eglibc-2.13/debian/changelog 2011-03-26 18:44:34 UTC 
(rev 4592)
+++ glibc-package/branches/eglibc-2.13/debian/changelog 2011-03-26 18:50:00 UTC 
(rev 4593)
@@ -141,6 +141,8 @@
   * Add patches/alpha/submitted-____longjmp_chk.diff to fix longjmp() with
     FORTIFY on alpha.
   * Add patches/alpha/submitted-PTR_MANGLE.diff to fix exceptions on alpha.
+  * Add patches/i386/cvs-cacheinfo.diff to fix empty LEVEL*CACHE* getconf()
+    entries for some CPU.  Closes: #609389.
 
   [ Samuel Thibault ]
   * Add patches/any/cvs-glro_dl_debug_mask.diff to fix build without

Added: glibc-package/branches/eglibc-2.13/debian/patches/i386/cvs-cacheinfo.diff
===================================================================
--- glibc-package/branches/eglibc-2.13/debian/patches/i386/cvs-cacheinfo.diff   
                        (rev 0)
+++ glibc-package/branches/eglibc-2.13/debian/patches/i386/cvs-cacheinfo.diff   
2011-03-26 18:50:00 UTC (rev 4593)
@@ -0,0 +1,137 @@
+2011-03-22  Ulrich Drepper  <[email protected]>
+
+       * sysdeps/unix/sysv/linux/i386/sysconf.c (intel_check_word): Increment
+       round counter.
+       * sysdeps/x86_64/cacheinfo.c (intel_check_word): Likewise.
+
+2011-03-20  Ulrich Drepper  <[email protected]>
+
+       [BZ #12587]
+       * sysdeps/unix/sysv/linux/i386/sysconf.c (intel_check_word):
+       Handle cache information in CPU leaf 4.
+       * sysdeps/x86_64/cacheinfo.c (intel_check_word): Likewise.
+
+diff --git a/sysdeps/unix/sysv/linux/i386/sysconf.c 
b/sysdeps/unix/sysv/linux/i386/sysconf.c
+index ff3cf9f..1f5d3b0 100644
+--- a/sysdeps/unix/sysv/linux/i386/sysconf.c
++++ b/sysdeps/unix/sysv/linux/i386/sysconf.c
+@@ -186,6 +186,57 @@ intel_check_word (int name, unsigned int value, bool 
*has_level_2,
+           /* No need to look further.  */
+           break;
+       }
++      else if (byte == 0xff)
++      {
++        /* CPUID leaf 0x4 contains all the information.  We need to
++           iterate over it.  */
++        unsigned int eax;
++        unsigned int ebx;
++        unsigned int ecx;
++        unsigned int edx;
++
++        unsigned int round = 0;
++        while (1)
++          {
++            asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1"
++                          : "=a" (eax), "=r" (ebx), "=c" (ecx), "=d" (edx)
++                          : "0" (4), "2" (round));
++
++            enum { null = 0, data = 1, inst = 2, uni = 3 } type = eax & 0x1f;
++            if (type == null)
++              /* That was the end.  */
++              break;
++
++            unsigned int level = (eax >> 5) & 0x7;
++
++            if ((level == 1 && type == data
++                 && folded_rel_name == M(_SC_LEVEL1_DCACHE_SIZE))
++                || (level == 1 && type == inst
++                    && folded_rel_name == M(_SC_LEVEL1_ICACHE_SIZE))
++                || (level == 2 && folded_rel_name == M(_SC_LEVEL2_CACHE_SIZE))
++                || (level == 3 && folded_rel_name == M(_SC_LEVEL3_CACHE_SIZE))
++                || (level == 4 && folded_rel_name == 
M(_SC_LEVEL4_CACHE_SIZE)))
++              {
++                unsigned int offset = M(name) - folded_rel_name;
++
++                if (offset == 0)
++                  /* Cache size.  */
++                  return (((ebx >> 22) + 1)
++                          * (((ebx >> 12) & 0x3ff) + 1)
++                          * ((ebx & 0xfff) + 1)
++                          * (ecx + 1));
++                if (offset == 1)
++                  return (ebx >> 22) + 1;
++
++                assert (offset == 2);
++                return (ebx & 0xfff) + 1;
++              }
++
++            ++round;
++          }
++        /* There is no other cache information anywhere else.  */
++        break;
++      }
+       else
+       {
+         if (byte == 0x49 && folded_rel_name == M(_SC_LEVEL3_CACHE_SIZE))
+diff --git a/sysdeps/x86_64/cacheinfo.c b/sysdeps/x86_64/cacheinfo.c
+index 337444d..bd4be3d 100644
+--- a/sysdeps/x86_64/cacheinfo.c
++++ b/sysdeps/x86_64/cacheinfo.c
+@@ -181,6 +181,57 @@ intel_check_word (int name, unsigned int value, bool 
*has_level_2,
+           /* No need to look further.  */
+           break;
+       }
++      else if (byte == 0xff)
++      {
++        /* CPUID leaf 0x4 contains all the information.  We need to
++           iterate over it.  */
++        unsigned int eax;
++        unsigned int ebx;
++        unsigned int ecx;
++        unsigned int edx;
++
++        unsigned int round = 0;
++        while (1)
++          {
++            asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1"
++                          : "=a" (eax), "=r" (ebx), "=c" (ecx), "=d" (edx)
++                          : "0" (4), "2" (round));
++
++            enum { null = 0, data = 1, inst = 2, uni = 3 } type = eax & 0x1f;
++            if (type == null)
++              /* That was the end.  */
++              break;
++
++            unsigned int level = (eax >> 5) & 0x7;
++
++            if ((level == 1 && type == data
++                 && folded_rel_name == M(_SC_LEVEL1_DCACHE_SIZE))
++                || (level == 1 && type == inst
++                    && folded_rel_name == M(_SC_LEVEL1_ICACHE_SIZE))
++                || (level == 2 && folded_rel_name == M(_SC_LEVEL2_CACHE_SIZE))
++                || (level == 3 && folded_rel_name == M(_SC_LEVEL3_CACHE_SIZE))
++                || (level == 4 && folded_rel_name == 
M(_SC_LEVEL4_CACHE_SIZE)))
++              {
++                unsigned int offset = M(name) - folded_rel_name;
++
++                if (offset == 0)
++                  /* Cache size.  */
++                  return (((ebx >> 22) + 1)
++                          * (((ebx >> 12) & 0x3ff) + 1)
++                          * ((ebx & 0xfff) + 1)
++                          * (ecx + 1));
++                if (offset == 1)
++                  return (ebx >> 22) + 1;
++
++                assert (offset == 2);
++                return (ebx & 0xfff) + 1;
++              }
++
++            ++round;
++          }
++        /* There is no other cache information anywhere else.  */
++        break;
++      }
+       else
+       {
+         if (byte == 0x49 && folded_rel_name == M(_SC_LEVEL3_CACHE_SIZE))

Modified: glibc-package/branches/eglibc-2.13/debian/patches/series
===================================================================
--- glibc-package/branches/eglibc-2.13/debian/patches/series    2011-03-26 
18:44:34 UTC (rev 4592)
+++ glibc-package/branches/eglibc-2.13/debian/patches/series    2011-03-26 
18:50:00 UTC (rev 4593)
@@ -138,6 +138,7 @@
 i386/local-linuxthreads-gscope.diff
 i386/local-pthread_cond_wait.diff
 i386/submitted-i686-timing.diff
+i386/cvs-cacheinfo.diff
 
 m68k/local-compat.diff
 m68k/local-dwarf2-buildfix.diff


-- 
To UNSUBSCRIBE, email to [email protected]
with a subject of "unsubscribe". Trouble? Contact [email protected]
Archive: http://lists.debian.org/[email protected]

Reply via email to