From: Jeff D. <jd...@ka...> - 2001-10-13 20:37:28
|
ju...@ac... said: > Basically, Linux supports 10x more devices than any other OS other > than Windows. So, why not run a copy of Linux under your other > operating system,.and write a hook that allows the other operating > system's kernel to connect to a process running under the UML kernel > and access the linux device through that channel. > Has anyone worked on this? There has been some sporatic work to support UBS device drivers in UML, but nothing beyond that. > What would be required to support it? Generally, the OS needs a driver that can basically recognize the device. This driver needs to be able to provide direct access to the device and to pass device interrupts out to userspace. As I understand it, PCI devices map their control registers and stuff into io space on the host. A Linux device driver can ioremap this out to a UML driver, which can then fiddle those registers directly. The driver would have to provide a file that the UML driver would open, and convert device interrupts into SIGIOs on that file descriptor. The driver would not have to do much beyond that. It would not have to know anything about actually operating the device. > What are the requirements on an OS to port UML to it? It hasn't been done yet, so the full set of requirements isn't yet known. However, a few things are obvious: a mechanism for intercepting and nullifying Linux system calls - this doesn't need to be an official system call interception facility. If the OS just faults the process when a Linux system call happens, that's just as good (and better from a performance standpoint). general, page-granular mmap something like clone would be nice, and so would the equivalent of CLONE_FILE There are probably a bunch of others, but any halfway complete OS will likely provide them. If you intend to do something about this, I would start by providing driver support for UML on Linux. This would avoid the need to do an OS port up-front and would be useful in its own right to Linux driver developers. Jeff |
From: Jeff D. <jd...@ka...> - 2001-10-13 23:15:09
|
ad...@do... said: > Currently, UML has a tracing thread, that uses ptrace to intercept all > syscalls. Could it not be possible to rewrite the memory, so instead > of calling int 80, it calls some other interrupt, which is then mapped > directly into UML's kernel space? You really want to try to scan the binary to find all the int 80's? And how are you going to avoid false positives? And deal with things that generate code on the fly? Jeff |
From: Adam H. <ad...@do...> - 2001-10-14 01:12:37
|
On Sat, 13 Oct 2001, Jeff Dike wrote: > ad...@do... said: > > Currently, UML has a tracing thread, that uses ptrace to intercept all > > syscalls. Could it not be possible to rewrite the memory, so instead > > of calling int 80, it calls some other interrupt, which is then mapped > > directly into UML's kernel space? > > You really want to try to scan the binary to find all the int 80's? And > how are you going to avoid false positives? And deal with things that > generate code on the fly? I never said scan. When an int 80 occurs, check to see if the source of the call is an unmodified executable page. If so, then modify it with a faster call, that doesn't require using PTRACE to intercept int 80 calls. ----BEGIN GEEK CODE BLOCK---- Version: 3.12 GCS d- s: a-- c+++ UL++++ P+ L++++ !E W+ M o+ K- W--- !O M- !V PS-- PE++ Y+ PGP++ t* 5++ X+ tv b+ D++ G e h*! !r z? -----END GEEK CODE BLOCK----- ----BEGIN PGP INFO---- Adam Heath <do...@de...> Finger Print | KeyID 67 01 42 93 CA 37 FB 1E 63 C9 80 1D 08 CF 84 0A | DE656B05 PGP AD46 C888 F587 F8A3 A6DA 3261 8A2C 7DC2 8BD4 A489 | 8BD4A489 GPG -----END PGP INFO----- |
From: Jeff D. <jd...@ka...> - 2001-10-14 01:29:50
|
ad...@do... said: > I never said scan. When an int 80 occurs, check to see if the source > of the call is an unmodified executable page. If so, then modify it > with a faster call, that doesn't require using PTRACE to intercept int > 80 calls. Oh, OK. Except it won't be any faster. The tracing thread has to be there in order to do the first interception of each system call. Whatever you replace the int 80 with has to generate a signal. Given the current semantics of ptrace, which don't let you ignore anything, that signal will be seen by the tracing thread and passed along by it to the running thread. So, this won't be saving any context switches. To do that, you need to completely eliminate the tracing thread. Jeff |
From: Adam H. <ad...@do...> - 2001-10-14 01:56:28
|
On Sat, 13 Oct 2001, Jeff Dike wrote: > ad...@do... said: > > I never said scan. When an int 80 occurs, check to see if the source > > of the call is an unmodified executable page. If so, then modify it > > with a faster call, that doesn't require using PTRACE to intercept int > > 80 calls. > > Oh, OK. Except it won't be any faster. The tracing thread has to be there > in order to do the first interception of each system call. Whatever you > replace the int 80 with has to generate a signal. Given the current > semantics of ptrace, which don't let you ignore anything, that signal will > be seen by the tracing thread and passed along by it to the running thread. UML controls all aspects of the process loading into the virtual memory map it has. So, as part of that memory, it can have the syscall translation code. So modifying this special vector to jump to this translation code should be straight forward. However, there is the problem of virtual and real memory. Plus, switching processes will have to modify that interrupt. ----BEGIN GEEK CODE BLOCK---- Version: 3.12 GCS d- s: a-- c+++ UL++++ P+ L++++ !E W+ M o+ K- W--- !O M- !V PS-- PE++ Y+ PGP++ t* 5++ X+ tv b+ D++ G e h*! !r z? -----END GEEK CODE BLOCK----- ----BEGIN PGP INFO---- Adam Heath <do...@de...> Finger Print | KeyID 67 01 42 93 CA 37 FB 1E 63 C9 80 1D 08 CF 84 0A | DE656B05 PGP AD46 C888 F587 F8A3 A6DA 3261 8A2C 7DC2 8BD4 A489 | 8BD4A489 GPG -----END PGP INFO----- |
From: Jeff D. <jd...@ka...> - 2001-10-14 03:42:35
|
ad...@do... said: > UML controls all aspects of the process loading into the virtual > memory map it has. So, as part of that memory, it can have the > syscall translation code. So modifying this special vector to jump to > this translation code should be straight forward. You're not making too much sense to me. Maybe you could fill in some of the steps that you're leaving out. You seem to be suggesting putting some special code in the process which would somehow magically and quickly get into the UML syscall code. However, here's a proof that, given the existence of a tracing thread and the current semantics of ptrace, that system calls can't be handled any more efficiently than they are now: There's a fundamental requirement that a system call cause a mode switch from an unprivileged user mode to a privileged kernel mode. UML defines privilege as not having your system calls traced. UML needs some help from the host kernel in order to securely switch to kernel mode. Securely means that user code can't do it and continue running its own code. If a process switches to kernel mode, it must then run in code defined by UML. Help from the host kernel is required because, if it can be done without entering the host kernel, then a nasty program can just include the requisite code in its own binary, allowing it to get into kernel mode, running code of its choice. The most efficient way of doing this is to deliver a signal to the process with the signal handler defined by UML. Since the tracing thread is ptracing the process, it will see that signal, causing at least two context switches before the system call can run. The current situation is that two context switches happen before a system call runs. QED So, don't bother telling me about new schemes for getting into the kernel unless you can show me a hole in that logic. Jeff |
From: Adam H. <ad...@do...> - 2001-10-14 17:00:56
|
ps: I just realized the falicy in my scheme. The protecting and unprotecting of pages, when traversing the trampoline, will cause more context switches than ptrace, so the overall effect will be a net loss. However, I include the following email anyways, so that you'll understand what I was talking about. One thing that must happen for my idea to take place, is that the uml code(that does the syscall translation) must be mapped into the process. These mapped pages(that contain protected, kernel code), must be mapped non-executable, non-readable, and non-writable. There is one page that is not protected(let's call this a trampoline) This trampoline page(s) is executable, but still non-readable and non-writable. It is this trampoline that the special interrupt vector is pointed to(see below more more detail). In normal(the way things are currently done), a syscall(int 80) causes the tracing thread to be signaled(or otherwise return from the ptrace). This causes the dual context switch that you refer to. However, in enhanced mode, this trampoline get's called instead. This trampoline can verify that that it's called from a user page(and therefore needs to translate the call, and do other various uml things), or fail otherwise. These various other things include enabling the kernel code and data pages for use. Now, you may be thinking about what stops the userland process from unprotecting the kernel pages. Well, since pages have to go thru a verification process(also, their parameters must also be verified), the mmap and mprotect calls will either be controlled by ptrace(and the tracing thread), or will have been verified as being safe, and will use the fastpath. int 80 calls always go thru the tracing thread(by way of ptrace). The special syscall goes thru the trampoline(and is verified). The question is whether the context switches(s) are fast, or the trampoline/verification is faster. On Sun, 14 Oct 2001, Jeff Dike wrote: > ad...@do... said: > > UML controls all aspects of the process loading into the virtual > > memory map it has. So, as part of that memory, it can have the > > syscall translation code. So modifying this special vector to jump to > > this translation code should be straight forward. > > You're not making too much sense to me. Maybe you could fill in some of the > steps that you're leaving out. I'm not talking about removing the existing mechanisms, but adding to them, to give them a fast path. > You seem to be suggesting putting some special code in the process which > would somehow magically and quickly get into the UML syscall code. Yes, exactly. > However, here's a proof that, given the existence of a tracing thread and > the current semantics of ptrace, that system calls can't be handled any more > efficiently than they are now: The tracing thread will not go away. It is still needed to handle the unverified code pages of the process in question. > There's a fundamental requirement that a system call cause a mode switch > from an unprivileged user mode to a privileged kernel mode. UML defines > privilege as not having your system calls traced. > UML needs some help from the host kernel in order to securely switch to kernel > mode. Securely means that user code can't do it and continue running its own > code. If a process switches to kernel mode, it must then run in code > defined by UML. It will still get help. I hope the above description shows how. > Help from the host kernel is required because, if it can be done without > entering the host kernel, then a nasty program can just include the requisite > code in its own binary, allowing it to get into kernel mode, running code of > its choice. Entrance into the kernel is done by way of int 80, which is ptraced, and intercepted, and causes your context switch. Entrace is done by way of a trampoline, which has high security, and verifies the data it receives. > The most efficient way of doing this is to deliver a signal to the process > with the signal handler defined by UML. > > Since the tracing thread is ptracing the process, it will see that signal, > causing at least two context switches before the system call can run. Once this is done, a code page verification takes place. > The current situation is that two context switches happen before a system > call runs. > > QED > > So, don't bother telling me about new schemes for getting into the kernel > unless you can show me a hole in that logic. It's not a new scheme, but an additional one. |
From: Adam H. <ad...@do...> - 2001-10-13 22:10:11
|
On Sat, 13 Oct 2001, Jeff Dike wrote: > a mechanism for intercepting and nullifying Linux system calls - this doesn't > need to be an official system call interception facility. If the OS just faults > the process when a Linux system call happens, that's just as good (and better > from a performance standpoint). Currently, UML has a tracing thread, that uses ptrace to intercept all syscalls. Could it not be possible to rewrite the memory, so instead of calling int 80, it calls some other interrupt, which is then mapped directly into UML's kernel space? Of course, I'm not sure if linux allows for arbitrary interrupt vectors to be modified. Another problem with this is that there are a limited number of interrupt vectors on i386, at least, which means that the special vector would have to be continously updated. ----BEGIN GEEK CODE BLOCK---- Version: 3.12 GCS d- s: a-- c+++ UL++++ P+ L++++ !E W+ M o+ K- W--- !O M- !V PS-- PE++ Y+ PGP++ t* 5++ X+ tv b+ D++ G e h*! !r z? -----END GEEK CODE BLOCK----- ----BEGIN PGP INFO---- Adam Heath <do...@de...> Finger Print | KeyID 67 01 42 93 CA 37 FB 1E 63 C9 80 1D 08 CF 84 0A | DE656B05 PGP AD46 C888 F587 F8A3 A6DA 3261 8A2C 7DC2 8BD4 A489 | 8BD4A489 GPG -----END PGP INFO----- |