summaryrefslogtreecommitdiff
path: root/Kernel/Scheduler.cpp
AgeCommit message (Collapse)Author
2019-11-14Kernel: Move Thread::m_joinee_exit_value into the JoinBlockerAndreas Kling
There's no need for this to be a permanent Thread member. Just use a reference in the JoinBlocker instead.
2019-11-14Kernel+LibPthread: Implement pthread_join()Andreas Kling
It's now possible to block until another thread in the same process has exited. We can also retrieve its exit value, which is whatever value it passed to pthread_exit(). :^)
2019-11-06Kernel: Rework Process::Priority into ThreadPriorityAndreas Kling
Scheduling priority is now set at the thread level instead of at the process level. This is a step towards allowing processes to set different priorities for threads. There's no userspace API for that yet, since only the main thread's priority is affected by sched_setparam().
2019-10-07Kernel: Add exception_code to RegisterDump.Drew Stratford
Added the exception_code field to RegisterDump, removing the need for RegisterDumpWithExceptionCode. To accomplish this, I had to push a dummy exception code during some interrupt entries to properly pad out the RegisterDump. Note that we also needed to change some code in sys$sigreturn to deal with the new RegisterDump layout.
2019-10-02Kernel: Don't update Thread TSS if scheduler tick reschedules itAndreas Kling
If we didn't find anything else that wants to run, we don't need to update the current thread's TSS since we're just gonna return to the same thread anyway.
2019-09-14Kernel: Stop idling after handling an IRQAndreas Kling
If we receive an IRQ while the idle task is running, prevent it from re-halting the CPU after the IRQ handler returns. Instead have the idle task yield to the scheduler, so we can see if the IRQ has unblocked something.
2019-09-09Kernel: Change m_blockers to m_blocker.Drew Stratford
Because of the way signals now work there should not be more than one blocker per thread. This changes the blocker and thread class to reflect that.
2019-09-08Kernel: waitpid() should unblock and -ECHILD if SIG_IGN reaps childAndreas Kling
2019-09-07Kernel: Support thread-local storageAndreas Kling
This patch adds support for TLS according to the x86 System V ABI. Each thread gets a thread-specific memory region, and the GS segment register always points _to a pointer_ to the thread-specific memory. In other words, to access thread-local variables, userspace programs start by dereferencing the pointer at [gs:0]. The Process keeps a master copy of the TLS segment that new threads should use, and when a new thread is created, they get a copy of it. It's basically whatever the PT_TLS program header in the ELF says.
2019-08-10Kernel: Use a more detailed state machine for socket setupConrad Pankoff
2019-08-07Kernel: Don't create Function objects in the scheduling codeAndreas Kling
Each Function is a heap allocation, so let's make an effort to avoid doing that during scheduling. Because of header dependencies, I had to put the runnables iteration helpers in Thread.h, which is a bit meh but at least this cuts out all the kmalloc() traffic in pick_next().
2019-08-01Scheduler: Fix bitrotted SCHEDULER_RUNNABLE_DEBUG codeAndreas Kling
The runnable lists have moved from Thread to Scheduler.
2019-08-01Scheduler: Fix deadlock when first scheduling candidate being inspectedAndreas Kling
Somewhat reproducible by opening ProcessManager and trying to view the stacks for WindowServer. Regressed in 53262cd08b08f3d4d2b77cff9c348e84b1bf5eb9.
2019-07-22Move runnable/non-runnable list control entirely over to SchedulerRobin Burchell
This way, we can change how the scheduler works without having to change Thread too.
2019-07-21Scheduler: Allow reentry into block()Robin Burchell
With the presence of signal handlers, it is possible that a thread might be blocked multiple times. Picture for instance a signal handler using read(), or wait() while the thread is already blocked elsewhere before the handler is invoked. To fix this, we turn m_blocker into a chain of handlers. Each block() call now prepends to the list, and unblocking will only consider the most recent (first) blocker in the chain. Fixes #309
2019-07-20Thread: Cleanup m_blocker handlingRobin Burchell
The only two places we set m_blocker now are Thread::set_state(), and Thread::block(). set_state is mostly just an issue of clarity: we don't want to end up with state() != Blocked with an m_blocker, because that's weird. It's also possible: if we yield, someone else may set_state() us. We also now set_state() and set m_blocker under lock in block(), rather than unlocking which might allow someone else to mess with our internals while we're in the process of trying to block. This seems to fix sending STOP & CONT causing a panic. My guess as to what was happening is this: thread A blocks in select(): Blocking & m_blocker != nullptr thread B sends SIGSTOP: Stopped & m_blocker != nullptr thread B sends SIGCONT: we continue execution. Runnable & m_blocker != nullptr thread A tries to block in select() again: * sets m_blocker * unlocks (in block_helper) * someone else tries to unblock us? maybe from the old m_blocker? unclear -- clears m_blocker * sets Blocked (while unlocked!) So, thread A is left with state Blocked & m_blocker == nullptr, leading to the scheduler assert (m_blocker != nullptr) failing. Long story short, let's do all our data management with the lock _held_.
2019-07-20Thread: Return a result from block() indicating why the block terminatedRobin Burchell
And use this to return EINTR in various places; some of which we were not handling properly before. This might expose a few bugs in userspace, but should be more compatible with other POSIX systems, and is certainly a little cleaner.
2019-07-19AK: Introduce IntrusiveListRobin Burchell
And use it in the scheduler. IntrusiveList is similar to InlineLinkedList, except that rather than making assertions about the type (and requiring inheritance), it provides an IntrusiveListNode type that can be used to put an instance into many different lists at once. As a proof of concept, port the scheduler over to use it. The only downside here is that the "list" global needs to know the position of the IntrusiveListNode member, so we have to position things a little awkwardly to make that happen. We also move the runnable lists to Thread, to avoid having to publicize the node.
2019-07-19Kernel: Some small refinements to the thread blockers.Andreas Kling
Committing some things my hands did while browsing through this code. - Mark all leaf classes "final". - FileDescriptionBlocker now stores a NonnullRefPtr<FileDescription>. - FileDescriptionBlocker::blocked_description() now returns a reference. - ConditionBlocker takes a Function&&.
2019-07-19Scheduler: Remove some raw use of the runnable listsRobin Burchell
2019-07-19Thread: Normalize all for_each constructs to use IterationDecisionRobin Burchell
This way a caller can abort the for_each early if they want.
2019-07-19Kernel: Restore state strings for block statesRobin Burchell
"Blocking" is not terribly informative, but now that everything is ported over, we can force the blocker to provide us with a reason. This does mean that to_string(State) needed to become a member, but that's OK.
2019-07-19Kernel: Rename Condition state to Blocked now we only have one blocking ↵Robin Burchell
mechanism :)
2019-07-19Kernel: Convert BlockedSignal and BlockedLurking to the new Blocker mechanismRobin Burchell
The last two of the old block states gone :)
2019-07-19Kernel: Avoid allocations for Select vectors by using inline capacityRobin Burchell
Good tip by Andreas :)
2019-07-19Kernel: Rename ThreadBlocker classes to avoid stutterRobin Burchell
Thread::ThreadBlockerFoo is a lot less nice to read than Thread::FooBlocker
2019-07-19Kernel: Port wait to ThreadBlockerRobin Burchell
2019-07-19Kernel: Port select to ThreadBlockerRobin Burchell
2019-07-19Kernel: Port sleep to ThreadBlockerRobin Burchell
2019-07-19Kernel: Introduce ThreadBlocker as a way to make unblocking neater :)Robin Burchell
And port all the descriptor-based blocks over to it as a proof of concept.
2019-07-18Scheduler: Move thread unblocking out of a lambda to help make things more ↵Robin Burchell
readable We also use a switch to explicitly make sure we handle all cases properly.
2019-07-18Kernel: Add a new block state for accept() on a blocking socketRobin Burchell
Rather than asserting, which really ruins everyone's day.
2019-07-17Kernel: Split SCHEDULER_DEBUG into a new SCHEDULER_RUNNABLE_DEBUGRobin Burchell
And use dbgprintf() consistently on a few of the pieces of logging here. This is useful when trying to track thread switching when you don't really care about what it's switching _to_.
2019-07-14Kernel: Add Thread::block_until(Condition).Andreas Kling
Replace the class-based snooze alarm mechanism with a per-thread callback. This makes it easy to block the current thread on an arbitrary condition: void SomeDevice::wait_for_irq() { m_interrupted = false; current->block_until([this] { return m_interrupted; }); } void SomeDevice::handle_irq() { m_interrupted = true; } Use this in the SB16 driver, and in NetworkTask :^)
2019-07-14Kernel: Add support for the WSTOPPED flag to the waitpid() syscall.Andreas Kling
This makes waitpid() return when a child process is stopped via a signal. Use this in Shell to catch stopped children and return control to the command line. :^) Fixes #298.
2019-07-09Kernel: Move i8253.cpp => Arch/i386/PIT.cppAndreas Kling
2019-07-03AK: Rename the common integer typedefs to make it obvious what they are.Andreas Kling
These types can be picked up by including <AK/Types.h>: * u8, u16, u32, u64 (unsigned) * i8, i16, i32, i64 (signed)
2019-06-22printf: Oops, '-' is the left padding modifier, not ' '.Andreas Kling
It's kinda funny how I can make a mistake like this in Serenity and then get so used to it by spending lots of time using this API that I start to believe that this is how printf() always worked..
2019-06-13Kernel: Rename "descriptor" to "description" where appropriate.Andreas Kling
Now that FileDescription is called that, variables of that type should not be called "descriptor". This is kinda wordy but we'll get used to it.
2019-06-07Kernel: Qualify a bunch of #include statements.Andreas Kling
2019-06-07Kernel: Run clang-format on everything.Andreas Kling
2019-06-07Kernel: Implement the alarm() syscall.Andreas Kling
2019-06-07Kernel: Rename FileDescriptor to FileDescription.Andreas Kling
After reading a bunch of POSIX specs, I've learned that a file descriptor is the number that refers to a file description, not the description itself. So this patch renames FileDescriptor to FileDescription, and Process now has FileDescription* file_description(int fd).
2019-05-20Kernel: Add support for recv() with MSG_DONTWAIT.Andreas Kling
Passing this flag to recv() temporarily puts the file descriptor into non-blocking mode. Also implement LocalSocket::recv() as a simple forwarding to read().
2019-05-18Kernel: Make sure we never put the colonel thread in the runnable list.Andreas Kling
This would cause it to get scheduled unnecessarily.
2019-05-18Kernel: Refactor thread scheduling a bit, breaking it into multiple lists.Andreas Kling
There are now two thread lists, one for runnable threads and one for non- runnable threads. Thread::set_state() is responsible for moving threads between the lists. Each thread also has a back-pointer to the list it's currently in.
2019-05-15Kernel: Add a beep() syscall that beeps the PC speaker.Andreas Kling
Hook this up in Terminal so that the '\a' character generates a beep. Finally emit an '\a' character in the shell line editing code when backspacing at the start of the line.
2019-05-03Kernel: Prepare Socket for becoming a File.Andreas Kling
Make the Socket functions take a FileDescriptor& rather than a socket role throughout the code. Also change threads to block on a FileDescriptor, rather than either an fd index or a Socket.
2019-04-29Kernel: Have File virtuals take a FileDescriptor& rather than a Process&.Andreas Kling
This will allow us to implement different behaviors depending on the role of the descriptor a File is being accessed through.
2019-04-29Kernel: Make FIFO inherit from File.Andreas Kling