- Updated sleeping paths such that a task is atomically put into
a runqueue and made RUNNABLE, or removed from a runqueue and made SLEEPING.
- Modified vma dropping sources to handle both copy_on_write() and exit() cases
in a common function.
- Added the first infrastructure to have a pager to suspend a task and wait for
suspend completion from the scheduler.
fs0 used to receive open() requests and notify pager about them via a syscall ipc.
This caused deadlocks because normally request flow is mm0 -> fs0 on all other calls.
The solution was to have mm0 ask and validate file descriptors from fs0 on the first
request instance that involved that file descriptor. By this method we delay the
validation of the fd until its first use, and avoid deadlock. It also fits well with
the lazy request handling design philosophy.
close() needs to flush dirty buffers.
pager needs to have read/write support properly implemented.
open() needs to record mode and access times.
The need for access times means we need rtc and time implementation.
Also need to add stat() access() etc.
Input paths are now parsed at the beginning and components
put into an ordered linked list headed by struct pathdata.
Lookup functions use these components to look up vnodes.
Factored out mapping of the physical page as the final generic code
after all fault-specific handling is done.
Fixed the error that zero page didn't have an owner (devzero).
Fixed the error that struct dirent did not have the record length
field as u16 as expected by userspace.
Dirbuf allocation was broken, fixed it.
Added more comments on reading directories.
Issues: fs0 ought to check buf address for sys_readdir(). Currently
test0 is passing an area on its stack and fs0 is writing the data to its own
address space (i.e. an area on its own stack.)
- fixed is_err(x), was evaluating x twice, resulting in calling a
function x twice.
- Divided task initialisation into multiple parts.
- MM0 now creates a tcb for itself and maintains memory regions of its own.
- MM0's tcb is used for mmapping other tasks' regions. MM0 mmaps and prefaults
those regions, instead of the typical mmap() and fault approach used by
non-pager tasks.
For example there's an internal shmget_shmat() path to map in other tasks'
shm utcbs. Those mappings are then prefaulted into mm0's address space using
the default fault handling path.
- FS0 now reads task data into its utcb from mm0 via a syscall.
FS0 shmat()s to utcbs of other tasks, e.g. mm0 and test0.
FS0 then crashes, that is to be fixed and where this commit is left last.
utcb as a shared page instead of the message registers.
Implemented the code that passes task information from mm0 to fs0
using the fs0 utcb. The code seems to work OK but:
There's an issue with anon pages that they end up on the same swapfile
and with same file offsets (e.g. utcb and stack at offset 0). Need to
fix this issue but otherwise this implementation seems to work.
TODO:
- Separate anon regions into separate vmfiles.
- Possibly map the stacks from virtual files so that they can be
read from userspace in the future for debugging.
- Possibly utcb could be created as a shared memory object using shmget/shmat
during startup.
Environment is backed by a special per-task file maintained by mm0 for each task.
This file is filled in by the env pager, by simple copying of env data into the
faulty page upon a fault. UTCB and all anon regions (stack) could use the same
scheme.
Fixed IS_ERR(x) to accept negative values that are above -1000 for errors. This
protects against false positives for pointers such as 0xE0000000.
modified: include/l4/generic/scheduler.h
modified: include/l4/macros.h
modified: src/arch/arm/exception.c
modified: tasks/fs0/include/linker.lds
modified: tasks/libl4/src/init.c
modified: tasks/libposix/shm.c
new file: tasks/mm0/include/env.h
modified: tasks/mm0/include/file.h
new file: tasks/mm0/include/lib/addr.h
deleted: tasks/mm0/include/lib/vaddr.h
modified: tasks/mm0/include/task.h
new file: tasks/mm0/include/utcb.h
new file: tasks/mm0/src/env.c
modified: tasks/mm0/src/fault.c
modified: tasks/mm0/src/file.c
modified: tasks/mm0/src/init.c
new file: tasks/mm0/src/lib/addr.c
modified: tasks/mm0/src/lib/idpool.c
deleted: tasks/mm0/src/lib/vaddr.c
modified: tasks/mm0/src/mmap.c
modified: tasks/mm0/src/shm.c
modified: tasks/mm0/src/task.c
new file: tasks/mm0/src/utcb.c
modified: tasks/test0/include/linker.lds
We now have a single dirbuf of size PAGE_SIZE kept on the vnode. This is
to be used for directory contents only. The reason it's kept on FS0 is
because the contents are modified by calls such as mkdir or create, and otherwise
these would have been handled by mm0 on the page cache buffers, which wouldn't work.
Boot files and tasks are now initialised together. Theads can ask for particular
space and thread ids, if they're unused. This enables us to get predefined ids for
known tasks such as the VFS task.
Fixes to README
Other minor fixes.
Previously python hex() would put an extra 'L' after printing out the
value and this would be trimmed in readelf.py. Now it doesn't seem to
do that so the lsd of the number was trimmed. This patch fixes that.