Skip to content

Commit f505cb9

Browse files
committed
darwin: add thread_act_t wrapper and helpers
1 parent 2efd0eb commit f505cb9

2 files changed

Lines changed: 56 additions & 4 deletions

File tree

lib/std/c/darwin.zig

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -603,6 +603,9 @@ pub extern "c" fn thread_resume(thread: thread_act_t) kern_return_t;
603603
pub const THREAD_BASIC_INFO = 3;
604604
pub const THREAD_BASIC_INFO_COUNT: mach_msg_type_number_t = @sizeOf(thread_basic_info) / @sizeOf(natural_t);
605605

606+
pub const THREAD_IDENTIFIER_INFO = 4;
607+
pub const THREAD_IDENTIFIER_INFO_COUNT: mach_msg_type_number_t = @sizeOf(thread_identifier_info) / @sizeOf(natural_t);
608+
606609
pub const thread_flavor_t = natural_t;
607610
pub const thread_info_t = *integer_t;
608611
pub const time_value_t = time_value;
@@ -634,6 +637,17 @@ pub const thread_basic_info = extern struct {
634637
sleep_time: integer_t,
635638
};
636639

640+
pub const thread_identifier_info = extern struct {
641+
/// System-wide unique 64-bit thread id
642+
thread_id: u64,
643+
644+
/// Handle to be used by libproc
645+
thread_handle: u64,
646+
647+
/// libdispatch queue address
648+
dispatch_qaddr: u64,
649+
};
650+
637651
/// Cachability
638652
pub const MATTR_CACHE = 1;
639653
/// Migrability

lib/std/os/darwin.zig

Lines changed: 42 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -17,11 +17,11 @@ const mach_task = if (builtin.target.isDarwin()) struct {
1717
Unexpected,
1818
};
1919

20-
pub const MachTask = struct {
20+
pub const MachTask = extern struct {
2121
port: std.c.mach_port_name_t,
2222

2323
pub fn isValid(self: MachTask) bool {
24-
return self.port != 0;
24+
return self.port != std.c.TASK_NULL;
2525
}
2626

2727
pub fn allocatePort(self: MachTask, right: std.c.MACH_PORT_RIGHT) MachError!MachTask {
@@ -439,11 +439,11 @@ const mach_task = if (builtin.target.isDarwin()) struct {
439439
}
440440
}
441441

442-
pub fn getThreads(task: MachTask) MachError![]std.c.mach_port_t {
442+
pub fn getThreads(task: MachTask) MachError![]ThreadId {
443443
var thread_list: std.c.mach_port_array_t = undefined;
444444
var thread_count: std.c.mach_msg_type_number_t = undefined;
445445
switch (std.c.getKernError(std.c.task_threads(task.port, &thread_list, &thread_count))) {
446-
.SUCCESS => return thread_list[0..thread_count],
446+
.SUCCESS => return @ptrCast([*]ThreadId, thread_list)[0..thread_count],
447447
else => |err| {
448448
log.err("task_threads kernel call failed with error code: {s}", .{@tagName(err)});
449449
return error.Unexpected;
@@ -452,6 +452,44 @@ const mach_task = if (builtin.target.isDarwin()) struct {
452452
}
453453
};
454454

455+
pub const ThreadId = extern struct {
456+
id: std.c.thread_act_t,
457+
458+
pub fn getBasicInfo(thread_id: ThreadId) MachError!std.c.thread_basic_info {
459+
var info: std.c.thread_basic_info = undefined;
460+
var count = std.c.THREAD_BASIC_INFO_COUNT;
461+
switch (std.c.getKernError(std.c.thread_info(
462+
thread_id.id,
463+
std.c.THREAD_BASIC_INFO,
464+
@ptrCast(std.c.thread_info_t, &info),
465+
&count,
466+
))) {
467+
.SUCCESS => return info,
468+
else => |err| {
469+
log.err("thread_info kernel call failed with error code: {s}", .{@tagName(err)});
470+
return error.Unexpected;
471+
},
472+
}
473+
}
474+
475+
pub fn getIdentifierInfo(thread_id: ThreadId) MachError!std.c.thread_identifier_info {
476+
var info: std.c.thread_identifier_info = undefined;
477+
var count = std.c.THREAD_IDENTIFIER_INFO_COUNT;
478+
switch (std.c.getKernError(std.c.thread_info(
479+
thread_id.id,
480+
std.c.THREAD_IDENTIFIER_INFO,
481+
@ptrCast(std.c.thread_info_t, &info),
482+
&count,
483+
))) {
484+
.SUCCESS => return info,
485+
else => |err| {
486+
log.err("thread_info kernel call failed with error code: {s}", .{@tagName(err)});
487+
return error.Unexpected;
488+
},
489+
}
490+
}
491+
};
492+
455493
pub fn machTaskForPid(pid: std.os.pid_t) MachError!MachTask {
456494
var port: std.c.mach_port_name_t = undefined;
457495
switch (std.c.getKernError(std.c.task_for_pid(std.c.mach_task_self(), pid, &port))) {

0 commit comments

Comments
 (0)