I am pretty surprised myself that I was able to consolidate all "page table range" functions into a single type of iterator (well, there are a couple of variations, but it's not too bad). I thought at least the functions which allocate new page tables would have to be seperate from those which don't.... it turns out that if you slightly change the implementation of the allocating functions, they start walking, quacking, etc. like the other type. This may also opens the way for things like: #define for_each_pud(pgd, start, end, pud, pud_start, pud_end) \ if (pud = (pud_t *)pgd, pud_start = start, pud_end = end, 1) for 2 and 3 level page tables (don't laugh if I've messed up the above completely - you get the idea). Then the last bit of the performance puzzle I think will just come from inlining things. Now Andi doesn't want to do that (probably rightly so)... what about compiling mm/ with -funit-at-a-time? It doesn't do much harm to the stack, and it shaves off quite a few KB... Anyway, this iterator patch shaves off a bit itself. I haven't looked at generated code, but I hope it is alright. npiggin@didi:~/usr/src/linux-2.6$ size mm/memory.o.before text data bss dec hex filename 11349 4 120 11473 2cd1 mm/memory.o npiggin@didi:~/usr/src/linux-2.6$ size mm/memory.o.after text data bss dec hex filename 11221 4 120 11345 2c51 mm/memory.o Suggestions, help, etc. welcome. Nick