]> git.ipfire.org Git - thirdparty/valgrind.git/commitdiff
Added seg_override test. Note this test fails on the 1.0.X branch (if you use
authorNicholas Nethercote <njn@valgrind.org>
Wed, 2 Oct 2002 10:36:46 +0000 (10:36 +0000)
committerNicholas Nethercote <njn@valgrind.org>
Wed, 2 Oct 2002 10:36:46 +0000 (10:36 +0000)
the --stable option to the regression test script).

git-svn-id: svn://svn.valgrind.org/valgrind/trunk@1162

none/tests/.cvsignore
none/tests/Makefile.am
none/tests/seg_override.c [new file with mode: 0644]
none/tests/seg_override.stderr.exp [new file with mode: 0644]
none/tests/seg_override.stderr.exp.hd [new file with mode: 0644]
none/tests/seg_override.stdout.exp [new file with mode: 0644]
none/tests/seg_override.vgtest [new file with mode: 0644]

index 2e718679bee41d71921ca2e3f1cbfe33e034d33d..a2ae42900790e89a5d0bc06196215d0247f99f41 100644 (file)
@@ -18,6 +18,7 @@ rcl_assert
 rcrl
 readline1
 resolv
+seg_override
 sha1_test
 shortpush
 shorts
index ae1065017ae52367f66d536d51372ebead0350be..e00d485bfd636221476fae3287960b3b47985059 100644 (file)
@@ -32,6 +32,8 @@ EXTRA_DIST = \
        readline1.stderr.exp readline1.stderr.exp.hd readline1.stdout.exp \
        readline1.vgtest \
        resolv.stderr.exp resolv.stderr.exp.hd resolv.stdout.exp resolv.vgtest \
+       seg_override.stderr.exp seg_override.stderr.exp.hd \
+       seg_override.stdout.exp seg_override.vgtest \
        sha1_test.stderr.exp sha1_test.stderr.exp.hd sha1_test.vgtest \
        shortpush.stderr.exp shortpush.stderr.exp.hd shortpush.vgtest \
        shorts.stderr.exp shorts.stderr.exp.hd shorts.vgtest \
@@ -40,7 +42,7 @@ EXTRA_DIST = \
 noinst_PROGRAMS = \
        bitfield1 bt_everything bt_literal coolo_strlen \
        cpuid dastest floored fork fucomip munmap_exe rcl_assert \
-       rcrl readline1 resolv sha1_test shortpush shorts smc1 \
+       rcrl readline1 resolv seg_override sha1_test shortpush shorts smc1 \
        pth_blockedsig \
        coolo_sigaction gxx304
 
@@ -63,6 +65,7 @@ rcl_assert_SOURCES    = rcl_assert.S
 rcrl_SOURCES           = rcrl.c
 readline1_SOURCES      = readline1.c
 resolv_SOURCES                 = resolv.c
+seg_override_SOURCES   = seg_override.c
 smc1_SOURCES           = smc1.c
 sha1_test_SOURCES      = sha1_test.c
 shortpush_SOURCES      = shortpush.c
diff --git a/none/tests/seg_override.c b/none/tests/seg_override.c
new file mode 100644 (file)
index 0000000..805bfda
--- /dev/null
@@ -0,0 +1,138 @@
+
+#include <stdio.h>
+#include <errno.h>
+#include <string.h>
+
+/* Stuff from Wine. */
+
+typedef  unsigned short  WORD;  /* I guess */
+typedef  unsigned char   BYTE;
+
+typedef struct _LDT_ENTRY {
+    WORD        LimitLow;
+    WORD        BaseLow;
+    union {
+        struct {
+            BYTE        BaseMid;
+            BYTE        Flags1;
+               /*Declare as bytes to avoid alignment problems */
+            BYTE        Flags2;
+            BYTE        BaseHi;
+        } Bytes;
+        struct {
+            unsigned    BaseMid         : 8;
+            unsigned    Type            : 5;
+            unsigned    Dpl             : 2;
+            unsigned    Pres            : 1;
+            unsigned    LimitHi         : 4;
+            unsigned    Sys             : 1;
+            unsigned    Reserved_0      : 1;
+            unsigned    Default_Big     : 1;
+            unsigned    Granularity     : 1;
+            unsigned    BaseHi          : 8;
+        } Bits;
+    } HighWord;
+} LDT_ENTRY;
+
+inline static void *wine_ldt_get_base( const LDT_ENTRY *ent )
+{
+    return (void *)(ent->BaseLow |
+                    (unsigned long)ent->HighWord.Bits.BaseMid << 16 |
+                    (unsigned long)ent->HighWord.Bits.BaseHi << 24);
+}
+inline static unsigned int wine_ldt_get_limit( const LDT_ENTRY *ent )
+{
+    unsigned int limit = ent->LimitLow | (ent->HighWord.Bits.LimitHi << 16);
+    if (ent->HighWord.Bits.Granularity) limit = (limit << 12) | 0xfff;
+    return limit;
+}
+
+
+/* our copy of the ldt */
+LDT_ENTRY ldt_copy[8192];
+
+/* System call to set LDT entry.  */
+//extern int __modify_ldt (int, struct modify_ldt_ldt_s *, size_t);
+extern int __modify_ldt (int, void *, size_t);
+
+void print_ldt ( void )
+{
+   int res;
+   res = __modify_ldt( 0, ldt_copy, 8192*sizeof(LDT_ENTRY) );
+   printf("got %d bytes\n", res );   
+   perror("error is");
+}
+
+/* Structure passed on `modify_ldt' call.  */
+#define MODIFY_LDT_CONTENTS_DATA        0
+#define MODIFY_LDT_CONTENTS_STACK       1
+#define MODIFY_LDT_CONTENTS_CODE        2
+
+struct modify_ldt_ldt_s
+{
+  unsigned int entry_number;
+  unsigned long int base_addr;
+  unsigned int limit;
+  unsigned int seg_32bit:1;
+  unsigned int contents:2;
+  unsigned int read_exec_only:1;
+  unsigned int limit_in_pages:1;
+  unsigned int seg_not_present:1;
+  unsigned int useable:1;
+  unsigned int empty:25;
+};
+
+/* System call to set LDT entry.  */
+//extern int __modify_ldt (int, struct modify_ldt_ldt_s *, size_t);
+
+void set_ldt1 ( void* base )
+{
+  int stat;
+  struct modify_ldt_ldt_s ldt_entry;
+
+  /* stop valgrind yelping about initialised holes in this struct. */
+  memset(&ldt_entry, 0, sizeof(ldt_entry));
+
+  ldt_entry.entry_number = 1;
+  ldt_entry.base_addr = (unsigned)base; //0x12345678;
+  ldt_entry.limit = 10;
+  ldt_entry.seg_32bit = 1;
+  ldt_entry.contents = MODIFY_LDT_CONTENTS_DATA;
+  ldt_entry.read_exec_only = 0;
+  ldt_entry.limit_in_pages = 0;
+  ldt_entry.seg_not_present = 0;
+  stat = __modify_ldt (1, &ldt_entry, sizeof (ldt_entry));
+  printf("stat = %d\n", stat);
+}
+
+
+void ldt_seg_write ( int ldt_entno, unsigned offset, unsigned val )
+{
+  asm volatile("movl %2, %%eax\n\t"
+               "movl %1, %%edx\n\t"
+              "movl %0, %%gs\n\t"
+               "movl %%eax, %%gs:(%%edx)\t"
+              : 
+               : "r" (7 /* LDT(TI), least privilege */ + (ldt_entno << 3)), 
+                 "r" (offset), "r" (val)
+               : "eax", "edx", "cc" );
+}
+
+int main ( void )
+{
+  int i;
+  int arr[9];
+
+  for (i = 0; i < 9; i++) arr[i] = 11*i;
+
+  set_ldt1( &arr[4] );
+  print_ldt();
+
+  ldt_seg_write(1 /* ldt entry # */, 4 /* offset */, 4444);
+
+  for (i = 0; i < 9; i++) printf("%d ", arr[i]);
+  printf("\n");
+
+  return 0;
+}
+
diff --git a/none/tests/seg_override.stderr.exp b/none/tests/seg_override.stderr.exp
new file mode 100644 (file)
index 0000000..f35fe11
--- /dev/null
@@ -0,0 +1,3 @@
+
+error is: Success
+
diff --git a/none/tests/seg_override.stderr.exp.hd b/none/tests/seg_override.stderr.exp.hd
new file mode 100644 (file)
index 0000000..23f3a8a
--- /dev/null
@@ -0,0 +1,24 @@
+
+The following failure _might_ be caused by linking to NVidia's
+   libGL.so, so avoiding it, if you can, _might_ help you.  For example,
+   re-build any Qt libraries you are using without OpenGL support.
+
+Valgrind detected that your program requires
+the following unimplemented functionality:
+   modify_ldt(): I (JRS) haven't investigated this yet; sorry.
+This may be because the functionality is hard to implement,
+or because no reasonable program would behave this way,
+or because nobody has yet needed it.  In any case, let me know
+(jseward@acm.org) and/or try to work around the problem, if you can.
+
+Valgrind has to exit now.  Sorry.  Bye!
+
+
+sched status:
+
+Thread 1: status = Runnable, associated_mx = 0x0, associated_cv = 0x0
+   at 0x4032F974: __modify_ldt (in /lib/i686/libc-2.2.2.so)
+   by 0x804865F: main (seg_override.c:128)
+   by 0x40265177: __libc_start_main (../sysdeps/generic/libc-start.c:129)
+   by 0x80483F1: memset@@GLIBC_2.0 (in /local/scratch-2/njn25/local/src/grind/head/none/tests/a.out)
+
diff --git a/none/tests/seg_override.stdout.exp b/none/tests/seg_override.stdout.exp
new file mode 100644 (file)
index 0000000..0e62771
--- /dev/null
@@ -0,0 +1,3 @@
+stat = 0
+got 65536 bytes
+0 11 22 33 44 4444 66 77 88 
diff --git a/none/tests/seg_override.vgtest b/none/tests/seg_override.vgtest
new file mode 100644 (file)
index 0000000..225b30e
--- /dev/null
@@ -0,0 +1 @@
+prog: seg_override