kernel: msg: async messages no longer hold a pointer to the thread/port that sent them

this prevents a race condition where an event is sent as a port is being destroyed.
when the server gets around to handling the event, it now refers to a different port
that was created in the mean-time.
This commit is contained in:
2026-03-25 20:19:19 +00:00
parent a0a6a061a4
commit 95d33ddcb9
3 changed files with 22 additions and 9 deletions
+12
View File
@@ -21,8 +21,20 @@ struct msg {
enum kmsg_status msg_status; enum kmsg_status msg_status;
struct btree_node msg_node; struct btree_node msg_node;
msgid_t msg_id; msgid_t msg_id;
union {
/* only valid for asynchronous messages (msg_status ==
* KMSG_ASYNC) */
struct {
koid_t msg_sender_port_id;
tid_t msg_sender_thread_id;
};
/* only valid for synchronous messages (msg_status !=
* KMSG_ASYNC) */
struct {
struct port *msg_sender_port; struct port *msg_sender_port;
struct thread *msg_sender_thread; struct thread *msg_sender_thread;
};
};
kern_status_t msg_result; kern_status_t msg_result;
kern_msg_type_t msg_type; kern_msg_type_t msg_type;
+4 -3
View File
@@ -2,6 +2,7 @@
#include <kernel/channel.h> #include <kernel/channel.h>
#include <kernel/msg.h> #include <kernel/msg.h>
#include <kernel/port.h> #include <kernel/port.h>
#include <kernel/printk.h>
#include <kernel/task.h> #include <kernel/task.h>
#include <kernel/thread.h> #include <kernel/thread.h>
#include <kernel/util.h> #include <kernel/util.h>
@@ -157,12 +158,12 @@ extern kern_status_t channel_recv_msg(
/* msg is now set to the next message to process */ /* msg is now set to the next message to process */
if (msg->msg_type != KERN_MSG_TYPE_DATA) { if (msg->msg_type != KERN_MSG_TYPE_DATA) {
/* event messages as asynchronous */ /* event messages are asynchronous */
out_msg->msg_id = msg->msg_id; out_msg->msg_id = msg->msg_id;
out_msg->msg_type = msg->msg_type; out_msg->msg_type = msg->msg_type;
out_msg->msg_event = msg->msg_event; out_msg->msg_event = msg->msg_event;
out_msg->msg_sender = msg->msg_sender_thread->tr_parent->t_id; out_msg->msg_sender = msg->msg_sender_thread_id;
out_msg->msg_endpoint = msg->msg_sender_port->p_base.ob_id; out_msg->msg_endpoint = msg->msg_sender_port_id;
spin_unlock_irqrestore(&msg->msg_lock, msg_lock_flags); spin_unlock_irqrestore(&msg->msg_lock, msg_lock_flags);
msg_free(msg); msg_free(msg);
+4 -4
View File
@@ -83,8 +83,8 @@ kern_status_t port_connect(struct port *port, struct channel *remote)
msg->msg_status = KMSG_ASYNC; msg->msg_status = KMSG_ASYNC;
msg->msg_type = KERN_MSG_TYPE_EVENT; msg->msg_type = KERN_MSG_TYPE_EVENT;
msg->msg_event = KERN_MSG_EVENT_CONNECTION; msg->msg_event = KERN_MSG_EVENT_CONNECTION;
msg->msg_sender_thread = current_thread(); msg->msg_sender_thread_id = current_thread()->tr_id;
msg->msg_sender_port = port; msg->msg_sender_port_id = port->p_base.ob_id;
unsigned long flags; unsigned long flags;
channel_lock_irqsave(remote, &flags); channel_lock_irqsave(remote, &flags);
@@ -112,8 +112,8 @@ kern_status_t port_disconnect(struct port *port)
msg->msg_status = KMSG_ASYNC; msg->msg_status = KMSG_ASYNC;
msg->msg_type = KERN_MSG_TYPE_EVENT; msg->msg_type = KERN_MSG_TYPE_EVENT;
msg->msg_event = KERN_MSG_EVENT_DISCONNECTION; msg->msg_event = KERN_MSG_EVENT_DISCONNECTION;
msg->msg_sender_thread = current_thread(); msg->msg_sender_thread_id = current_thread()->tr_id;
msg->msg_sender_port = port; msg->msg_sender_port_id = port->p_base.ob_id;
unsigned long flags; unsigned long flags;
channel_lock_irqsave(port->p_remote, &flags); channel_lock_irqsave(port->p_remote, &flags);