[<prev] [next>] [day] [month] [year] [list]
Message-ID: <CAC12nxd9qfvoskRiP+fm6daoxKUbNO9LBH4VX_RoXRsuL-9Jmg@mail.gmail.com>
Date: Tue, 31 May 2022 09:11:59 -0400
From: Alphabet Hotel <alephhotel285@...il.com>
To: linux-kernel@...r.kernel.org
Subject: x86-32: can't create call gate in LDT?
I was looking at emulating the lcall7 syscall interface in userspace
but it seems I can't even ask for a call gate. I did get it to work by
using a regular code segment for entry 0 and mapping my lcall7 handler
at offset 0 but now I'm in a different code segment and GCC is lost.
Could the ability to use call gates be added to the kernel? The patch
looks fairly easy and if it only allows calls into the existing CS it
should be safe. My test program works as-is but it's a hack and it
would require switching segments on every syscall.
#define _GNU_SOURCE
#include <stdio.h>
#include <err.h>
#include <sys/syscall.h>
#include <asm/ldt.h>
static int ret = 1, val = 0;
static void __attribute__ ((regparm(1))) lcall7(int call_nr) {
val = call_nr; // remaining args are on the stack
asm volatile ("xor %eax,%eax;"
"lret;" // far return is required
);
}
int main() {
struct user_desc desc = {
.entry_number = 0,
.base_addr = (unsigned long)&lcall7,
.limit = 1, // one page
.limit_in_pages = 1,
.seg_32bit = 1,
.contents = 2, // non-conforming code
};
if (syscall(__NR_modify_ldt, 0x11, &desc, sizeof(desc)))
err(1, "modify_ldt");
asm volatile ("lcall $7,$0;"
: "=a" (ret)
: "a" (42)
);
if (!ret && val == 42)
printf("lcall7 worked\n");
}
Powered by blists - more mailing lists