pooka
0cadacacab
* create /dev on the rump rootfs automatically
...
* make rump_vfs_makedevnodes() take a full basepath instead of hardcoding
an assumption that the device node is created in /dev
+ the caller is responsible that the directory the nodes are being
created in exists
2009-12-03 15:06:04 +00:00
pooka
89d988455a
Do bounds-checking before adding host offset. Otherwise the host
...
offset would be counted in with "size" and incorrect operation
would ensue.
2009-12-03 14:05:46 +00:00
pooka
2ce80d0210
Remove last remnants of the long-ago-properly-fixed RUMP_LMUTEX_MAGIC hack.
2009-12-03 13:12:16 +00:00
pooka
4535fac711
Make sure node lengths match in addition to strncmp().
...
(I thought i fixed this already once?)
2009-12-03 12:54:30 +00:00
pooka
f703feb95e
Call spec_init() to avoid device open lossage.
2009-12-03 12:52:42 +00:00
pooka
1e98588f3b
Decide it's not worth the fuss to have rumpfs as a module and just
...
hardcode attach into rump_vfs_init(). Saves us from a lot of
pingpong init bouncing from one component to another to get the order
right.
2009-12-03 12:35:34 +00:00
pooka
53ddf73f75
Soft-fail xcall thread creation to make RUMP_THREADS=0 work again.
2009-12-03 12:16:36 +00:00
pooka
c92b36b85b
fix inverted comparison
2009-12-02 17:18:59 +00:00
uebayasi
5eef0d3167
Declare global pointers as extern, otherwise they become common symbols.
...
Fix mips build in lib/librumpnet.
2009-12-02 08:31:56 +00:00
pooka
9fd1bf7eef
call cache_cpu_init() for all cpus
2009-12-01 09:56:59 +00:00
pooka
612479bd5e
Include cpu crosscall support (instead of stubbing it out).
2009-12-01 09:52:29 +00:00
pooka
62e84772b7
Almost there for virtual CPU MP support:
...
* support bound kernel threads
* bind softint threads to specific virtual cpus
+ remove now-unnecessary locks from softint code
Now, if we only had MI CPU_INFO_FOREACH() .... (hi rmind ;)
2009-12-01 09:50:51 +00:00
pooka
03735afa20
whitespace
2009-12-01 09:04:21 +00:00
pooka
d772942437
test for error in creating root vnode before using it
2009-11-30 12:32:13 +00:00
pooka
0c5879110f
Use genfs_statvfs() for now.
2009-11-30 11:18:22 +00:00
pooka
ea0564ea28
fix comment
2009-11-30 11:14:58 +00:00
pooka
307d8134c0
support lookup of pathname component "."
2009-11-30 10:11:09 +00:00
pooka
2a0ed023df
Remove no longer necessary vfs weak symbols.
2009-11-27 17:55:04 +00:00
pooka
ee0457e379
include subr_kobj_vfs
2009-11-27 17:54:24 +00:00
pooka
8102fe7341
Move rootfs-related init from init_main() to vfs_mountroot().
...
Reduces code re-written in rump.
2009-11-27 16:43:51 +00:00
pooka
ebb48144a9
Now that Makefile.rump was changed and everything gets built in
...
update builds too, flip the allocator define to prefer the kernel
pool/kmem instead of malloc(3). Use malloc(3) only if
RUMP_USE_UNREAL_ALLOCATORS is defined.
2009-11-27 13:45:15 +00:00
pooka
67cd12f07f
Include arch/include/Makefile.inc for some compiler flags.
2009-11-27 13:36:30 +00:00
pooka
b318442ec7
Make sure rumpfs is attached on all host platforms.
2009-11-26 21:04:42 +00:00
pooka
aee2ff8e8d
For rumpfs, do mountroot instead of the bunch of homegrown hacks
...
currently there. Still needs a little massage to get the kernel
interfaces right and avoid copypaste especially from main().
Also, move it a bit more into the direction of a real file system
(finally!) by giving it a vfsops. Most ops are still unimplemented,
though.
2009-11-26 20:58:51 +00:00
pooka
f631bc6ff9
remember to call pipe_init()
2009-11-26 17:36:22 +00:00
pooka
9c1300e7ee
Provide some sort of cv_is_valid(). What a silly routine.
2009-11-26 17:29:34 +00:00
pooka
fea060dfd3
include sys_pipe.c
2009-11-26 17:24:52 +00:00
pooka
7bcd019a9d
regen for rump_sys_pipe()
2009-11-26 17:24:36 +00:00
pooka
c845b495c5
regen: retval -> retval[2]
2009-11-26 16:38:01 +00:00
pooka
32e96a0e50
* load symbols only up to actual size of symbol table instead of size
...
we allocated for storing the table
* trimm unused end off of table before passing to the kernel
2009-11-26 15:44:26 +00:00
pooka
d2b375e830
Shuffle types around and add some random typecasts to make lint
...
and LP64 gcc sign comparison shut up. I'm not sure what benefit
this brings apart from introducing some more bugs for everyone's
debugging pleasure.
2009-11-26 10:57:26 +00:00
pooka
2dc78d8839
Remove assym.h. It's no longer required by hppa since spcopy is
...
not included anymore.
2009-11-26 10:42:04 +00:00
pooka
b3d7587523
update a bit
2009-11-26 10:10:50 +00:00
pooka
300f534bd8
Build the kernel symbol table in rumpuser bootstrap and feed it to
...
the rump kernel. After this change it is possible to use the
in-kernel linker and rump_sys_modctl() to load kernel modules at
runtime.
Previously loading modules at runtime was possible only through
using the host system ld.so. Note that it is still preferred to
use shared libs when possible, since they are PIC and n virtual
kernels will only require one copy of r/o segments. However, when
there is no access to source code, a binary kernel module is the
only thing available ...
2009-11-26 09:50:38 +00:00
pooka
4f28ef3250
regen: rump_kernelfsym_load()
2009-11-26 09:21:16 +00:00
pooka
ff492c8ebe
Add rump_kernelfsym_load(), which loads the kernel symbol table.
2009-11-26 09:20:07 +00:00
pooka
7d11849a4a
regen: rump_sys_modctl()
2009-11-26 09:02:38 +00:00
pooka
282ff84bcb
Include kern_module_vfs and the modctl() syscall. The modctl()
...
syscall is here because module loading is a vfs operation.
Theoretically you shouldn't be able to have modules without vfs
support.
2009-11-26 07:30:24 +00:00
pooka
4686e2c38a
* report partition size in blocks instead of bytes
...
* "support" DIOCCACHESYNC.
2009-11-25 15:01:28 +00:00
pooka
3d17105af3
Include link.h instead of the NetBSD-specific link_elf.h. Use
...
dlinfo() only if __ELF__ is defined.
2009-11-23 14:39:35 +00:00
pooka
09dbb89b44
If cpu_disklabel includes struct dkbad, define __HAVE_DISKLABEL_DKBAD.
...
This allows use of subr_disk_mbr on all archs. Default to it for
the rump disk component. No functional change for regular kernels.
(The other option would've been to include dkbad in disklabels
everywhere, but arguably this approach has less possible side-effects,
especially given that wedges and related magic will take over the
world any second now).
2009-11-23 13:40:08 +00:00
pooka
f8d9830a1a
Add rf_paritymap.c, which is now required for raidframe.
2009-11-23 12:23:20 +00:00
pooka
bb7f50bcca
kern_physio is already provided by rumpvfs
2009-11-23 11:20:25 +00:00
pooka
02a11f095f
Generate fictional disklabel and return that from ioctl() instead
...
of the halfwitted semi-host semi-virtual ioctl nonsense that was
here previously.
2009-11-20 17:48:52 +00:00
pooka
071c062533
include components required by smbfs
2009-11-20 15:37:44 +00:00
pooka
59f20ea12d
Hmm, in addition to leaving out -lc, -nostdlibs also leaves out
...
libgcc, and causes problems on some platforms. Currently there is
no easy way to say "link against libgcc but not against libc", so
just comment out -nostdlibs until a better way is invented.
2009-11-20 12:24:17 +00:00
pooka
8e8d412248
Create async i/o "interrupt" thread from within the kernel so that
...
it gets a kernel thread context.
2009-11-19 14:44:58 +00:00
pooka
1de15b17c4
* don't open device when calling getfileinfo(), it might need to open
...
the device and will f-a-i-l if it's a block device
* use rumpuser_ioctl() as little as possible (going away completely
wewy wewy soon)
* improve some variable scoping
2009-11-19 13:46:55 +00:00
pooka
e7c51ca379
.. umm, and use correct device value for previous.
...
And use 64bit arithmetic.
2009-11-19 13:42:29 +00:00
pooka
69eddfb6c5
Improve host file size detection for devices (i.e. make it work).
...
Use ioctl() on NetBSD since it appears to be the only way to get
the info. On other platforms, attempt lseek() and if that doesn't
work, punt, and hope someone comes along with a better implementation
later.
2009-11-19 13:25:48 +00:00
pooka
1fb57ddbb5
Don't link rump kernel libs against libc. They have no host system
...
dependencies apart from indirect ones via rumpuser.
2009-11-17 16:17:06 +00:00
pooka
f7dd9c5812
Don't build rumpuser if NORUMPUSER is set.
2009-11-17 15:36:28 +00:00
pooka
8ef9411fc9
init global cv only once
2009-11-17 15:23:42 +00:00
pooka
53e3c13474
set return value properly
2009-11-11 16:50:17 +00:00
pooka
9359f96adb
support timeouts in tsleep
2009-11-11 16:47:50 +00:00
pooka
ee4c8e1012
Make rumpuser_cv_timedwait take two int64's instead timespec to
...
uncouple it from the timespec layout. Also, change return value
to zero for "timeout didn't expire" and non-zero for "timeout
expired". This decouples the interface from errno assignments.
2009-11-11 16:46:50 +00:00
pooka
303e90e2c8
Give this a makefile for easy rebuild of all the components when
...
the kernel ABI changes.
2009-11-11 13:54:54 +00:00
pooka
886a3cee40
init uvm readahead
2009-11-10 17:02:36 +00:00
pooka
054e6b6e93
Code which uses pages fetched by the pager needs PGO_SYNCIO for
...
obvious reasons.
2009-11-10 16:55:12 +00:00
pooka
644009f9cb
Hash out soft interrupts to be a little closer to real softints:
...
* split them into levels
* allow only one per level to be active at a time
* fire softints only when we are unscheduling from a CPU instead
of immediately in softint_schedule(). this will later morph
into return from interrupt, but that part isn't done yet.
2009-11-09 19:16:18 +00:00
pooka
19cde6b50d
adjust comment for previous
2009-11-09 19:02:49 +00:00
pooka
1029997ffd
set LP_INTR for KTHREAD_INTR
2009-11-09 19:00:52 +00:00
pooka
f1be958892
Add scheduling points around the iothread call to biodone()
2009-11-09 18:00:26 +00:00
nakayama
62117cce6e
- make this compile on sparc.
...
- shrink blanks to fit in 80 columns.
2009-11-09 14:35:38 +00:00
dsl
26a8a91ded
Fix stub prototype
2009-11-07 12:08:35 +00:00
pooka
3ad682caa6
Enable kernel kmem/vmem/pool/pool_cache by default again instead
...
of malloc(3) allocators.
2009-11-06 16:16:59 +00:00
pooka
83a2f995b9
In case a temp thread is exiting, borrow lwp0 for the respective
...
kmem_free().
2009-11-06 16:15:16 +00:00
pooka
9d391c932b
account creds for processes, not lwp's
2009-11-06 15:22:33 +00:00
pooka
6abd8e3cdf
lie that we are never in a softintr (i.e. add stub)
2009-11-06 15:22:16 +00:00
pooka
f5b3a079d0
Loop over dso list while loading succeeds (brute force dependency handling).
2009-11-05 14:13:03 +00:00
pooka
2a244b850d
enqueue loaded modules and prevent duplicates
2009-11-05 14:10:53 +00:00
pooka
947f23c334
Pull all relegating memory allocators under a common roof in memalloc.c
...
(forgot to commit the new file)
2009-11-04 20:38:58 +00:00
pooka
d502da58ec
misc_stub and emul have been the same thing for a looong time now,
...
so just move the few remaining routines in misc_stub to emul.
2009-11-04 19:21:51 +00:00
pooka
c03306bc0d
Give the kthread->pthread interface emulation its own module.
2009-11-04 19:17:53 +00:00
pooka
8ec96b27ff
trim trailing whitespace
2009-11-04 18:27:40 +00:00
pooka
8ef52102c2
Pull all relegating memory allocators under a common roof in memalloc.c
2009-11-04 18:25:36 +00:00
pooka
83dbe94e8b
Implement yield()/preempt() now that there is a CPU scheduler.
2009-11-04 18:11:11 +00:00
pooka
080522e1ce
move copy-related routines to their own module
2009-11-04 17:01:45 +00:00
pooka
a69d555865
Use std. uiomove() & friends.
2009-11-04 16:55:20 +00:00
pooka
510038040b
Use kern_mutex_obj.c directly instead of copypasting code.
2009-11-04 13:32:39 +00:00
pooka
332ad24cfd
Weak aliazeize usermount_common_policy() to uncouple rumpkern
...
linkage from rumpvfs once again after the secmodel changes.
(temp solution, should find a better one)
2009-11-03 20:25:31 +00:00
pooka
652a56fde0
Reorder enough of lwp/cpu initialization to have enough context
...
for pool/kmem init to work again with the stock versions (as opposed
to rump malloc relegations).
2009-11-03 20:22:33 +00:00
pooka
341072b737
move module to SRCS where it logically belongs. no functional change.
2009-11-03 18:44:15 +00:00
pooka
2a63153751
regen: add AB_* macros
2009-11-03 18:23:15 +00:00
pooka
ef8c3e068e
include AB_* macros from reboot.h
2009-11-03 18:22:44 +00:00
pooka
b32585a644
Add rump_boot_set/gethowto(), which can be called before rump_init()
...
to control .... *tadaa* boothowto.
2009-11-03 18:22:16 +00:00
pooka
99e178a1c1
Pass modinit to rumpuser_dl_module_bootstrap() as a function pointer
...
to avoid linker rump -> rumpuser -> rump dependency which is annoying
redundancy in static linking.
2009-10-24 11:36:59 +00:00
pooka
c9f53946a5
unused rumpuser_realpath is really dead
2009-10-24 11:29:55 +00:00
rmind
10758cb0f9
Simplify pmap_remove() a little by avoiding pmap_do_remove() layer, since
...
possibility to skip wired mappings is not needed anymore. Apart from that,
no functional differences are intended.
2009-10-22 19:50:55 +00:00
rmind
3e88e8e75c
Sync rump with kernel changes.
2009-10-21 23:13:53 +00:00
rmind
40cf6f3659
Remove uarea swap-out functionality:
...
- Addresses the issue described in PR/38828.
- Some simplification in threading and sleepq subsystems.
- Eliminates pmap_collect() and, as a side note, allows pmap optimisations.
- Eliminates XS_CTL_DATA_ONSTACK in scsipi code.
- Avoids few scans on LWP list and thus potentially long holds of proc_lock.
- Cuts ~1.5k lines of code. Reduces amd64 kernel size by ~4k.
- Removes __SWAP_BROKEN cases.
Tested on x86, mips, acorn32 (thanks <mpumford>) and partly tested on
acorn26 (thanks to <bjh21>).
Discussed on <tech-kern>, reviewed by <ad>.
2009-10-21 21:11:57 +00:00
pooka
5a1b660dab
use autogenerated prototype
2009-10-20 23:29:57 +00:00
pooka
b762b305fb
regen
2009-10-20 23:29:39 +00:00
pooka
693ea25ed2
add shmif_create
2009-10-20 23:28:50 +00:00
pooka
17e6aa2d7b
printf -> rumpuser_dprintf
...
(can't use printf while holding spinlock)
2009-10-20 23:21:53 +00:00
tron
3ad0ebd5a8
Only allocate a "struct iovec" array from the healp if a reasonably sized
...
stack array isn't large enough.
2009-10-20 12:17:44 +00:00
pooka
0d29473b2c
Actually, put uvm_readahead into rumpkern, since while it's
...
technically vfs stuff, sys_descrip depends on it and readahead
itself uses only the pager interface.
2009-10-20 10:42:41 +00:00
pooka
02a39de4a7
fix sign-compare warnings
2009-10-20 00:25:26 +00:00
pooka
fe208f2f7a
__weak_alias for uvm_readahead() since it's used also in sys_descrip.c
2009-10-19 22:35:11 +00:00
pooka
639268f462
remove stale uvm_readahead() stub
2009-10-19 22:31:47 +00:00
christos
32ec2634aa
treat sun2 like the other losing platforms.
2009-10-19 22:07:29 +00:00
pooka
c8d929f4fb
add Arnaud's EuroBSDCon paper
2009-10-19 14:43:46 +00:00
tron
8cd44ca832
Avoid panic if a file system tries to write a chain of more than 32 mbuf-s
...
to a socket. This happens e.g. when copying large files to SMBFS.
Code reviewed by Antti Kantee.
2009-10-18 22:55:56 +00:00
pooka
9646a920b0
Clear PG_FAKE for pages we wrote to. This avoids paging in data
...
we already have (and the backend might not yet have) in cases where
fs_bshift > PAGE_SHIFT.
2009-10-18 00:41:09 +00:00
pooka
a6085c2236
fix off-by-one in sanity check and bump lazy bum magic value
2009-10-17 20:35:52 +00:00
pooka
291f141ce9
for udp sockets crank snd/rcvbufsize to 64k
2009-10-16 23:17:46 +00:00
pooka
afa1f603b7
In case of timeout, remember to remove ourselves from the sleep staleq.
2009-10-16 02:13:54 +00:00
pooka
d0c17feb81
We have real pollsuck() now, so remove this, ahem, less-than-perfect one.
...
(XXX: only thing in the kernel using pollsuck is netsmb)
2009-10-16 00:16:32 +00:00
pooka
254ffabc38
Include sys_select.c for proper select()/poll() support.
2009-10-16 00:14:53 +00:00
pooka
cc056ae92c
include rumpcpu_generic
2009-10-15 23:42:40 +00:00
pooka
2f6e67dfd6
When allocating the temporary lwp we must have an lwp context. So
...
take turns using lwp0 for this purpose, nothing else uses it.
2009-10-15 23:15:55 +00:00
pooka
cfc0373f49
rump_get_curlwp() is dead
2009-10-15 16:46:37 +00:00
pooka
c663ed2f3f
regen: lwp interface changes
2009-10-15 16:40:15 +00:00
pooka
8559951571
Give lwp usage some much-needed love: stop treating lwp0 as the
...
all-sink and make sure each separate thread in rump has its own
lwp. Happy-go-lucky callers will get scheduled a temporary lwp
on entry, while true lwp connoisseurs may request a stable lwp
for their purposes. Some more love may be required later down the
road, but for now different threads will stepping on each others
toes.
2009-10-15 16:39:22 +00:00
pooka
5a586117cf
fix previous to make sense
2009-10-15 01:50:08 +00:00
pooka
466e9bcfec
adjust for new rump_cpu
2009-10-15 01:35:23 +00:00
pooka
8c6bd3376a
forgot to commit with previous batch
2009-10-15 01:29:06 +00:00
pooka
9bb1dbd8d7
rump_cpu is now a pointer
2009-10-15 00:34:05 +00:00
pooka
fcebdb26e0
Add prototype for wait operation variants which do not drop any
...
resources (because they should be holding any in the first place).
2009-10-15 00:33:37 +00:00
pooka
f1f3f36233
regen: scheduling points
2009-10-15 00:32:11 +00:00
pooka
000a197343
regen: scheduling points in rump_pub wrappers
2009-10-15 00:31:25 +00:00
pooka
cd231d0604
Generate scheduling points in rump_pub calls.
2009-10-15 00:29:19 +00:00
pooka
9454f185c4
Add initial work on a rump virtual cpu scheduler. This is necessary
...
for kernel code which has been written to avoid MP contention by
using cpu-local storage (most prominently, select and pool_cache).
Instead of always assuming rump_cpu, the scheduler must now be run
(and unrun) on all entry points into rump. Likewise, rumpuser
unruns and re-runs the scheduler around each potentially blocking
operation. As an optimization, I modified some locking primitives
to try to get the lock without blocking before releasing the cpu.
Also, ltsleep was modified to assume that it is never called without
the biglock held and made to use the biglock as the sleep interlock.
Otherwise there is just too much drama with deadlocks. If some
kernel code wants to call ltsleep without the biglock, then, *snif*,
it's no longer supported and rump and should be modified to support
newstyle locks anyway.
2009-10-15 00:28:46 +00:00
pooka
36f718311e
whoops, restore probing of ugen{0..3} instead of just ugen2
2009-10-14 23:29:42 +00:00
pooka
a9cd93a788
use rump_pub
2009-10-14 19:14:39 +00:00
pooka
d09e2773d0
"rumppriv" goes back to "rump" per internal interface naming change.
2009-10-14 18:18:53 +00:00
pooka
a6f92a2b8f
regen: put all public interfaces created by ifspec into a rump_pub namespace
2009-10-14 18:16:41 +00:00
pooka
abf164854c
Actually, adjust previous a bit: instead of preserving the names
...
of the external interfaces and namespacing the internal ones to
"rumppriv", put the external ones in a "rump_pub" namespace. While
this requires adjusting all of the external callers of these
interfaces, it is the right thing to do in the long run, since it
clarifies the structure.
2009-10-14 18:14:48 +00:00
pooka
aa022ebd2b
This wasn't supposed to go in -- the tree is under temporary
...
component boundary breakage.
2009-10-14 17:34:08 +00:00
pooka
8ca7f09f6e
g/c some stuff which wasn't supposed to see the light of day
2009-10-14 17:30:52 +00:00
pooka
42972db848
Adjust rump sources for external/internal interfaces.
...
No functional change.
2009-10-14 17:29:19 +00:00
pooka
796b2444f2
generate rump local interfaces
2009-10-14 17:28:13 +00:00
pooka
c1bfb8966b
adjust whitespace a bit
2009-10-14 17:26:09 +00:00
pooka
f2c144d595
Create rump public interfaces from description tables. This allows
...
us to control and wrap all entry points from "userspace" into rump.
This in turn is necessary for the upcoming rump cpu scheduler.
For each interface "foo" a public wrapper called "rump_foo" is
created. It calls the internal implementation "rumppriv_foo". In
case foo is to be called from inside of rump kernel space, the
private interface "rumppriv_foo" is used -- the userspace wrapper
prototypes are not even exported into the rump kernel namespace.
Needless to say, the rump kernel internal interfaces are not exported
for users.
Now, three classes of interfaces fight for control of rump:
+ the noble local control interfaces (which this commit addresses)
+ the insidious rump system calls (which are generated from syscalls.master)
+ and the evil vnode interfaces (which are generated from vnode_if.src)
2009-10-14 17:17:00 +00:00
pooka
ddc943db02
regen: fix rump varargs syscalls prototypes
2009-10-13 21:57:52 +00:00
pooka
5ac5a300e2
don't define curlwp, it's just (unused) sugar
2009-10-13 20:08:08 +00:00
pooka
b7f550b683
add one more passthrough
2009-10-13 18:36:48 +00:00
pooka
c8c66517fe
Bump iovec lazy bum magic value to 32: nfsd likes to write mbufs
...
with 17 per chain (previous i'm-too-lazy-for-my-forloop value was
of course 16).
2009-10-12 02:25:44 +00:00
pooka
8ac0fe74d9
add recvmsg and sendmsg to networking rump syscalls
2009-10-11 23:23:09 +00:00
pooka
7e9bd843aa
Include host offset in regular etfs read/write operations (I can't
...
imagine it being particularly useful, but let's call file this
under POLA).
2009-10-11 18:12:51 +00:00
pooka
860f5d7238
Support creating file system sockets (non-sockets not supported in
...
VOP_CREATE since I don't want to have to write read/write support
for non-etfs files).
2009-10-11 17:54:22 +00:00
pooka
fed1ab4ee0
raidframe works well enough now to initialize parity, so install it.
2009-10-11 11:26:40 +00:00
pooka
8d38112c32
add some stubs required by raidframe linkage
2009-10-10 21:10:04 +00:00
pooka
d4069e2c5e
Provide an interface for reboot.
2009-10-09 14:41:36 +00:00
pooka
d3da4377ca
regen
2009-10-09 14:32:07 +00:00
pooka
4dd39169ff
namespace RB_ from reboot.h
2009-10-09 14:31:47 +00:00
pooka
0111b794da
Seems like module loading code is tasked with calling secmodel_register()
...
these days ...
2009-10-08 00:47:47 +00:00
pooka
b15be8fcc2
remove extraneous call to secmodel_suser_start()
2009-10-08 00:36:56 +00:00
pooka
4ecb17968a
dlclose() in error branch
2009-10-08 00:34:54 +00:00
pooka
366ae82927
Use uvm_readahead.c instead of null stubs.
2009-10-07 10:23:50 +00:00