Synchronize kernel pages (global resource) across processes

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Synchronize kernel pages (global resource) across processes

Post by bluemoon »

Hi,

My kernel uses plain old 32-bit 2-level paging, and now face an issue:

Adding page
Upon adding new page into global address space, I can synchronize that to other process upon page fault (lazy TLB update). There is no problem.

Removing page
Problem! I may need to loop all the process's PD structure and remove the entry there.

Remapping address into different page
This may happen for example when switching video mode or hardware state changes, but I'm not sure.
Problem! I may need to loop all the process's PD structure and modify the entry there.


To resolve these issue I'm thinking to use PAE. With extra level of directory, all process can refer to the same PDE to put kernel and global resource there.

So, before I do this move, is there any other way to resolve the above issues? How people do before PAE exist?
gerryg400
Member
Member
Posts: 1801
Joined: Thu Mar 25, 2010 11:26 pm
Location: Melbourne, Australia

Re: Synchronize kernel pages (global resource) across proces

Post by gerryg400 »

One method I have used is to use a version number on the kernel page directory. Whenever the kernel PD is updated increase a 64bit number in the kernel. Whenever you do a context switch, check that the version number of the PD copy in the new process is correct. If it is not, copy the kernel PD to the process and update the process' PD version number.
If a trainstation is where trains stop, what is a workstation ?
User avatar
serviper
Member
Member
Posts: 31
Joined: Sat Jul 16, 2011 6:05 am
Location: China
Contact:

Re: Synchronize kernel pages (global resource) across proces

Post by serviper »

gerryg400 wrote:One method I have used is to use a version number on the kernel page directory. Whenever the kernel PD is updated increase a 64bit number in the kernel. Whenever you do a context switch, check that the version number of the PD copy in the new process is correct. If it is not, copy the kernel PD to the process and update the process' PD version number.
That's a nice solution...Thanks for the idea!
Last edited by serviper on Sun Apr 22, 2012 7:11 am, edited 1 time in total.
User avatar
bluemoon
Member
Member
Posts: 1761
Joined: Wed Dec 01, 2010 3:41 am
Location: Hong Kong

Re: Synchronize kernel pages (global resource) across proces

Post by bluemoon »

good idea.
egos
Member
Member
Posts: 612
Joined: Fri Nov 16, 2007 1:59 pm

Re: Synchronize kernel pages (global resource) across proces

Post by egos »

It's possible to map page tables for kernel reserved space during initialization, and then to copy their entries into new pagedir when process is forking.
If you have seen bad English in my words, tell me what's wrong, please.
User avatar
Brendan
Member
Member
Posts: 8561
Joined: Sat Jan 15, 2005 12:00 am
Location: At his keyboard!
Contact:

Re: Synchronize kernel pages (global resource) across proces

Post by Brendan »

Hi,
bluemoon wrote:So, before I do this move, is there any other way to resolve the above issues? How people do before PAE exist?
There's 4 ways that I know of:
  1. Pre-allocate page tables: If page tables are pre-allocated then page directory entries never change and the problem disappears. This is the fastest method. The disadvantage is that (if kernel space is 1 GiB) all the page tables will consume 1 MiB of RAM and you might not actually use half of them, so maybe 512 KiB of RAM gets wasted. This doesn't sound like much for a modern machine that supports PAE, but for older computers that don't support PAE there might only be 8 MiB of RAM and you might be wasting 6.25% of it.
  2. Map all page directories into kernel space: This works and is fairly easy to do. The disadvantage is that you have to compromise between kernel space usage and the maximum number of processes you can support. For example, if you reserve 128 MiB of kernel space for a "sparse array of page directory mappings" then you'd be limited to a maximum of 32768 processes.
  3. Version Number: This is the fastest way of making the actual page directory changes. The disadvantage is that it adds overhead to task switching, and because you don't remember which page directory entries were changed you have to copy all of them during the task switch. For example, if you change one page directory entry, then (if kernel space is 1 GiB) 1 KiB of data would have to be copied for each process, during later task switches.
  4. Journaling: This is like the version numbering; except you keep a journal/log of the last "n" changes. During the task switch you work out how many changes were made ("change_count = current global version - process version"). If "change_count" is zero you do nothing, if "change_count" is less than "n" you make the latest "change_count" changes listed in the journal/log, and if "change_count" is greater than "n" you copy the entire area of the page directory. The disadvantage here is complexity - whether it's worth the hassle or not depends on how often page directory entries are changed.
Also, note that the first 2 methods are the only methods that work if you allow page directory entries that are used by the kernel's code to be changed. Most people don't allow that though.


Cheers,

Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
Post Reply