summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAndy Lutomirski <luto@amacapital.net>2014-11-23 13:59:35 -0800
committerAndy Lutomirski <luto@amacapital.net>2014-11-23 13:59:35 -0800
commit92ab0e82faa75814f28f2a184a8fa6f3b6f5158a (patch)
treecc1fbc2e7401c5ff0f16547a5fe6b3b6bc476d8c
parent5655bd41ffedc002af69e3a8d1b0a168c22f2549 (diff)
downloadmisc-tests-92ab0e82faa75814f28f2a184a8fa6f3b6f5158a.tar.gz
user_visible_state: Add LDT decoding (useless without other changes)
-rw-r--r--user_visible_state.c20
1 files changed, 13 insertions, 7 deletions
diff --git a/user_visible_state.c b/user_visible_state.c
index d878e1a..0d61de6 100644
--- a/user_visible_state.c
+++ b/user_visible_state.c
@@ -7,6 +7,7 @@
#include <xmmintrin.h>
#include <asm/prctl.h>
#include <sys/prctl.h>
+#include <asm/ldt.h>
extern int arch_prctl(int, unsigned long);
@@ -174,26 +175,28 @@ static const char *user_seg_types[] = {
"XR code, confirming",
};
-static void show_segment(uint16_t index)
+static void show_segment(uint16_t index, int ldt)
{
uint32_t has_limit = 0, has_ar = 0, limit, ar;
- asm ("lsl %[index], %[limit]\n\t"
+ uint32_t selector = (index << 3) | (ldt << 2) | 3;
+
+ asm ("lsl %[selector], %[limit]\n\t"
"jnz 1f\n\t"
"mov $1, %[has_limit]\n\t"
"1:"
: [limit] "=r" (limit), [has_limit] "+rm" (has_limit)
- : [index] "r" ((index << 3) + 3));
- asm ("larl %[index], %[ar]\n\t"
+ : [selector] "r" (selector));
+ asm ("larl %[selector], %[ar]\n\t"
"jnz 1f\n\t"
"mov $1, %[has_ar]\n\t"
"1:"
: [ar] "=r" (ar), [has_ar] "+rm" (has_ar)
- : [index] "r" ((index << 3) + 3));
+ : [selector] "r" (selector));
if (!has_limit && !has_ar)
return;
- printf("GDT entry %02hu: ", index);
+ printf("%s entry %02hu: ", (ldt ? "LDT" : "GDT"), index);
if (has_limit)
printf(" limit = 0x%08X", limit);
@@ -221,6 +224,7 @@ int main()
// Optional: gives some visibility into how TLS works.
arch_prctl(ARCH_SET_GS, 500);
+ set_ldt();
uint16_t gdtlimit = show_gdt_and_idt();
show_ldt();
show_tr();
@@ -228,5 +232,7 @@ int main()
show_flags();
show_rdtscp();
for (int i = 0; i <= gdtlimit; i++)
- show_segment(i);
+ show_segment(i, 0);
+ for (int i = 0; i < 10; i++)
+ show_segment(i, 1);
}