Commit graph

3337 commits

Author SHA1 Message Date
Tom
766db673c1 Kernel: Flush TLBs concurrently
Instead of flushing the TLB on the current processor first and then
notifying the other processors to do the same, notify the others
first, and while waiting on the others flush our own.
2020-12-02 23:49:52 +01:00
Tom
5e08ae4e14 Kernel: Fix counting interrupts
Move counting interrupts out of the handle_interrupt method so that
it is done in all cases without the interrupt handler having to
implement it explicitly.

Also make the counter an atomic value as e.g. the LocalAPIC interrupts
may be triggered on multiple processors simultaneously.

Fixes #4297
2020-12-02 23:19:59 +01:00
Tom
12cf6f8650 Kernel: Add CLOCK_REALTIME support to the TimerQueue
This allows us to use blocking timeouts with either monotonic or
real time for all blockers. Which means that clock_nanosleep()
now also supports CLOCK_REALTIME.

Also, switch alarm() to use CLOCK_REALTIME as per specification.
2020-12-02 13:02:04 +01:00
Tom
4c1e27ec65 Kernel: Use TimerQueue for SIGALRM 2020-12-02 13:02:04 +01:00
Tom
601a688b6f Kernel: TimerQueue::cancel_timer needs to wait if timer is executing
We need to be able to guarantee that a timer won't be executing after
TimerQueue::cancel_timer returns. In the case of multiple processors
this means that we may need to wait while the timer handler finishes
execution on another core.

This also fixes a problem in Thread::block and Thread::wait_on where
theoretically the timer could execute after the function returned
and the Thread disappeared.
2020-12-02 13:02:04 +01:00
Tom
1f86d88dc4 Kernel: Don't assert if we can't deliver a signal due to thread state
Fixes an assertion found in #3990
2020-12-01 16:09:15 +01:00
Ben Wiederhake
2b3113cd2a Meta: Fix ACPI_DEBUG, and always build on CI 2020-12-01 11:06:53 +01:00
Andrew Kaster
3f808b0dda LibELF+Kernel: Validate program headers in Image::parse
This should catch more malformed ELF files earlier than simply
checking the ELF header alone. Also change the API of
validate_program_headers to take the interpreter_path by pointer. This
makes it less awkward to call when we don't care about the interpreter,
and just want the validation.
2020-12-01 09:58:21 +01:00
Tom
78f1b5e359 Kernel: Fix some problems with Thread::wait_on and Lock
This changes the Thread::wait_on function to not enable interrupts
upon leaving, which caused some problems with page fault handlers
and in other situations. It may now be called from critical
sections, with interrupts enabled or disabled, and returns to the
same state.

This also requires some fixes to Lock. To aid debugging, a new
define LOCK_DEBUG is added that enables checking for Lock leaks
upon finalization of a Thread.
2020-12-01 09:48:34 +01:00
Tom
9e32d79e02 Kernel: Fix leaking a reference on thread creation
New Thread objects should be adopted into a RefPtr upon creation.
If creating a thread failed (e.g. out of memory), releasing the RefPtr
will destruct the partially created object, but in the successful case
the thread will add an additional reference that it keeps until it
finishes execution. Adopting will drop it to 1 when returning from
create_thread, or 0 if the thread could not be fully constructed.
2020-12-01 09:26:37 +01:00
Tom
3bda458735 Kernel: Lock should keep a reference to whoever holds the lock
Fixes a crash reported in #3990
2020-11-30 13:17:02 +01:00
Tom
046d6855f5 Kernel: Move block condition evaluation out of the Scheduler
This makes the Scheduler a lot leaner by not having to evaluate
block conditions every time it is invoked. Instead evaluate them as
the states change, and unblock threads at that point.

This also implements some more waitid/waitpid/wait features and
behavior. For example, WUNTRACED and WNOWAIT are now supported. And
wait will now not return EINTR when SIGCHLD is delivered at the
same time.
2020-11-30 13:17:02 +01:00
Tom
6a620562cc Kernel: Allow passing a thread argument for new kernel threads
This adds the ability to pass a pointer to kernel thread/process.
Also add the ability to use a closure as thread function, which
allows passing information to a kernel thread more easily.
2020-11-30 13:17:02 +01:00
Tom
6cb640eeba Kernel: Move some time related code from Scheduler into TimeManagement
Use the TimerQueue to expire blocking operations, which is one less thing
the Scheduler needs to check on every iteration.

Also, add a BlockTimeout class that will automatically handle relative or
absolute timeouts as well as overriding timeouts (e.g. socket timeouts)
more consistently.

Also, rework the TimerQueue class to be able to fire events from
any processor, which requires Timer to be RefCounted. Also allow
creating id-less timers for use by blocking operations.
2020-11-30 13:17:02 +01:00
Luke
72abf3491b LibCrypto: Require intent parameter in CTR constructor
This was preventing clang from building.
2020-11-29 20:22:56 +01:00
Tom
2b78b17926 Kernel: Enable VMWareBackdoor immediately at boot
Rather than waiting until we get the first mouse packet, enable the
absolute mode immediately. This avoids having to click first to be
able to move the mouse.
2020-11-26 10:00:01 +01:00
Andreas Kling
76308c2e1f Kernel: Reduce ByteBuffer thrashing in inode block list generation
Instead of creating and destroying a new ByteBuffer for every block we
process during block list generation, just use stack memory instead.
2020-11-24 21:29:08 +01:00
Tom
68abd1cb29 Kernel: Fix SharedBuffer reference counting on fork
We need to not only add a record for a reference, but we need
to copy the reference count on fork as well, because the code
in the fork assumes that it has the same amount of references,
still.

Also, once all references are dropped when a process is disowned,
delete the shared buffer.

Fixes #4076
2020-11-24 21:26:39 +01:00
Andreas Kling
5f2f31861c Kernel: Use a doubly-linked list for the BlockBasedFS cache
This makes misses in the BlockBasedFS's LRU block cache faster by
storing the cache entries in one of two doubly-linked list.

Dirty and clean cache entries are kept in two separate lists, and
move between them when their state changes. This can probably be
improved upon further.
2020-11-24 16:42:01 +01:00
Andreas Kling
3e3a72f2a2 Ext2FS: Oops, fix forgotten assignment in Ext2FSInode::resize()
If the inode's block list cache is empty, we forgot to assign the
result of computing the block list. The fact that this worked anyway
makes me wonder when we actually don't have a cache..

Thanks to szyszkienty for spotting this! :^)
2020-11-24 16:16:09 +01:00
Andreas Kling
a6a3c20071 Kernel: Add a fast lookup table to the BlockBasedFS disk cache
Instead of doing a linear scan of the entire cache when doing a lookup,
we now have a nice O(1) HashMap in front of the cache.

The cache miss case can still be improved, this patch really only helps
the cache hit case.

This dramatically improves cached filesystem I/O. :^)
2020-11-24 13:40:54 +01:00
Andreas Kling
20205708b9 Ext2FS: Use cached inode block list in resize() if available
If we have already cached the block list of an Ext2FSInode, we can save
a lot of time by not regenerating it.
2020-11-24 13:40:45 +01:00
Andreas Kling
541579bc04 Kernel: Remove unnecessary SmapDisablers in FileDescription
Since we're using UserOrKernelBuffers, SMAP will be automatically
disabled when we actually access the buffer later on. There's no need
to disable it wholesale across the entire read/write operations.
2020-11-24 11:26:40 +01:00
Sergey Bugaev
098070b767 Kernel: Add unveil('b')
This is a new "browse" permission that lets you open (and subsequently list
contents of) directories underneath the path, but not regular files or any other
types of files.
2020-11-23 18:37:40 +01:00
Tom
97b3035c14 Kernel: Don't resume thread into Running state directly on SIGCONT
We should never resume a thread by directly setting it to Running state.
Instead, if a thread was in Running state when stopped, record the state
as Runnable.

Fixes #4150
2020-11-23 18:33:19 +01:00
Andreas Kling
dfce9051fa ProcFS: Take the "all inodes" lock when generating /proc/inodes
Otherwise the kernel asserts.
2020-11-23 16:19:30 +01:00
Andreas Kling
086522537e Kernel: Don't leak ref on executable inode in sys$execve()
We were leaking a ref on the executed inode in successful calls to
sys$execve(). This meant that once a binary had ever been executed,
it was impossible to remove it from the file system.

The execve system call is particularly finicky since the function
does not return normally on success, so extra care must be taken to
ensure nothing is kept alive by stack variables.

There is a big NOTE comment about this, and yet the bug still got in.
It would be nice to enforce this, but I'm unsure how.
2020-11-23 16:08:42 +01:00
Andreas Kling
bb9c705fc2 Ext2FS: Move some EXT2_DEBUG logging behind EXT2_VERY_DEBUG
This makes the build actually somewhat usable with EXT2_DEBUG. :^)
2020-11-23 16:08:42 +01:00
Andreas Kling
1951dfa46a Kernel: Convert dbg() to dbgln() in Syscall.cpp 2020-11-23 16:08:42 +01:00
Andreas Kling
df758a5a51 Ext2FS: Clear out the direct block list when an inode is resized to 0
e2fsck was complaining about blocks being allocated in an inode's list
of direct blocks while at the same time being free in the block bitmap.

It was easy to reproduce by creating a file with non-zero length and
then truncating it. This fixes the issue by clearing out the direct
block list when resizing a file to 0.
2020-11-23 14:08:50 +01:00
Tom
a89648e159 Kernel: Inherit shared buffers when forking
We need to create a reference for the new PID for each shared buffer
that the process had a reference to. If the process subsequently
get replaced through exec, those references will be dropped again.
But if exec for some reason fails then other code, such as global
destructors could still expect having access to them.

Fixes #4076
2020-11-23 09:39:32 +01:00
Andreas Kling
94ff04b536 Kernel: Make CLOCK_MONOTONIC respect the system tick frequency
The time returned by sys$clock_gettime() was not aligned with the delay
calculations in sys$clock_nanosleep(). This patch fixes that by taking
the system's ticks_per_second value into account in both functions.

This patch also removes the need for Thread::sleep_until() and uses
Thread::sleep() for both absolute and relative sleeps.

This was causing the nesalizer emulator port to sleep for a negative
amount of time at the end of each frame, making it run way too fast.
2020-11-22 17:20:58 +01:00
Lenny Maiorani
bdf3baa8ac MACAddress: AK::Array as member variable instead of C-array
Problem:
- C-style arrays do not automatically provide bounds checking and are
  less type safe overall.
- `__builtin_memcmp` is not a constant expression in the current gcc.

Solution:
- Change private m_data to be AK::Array.
- Eliminate constructor from C-style array.
- Change users of the C-style array constructor to use the default
  constructor.
- Change `operator==()` to be a hand-written comparison loop and let
  the optimizer figure out to use `memcmp`.
2020-11-20 21:18:14 +01:00
Tom
53cffb5ad9 Kernel: Fix mouse lag when VMWareBackdoor absolute mode is enabled
We won't be receiving full PS/2 mouse packets when the VMWareBackdoor
absolute mouse mode is enabled. So, read just one byte every time
and retrieve the latest mouse packet from VMWareBackdoor immediately.

Fixes #4086
2020-11-14 22:09:48 +01:00
Tom
13383f3267 Revert "Kernel: Keep reading from i8042 until the buffer is empty"
This reverts commit 467f6c74a4.
2020-11-14 22:09:48 +01:00
Andreas Kling
467f6c74a4 Kernel: Keep reading from i8042 until the buffer is empty
Otherwise we might not drain the mouse buffer until the next IRQ.
2020-11-14 17:20:17 +01:00
Andreas Kling
abe9cec612 TmpFS: Set the root inode's timestamp to the current time
cc @bcoles :^)
2020-11-14 10:44:47 +01:00
Tom
e445ff670d Kernel: Implement an asynchronous device request stack
This allows issuing asynchronous requests for devices and waiting
on the completion of the request. The requests can cascade into
multiple sub-requests.

Since IRQs may complete at any time, if the current process is no
longer the same that started the process, we need to swich the
paging context before accessing user buffers.

Change the PATA driver to use this model.
2020-11-12 18:04:30 +01:00
Tom
91db31880f Kernel: Add I8042Controller to detect and manage PS/2 devices
Rework the PS/2 keyboard and mouse drivers to use a common 8042
controller driver. Also, reset and reconfigure the 8042 controller
as they are not guaranteed to be in the state that we expect.
2020-11-12 18:04:16 +01:00
Tom
e1c27c16d8 Kernel: Assume 8042 controller is present if ACPI FADT revision <= 1
This field wasn't specified until revision 2 and should be assumed to
be set on older versions.
2020-11-12 18:04:16 +01:00
Tom
6b97118e89 Kernel: Fix race during thread destruction if it is preempted
This fixes a lot of crashes in Bochs, which is more likely to
preempt thread destruction.
2020-11-12 10:18:16 +01:00
Tom
dc9ddf8104 Kernel: Fix deadlock when unicasting/broadcasting SMP message
When two processors send each others a SMP message at the same time
they need to process messages while waiting for delivery of the
message they just sent, or they will deadlock.
2020-11-11 12:27:25 +01:00
Tom
3ee7c21fae Kernel: Implement capturing stack trace on a different CPU
When trying to get a stack trace of a thread on another CPU we send
a SMP message to that processor to capture the stack trace for us.
2020-11-11 12:27:25 +01:00
Tom
5b38132e3c Kernel: Protect the PageDirectory from concurrent access 2020-11-11 12:27:25 +01:00
Tom
2b25a89ab5 Kernel: Add locks around RangeAllocator
We need to keep multiple processors from changing it at the same time.
2020-11-11 12:27:25 +01:00
Tom
66f46d03e4 Kernel: Minor Lock optimization 2020-11-11 12:27:25 +01:00
Tom
b4c9e85056 Kernel: Minor SpinLock improvements 2020-11-11 12:27:25 +01:00
Tom
e26e0445b5 Kernel: Make m_halt_requested an atomic variable
We need to make sure the change to this variable is visible to all
processors instantly.
2020-11-11 12:27:25 +01:00
Tom
a14884dd33 Kernel: Lock needs to call Processor::wait_check while looping
We need to process SMP messages while looping.
2020-11-11 12:27:25 +01:00
Tom
75f61fe3d9 AK: Make RefPtr, NonnullRefPtr, WeakPtr thread safe
This makes most operations thread safe, especially so that they
can safely be used in the Kernel. This includes obtaining a strong
reference from a weak reference, which now requires an explicit
call to WeakPtr::strong_ref(). Another major change is that
Weakable::make_weak_ref() may require the explicit target type.
Previously we used reinterpret_cast in WeakPtr, assuming that it
can be properly converted. But WeakPtr does not necessarily have
the knowledge to be able to do this. Instead, we now ask the class
itself to deliver a WeakPtr to the type that we want.

Also, WeakLink is no longer specific to a target type. The reason
for this is that we want to be able to safely convert e.g. WeakPtr<T>
to WeakPtr<U>, and before this we just reinterpret_cast the internal
WeakLink<T> to WeakLink<U>, which is a bold assumption that it would
actually produce the correct code. Instead, WeakLink now operates
on just a raw pointer and we only make those constructors/operators
available if we can verify that it can be safely cast.

In order to guarantee thread safety, we now use the least significant
bit in the pointer for locking purposes. This also means that only
properly aligned pointers can be used.
2020-11-10 19:11:52 +01:00