this repo has no description
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Update a bunch of Mach traps to use darlingserver; more...

Additionally, the elfcalls threading code now handles opening a new RPC socket for the new thread.

Also, we now set close-on-exec RPC sockets on the client-side.

+287 -240
+3 -3
src/kernel/emulation/linux/bsdthread/pthread_canceled.c
··· 3 3 #include "../errno.h" 4 4 #include <linux-syscalls/linux.h> 5 5 #include <stddef.h> 6 - #include "../mach/lkm.h" 7 - #include "../../../../external/lkm/api.h" 8 6 #include "bsdthread_create.h" 9 7 #include <sys/errno.h> 8 + 9 + #include <darlingserver/rpc.h> 10 10 11 11 long sys_pthread_canceled(int action) 12 12 { 13 13 if (action == 0 && !uses_threads()) 14 14 return -EINVAL; 15 15 16 - int ret = lkm_call(NR_pthread_canceled, (void*)(long) action); 16 + int ret = dserver_rpc_pthread_canceled(action); 17 17 if (ret < 0) 18 18 ret = errno_linux_to_bsd(ret); 19 19
+3 -8
src/kernel/emulation/linux/bsdthread/pthread_kill.c
··· 4 4 #include "../signal/duct_signals.h" 5 5 #include <sys/errno.h> 6 6 #include <stddef.h> 7 - #include "../mach/lkm.h" 8 - #include "../../../../external/lkm/api.h" 9 7 #include "../simple.h" 10 8 9 + #include <darlingserver/rpc.h> 10 + 11 11 long sys_pthread_kill(int thread_port, int sig) 12 12 { 13 - struct pthread_kill_args args; 14 - 15 - args.thread_port = thread_port; 16 - args.sig = signum_bsd_to_linux(sig); 17 - 18 - int ret = lkm_call(NR_pthread_kill_trap, &args); 13 + int ret = dserver_rpc_pthread_kill(thread_port, signum_bsd_to_linux(sig)); 19 14 if (ret < 0) 20 15 ret = errno_linux_to_bsd(ret); 21 16
+4 -4
src/kernel/emulation/linux/bsdthread/pthread_markcancel.c
··· 3 3 #include "../errno.h" 4 4 #include <linux-syscalls/linux.h> 5 5 #include <stddef.h> 6 - #include "../mach/lkm.h" 7 - #include "../../../../external/lkm/api.h" 8 6 9 - long sys_pthread_markcancel(int thread_port) 7 + #include <darlingserver/rpc.h> 8 + 9 + long sys_pthread_markcancel(unsigned int thread_port) 10 10 { 11 - int ret = lkm_call(NR_pthread_markcancel, (void*)(long) thread_port); 11 + int ret = dserver_rpc_pthread_markcancel(thread_port); 12 12 if (ret < 0) 13 13 ret = errno_linux_to_bsd(ret); 14 14
+1 -1
src/kernel/emulation/linux/bsdthread/pthread_markcancel.h
··· 1 1 #ifndef PTHREAD_MARKCANCEL_H 2 2 #define PTHREAD_MARKCANCEL_H 3 3 4 - long sys_pthread_markcancel(int thread_port); 4 + long sys_pthread_markcancel(unsigned int thread_port); 5 5 6 6 #endif 7 7
+2 -2
src/kernel/emulation/linux/mach/lkm.h
··· 3 3 4 4 #include <os/tsd.h> 5 5 6 - // TSD slot 6 is reserved by Apple for Windows/WINE compatibility. 6 + // TSD slot 11 is reserved by Apple for Windows/WINE compatibility. 7 7 // Since WINE can never run under Darling, we can use that slot for our own purposes. 8 8 // Namely, we use it to store the the per-thread darlingserver socket. 9 - #define __TSD_DSERVER_RPC_FD 6 9 + #define __TSD_DSERVER_RPC_FD 11 10 10 11 11 void mach_driver_init(const char** applep); 12 12 int lkm_call(int call_nr, void* arg);
+224 -218
src/kernel/emulation/linux/mach/mach_traps.c
··· 5 5 #include <sys/mman.h> 6 6 #include <fcntl.h> 7 7 #include <unistd.h> 8 - #include "../../external/lkm/api.h" 9 - #include "lkm.h" 10 8 #include "mach_traps.h" 11 9 #include <mach/mach_init.h> 12 10 #include "../ext/mremap.h" ··· 17 15 18 16 mach_port_name_t mach_reply_port_impl(void) 19 17 { 20 - __simple_printf("Got to mach_reply_port_impl\n"); 21 18 unsigned int port_name; 22 19 if (dserver_rpc_mach_reply_port(&port_name) != 0) { 23 - __simple_printf("mach_reply_port_impl RPC failed\n"); 24 20 port_name = MACH_PORT_NULL; 25 21 } 26 - __simple_printf("Returning from mach_reply_port_impl: %d\n", port_name); 27 - //__simple_abort(); 28 22 return port_name; 29 23 } 30 24 31 25 mach_port_name_t thread_self_trap_impl(void) 32 26 { 33 - __simple_printf("Got to thread_self_trap_impl\n"); 34 27 unsigned int port_name; 35 28 if (dserver_rpc_thread_self_trap(&port_name) != 0) { 36 - __simple_printf("thread_self_trap_impl RPC failed\n"); 37 29 port_name = MACH_PORT_NULL; 38 30 } 39 - __simple_printf("Returning from thread_self_trap_impl: %d\n", port_name); 40 - //__simple_abort(); 41 31 return port_name; 42 32 } 43 33 44 34 mach_port_name_t host_self_trap_impl(void) 45 35 { 46 - __simple_printf("Got to host_self_trap_impl\n"); 47 36 unsigned int port_name; 48 37 if (dserver_rpc_host_self_trap(&port_name) != 0) { 49 - __simple_printf("host_self_trap_impl RPC failed\n"); 50 38 port_name = MACH_PORT_NULL; 51 39 } 52 - __simple_printf("Returning from host_self_trap_impl: %d\n", port_name); 53 - //__simple_abort(); 54 40 return port_name; 55 41 } 56 42 ··· 80 66 mach_msg_header_t *rcv_msg, 81 67 mach_msg_size_t rcv_limit) 82 68 { 83 - int code = dserver_rpc_mach_msg_overwrite(msg, option, send_size, rcv_size, rcv_name, timeout, notify, rcv_msg, rcv_limit); 69 + int code = dserver_rpc_mach_msg_overwrite(msg, option, send_size, rcv_size, rcv_name, timeout, notify, rcv_msg); 84 70 85 71 if (code < 0) { 86 72 __simple_printf("mach_msg_overwrite failed (internally): %d\n", code); ··· 93 79 kern_return_t semaphore_signal_trap_impl( 94 80 mach_port_name_t signal_name) 95 81 { 96 - struct semaphore_signal_args args = { 97 - .signal = signal_name 98 - }; 82 + int code = dserver_rpc_semaphore_signal(signal_name); 99 83 100 - return lkm_call(NR_semaphore_signal_trap, &args); 84 + if (code < 0) { 85 + __simple_printf("semaphore_signal failed (internally): %d\n", code); 86 + __simple_abort(); 87 + } 88 + 89 + return code; 101 90 } 102 91 103 92 kern_return_t semaphore_signal_all_trap_impl( 104 93 mach_port_name_t signal_name) 105 94 { 106 - struct semaphore_signal_all_args args = { 107 - .signal = signal_name 108 - }; 95 + int code = dserver_rpc_semaphore_signal_all(signal_name); 96 + 97 + if (code < 0) { 98 + __simple_printf("semaphore_signal_all failed (internally): %d\n", code); 99 + __simple_abort(); 100 + } 109 101 110 - return lkm_call(NR_semaphore_signal_all_trap, 111 - &args); 102 + return code; 112 103 } 113 104 114 105 kern_return_t semaphore_signal_thread_trap_impl( ··· 122 113 kern_return_t semaphore_wait_trap_impl( 123 114 mach_port_name_t wait_name) 124 115 { 125 - struct semaphore_wait_args args = { 126 - .signal = wait_name 127 - }; 116 + int code = dserver_rpc_semaphore_wait(wait_name); 128 117 129 - return lkm_call(NR_semaphore_wait_trap, &args); 118 + if (code < 0) { 119 + __simple_printf("semaphore_wait failed (internally): %d\n", code); 120 + __simple_abort(); 121 + } 122 + 123 + return code; 130 124 } 131 125 132 126 kern_return_t semaphore_wait_signal_trap_impl( 133 127 mach_port_name_t wait_name, 134 128 mach_port_name_t signal_name) 135 129 { 136 - struct semaphore_wait_signal_args args = { 137 - .signal = signal_name, 138 - .wait = wait_name 139 - }; 130 + int code = dserver_rpc_semaphore_wait_signal(wait_name, signal_name); 131 + 132 + if (code < 0) { 133 + __simple_printf("semaphore_wait_signal failed (internally): %d\n", code); 134 + __simple_abort(); 135 + } 140 136 141 - return lkm_call(NR_semaphore_wait_signal_trap, 142 - &args); 137 + return code; 143 138 } 144 139 145 140 kern_return_t semaphore_timedwait_trap_impl( ··· 147 142 unsigned int sec, 148 143 clock_res_t nsec) 149 144 { 150 - struct semaphore_timedwait_args args = { 151 - .wait = wait_name, 152 - .sec = sec, 153 - .nsec = nsec 154 - }; 145 + int code = dserver_rpc_semaphore_timedwait(wait_name, sec, nsec); 155 146 156 - return lkm_call(NR_semaphore_timedwait_trap, 157 - &args); 147 + if (code < 0) { 148 + __simple_printf("semaphore_timedwait failed (internally): %d\n", code); 149 + __simple_abort(); 150 + } 151 + 152 + return code; 158 153 } 159 154 160 155 kern_return_t semaphore_timedwait_signal_trap_impl( ··· 163 158 unsigned int sec, 164 159 clock_res_t nsec) 165 160 { 166 - struct semaphore_timedwait_signal_args args = { 167 - .wait = wait_name, 168 - .signal = signal_name, 169 - .sec = sec, 170 - .nsec = nsec 171 - }; 161 + int code = dserver_rpc_semaphore_timedwait_signal(wait_name, signal_name, sec, nsec); 162 + 163 + if (code < 0) { 164 + __simple_printf("semaphore_timedwait_signal failed (internally): %d\n", code); 165 + __simple_abort(); 166 + } 172 167 173 - return lkm_call(NR_semaphore_timedwait_signal_trap, 174 - &args); 168 + return code; 175 169 } 176 170 177 171 kern_return_t clock_sleep_trap_impl( ··· 193 187 { 194 188 if (target != 0 && target != mach_task_self()) 195 189 { 196 - struct mach_vm_allocate_args args = { 197 - .target = target, 198 - .address = (uint64_t) *addr, 199 - .size = size, 200 - .flags = flags 201 - }; 190 + int code = dserver_rpc_mach_vm_allocate(target, addr, size, flags); 202 191 203 - int rv = lkm_call(NR__kernelrpc_mach_vm_allocate_trap, &args); 192 + if (code < 0) { 193 + __simple_printf("mach_vm_allocate failed (internally): %d\n", code); 194 + __simple_abort(); 195 + } 204 196 205 - if (rv == KERN_SUCCESS) 206 - *addr = args.address; 207 - 208 - return rv; 197 + return code; 209 198 } 210 199 else 211 200 { ··· 224 213 225 214 if (target != 0 && target != mach_task_self()) 226 215 { 227 - struct mach_vm_deallocate_args args = { 228 - .target = target, 229 - .address = (uint64_t) address, 230 - .size = size, 231 - }; 216 + int code = dserver_rpc_mach_vm_deallocate(target, address, size); 217 + 218 + if (code < 0) { 219 + __simple_printf("mach_vm_deallocate failed (internally): %d\n", code); 220 + __simple_abort(); 221 + } 232 222 233 - return lkm_call(NR__kernelrpc_mach_vm_deallocate_trap, &args); 223 + return code; 234 224 } 235 225 else 236 226 { ··· 246 236 return KERN_SUCCESS; 247 237 } 248 238 249 - ret = munmap(address, size); 239 + ret = munmap((void*)address, size); 250 240 251 241 if (ret == -1) 252 242 return KERN_FAILURE; ··· 279 269 if (new_protection & VM_PROT_EXECUTE) 280 270 prot |= PROT_EXEC; 281 271 282 - ret = mprotect(address, size, prot); 272 + ret = mprotect((void*)address, size, prot); 283 273 if (ret == -1) 284 274 return KERN_FAILURE; 285 275 ··· 313 303 if (!(flags & VM_FLAGS_ANYWHERE)) 314 304 posix_flags |= MAP_FIXED; 315 305 if ((flags >> 24) == VM_MEMORY_REALLOC) 316 - addr = __linux_mremap(((char*)*address) - 0x1000, 0x1000, 0x1000 + size, 0, NULL); 306 + addr = (void*)__linux_mremap(((char*)*address) - 0x1000, 0x1000, 0x1000 + size, 0, NULL); 317 307 else 318 - addr = mmap(*address, size, prot, posix_flags, -1, 0); 308 + addr = mmap((void*)*address, size, prot, posix_flags, -1, 0); 319 309 320 310 if (addr == MAP_FAILED) 321 311 { ··· 332 322 // This may not work for some crazy masks. Consider using __builtin_clz(). 333 323 boundary = mask + 1; 334 324 335 - iaddr = mmap(*address, size + boundary, prot, posix_flags, -1, 0); 325 + iaddr = (uintptr_t)mmap((void*)*address, size + boundary, prot, posix_flags, -1, 0); 336 326 if (iaddr == (uintptr_t) MAP_FAILED) 337 327 return KERN_FAILURE; 338 328 ··· 340 330 diff = q - iaddr; 341 331 342 332 if (diff > 0) 343 - munmap(iaddr, diff); 333 + munmap((void*)iaddr, diff); 344 334 if (boundary - diff > 0) 345 335 munmap((void*) (q + size), boundary - diff); 346 336 347 337 addr = (void*) q; 348 338 } 349 339 350 - *address = addr; 340 + *address = (uintptr_t)addr; 351 341 return KERN_SUCCESS; 352 342 } 353 343 ··· 357 347 mach_port_name_t *name 358 348 ) 359 349 { 360 - kern_return_t ret; 350 + int code = dserver_rpc_mach_port_allocate(target, right, name); 361 351 362 - struct mach_port_allocate_args args = { 363 - .task_right_name = target, 364 - .right_type = right, 365 - .out_right_name = name 366 - }; 352 + if (code < 0) { 353 + __simple_printf("mach_port_allocate failed (internally): %d\n", code); 354 + __simple_abort(); 355 + } 367 356 368 - ret = lkm_call(NR__kernelrpc_mach_port_allocate, 369 - &args); 370 - return ret; 357 + return code; 371 358 } 372 359 373 360 ··· 376 363 mach_port_name_t name 377 364 ) 378 365 { 379 - struct mach_port_destroy_args args = { 380 - .task_right_name = target, 381 - .port_right_name = name 382 - }; 366 + int code = dserver_rpc_mach_port_destruct(target, name, 0, 0); 367 + 368 + if (code < 0) { 369 + __simple_printf("mach_port_destroy failed (internally): %d\n", code); 370 + __simple_abort(); 371 + } 383 372 384 - return lkm_call(NR__kernelrpc_mach_port_destroy, 385 - &args); 373 + return code; 386 374 } 387 375 388 376 kern_return_t _kernelrpc_mach_port_deallocate_trap_impl( ··· 407 395 mach_port_delta_t delta 408 396 ) 409 397 { 410 - struct mach_port_mod_refs_args args = { 411 - .task_right_name = target, 412 - .port_right_name = name, 413 - .right_type = right, 414 - .delta = delta 415 - }; 398 + int code = dserver_rpc_mach_port_mod_refs(target, name, right, delta); 416 399 417 - return lkm_call(NR__kernelrpc_mach_port_mod_refs, &args); 400 + if (code < 0) { 401 + __simple_printf("mach_port_deallocate failed (internally): %d\n", code); 402 + __simple_abort(); 403 + } 404 + 405 + return code; 418 406 } 419 407 420 408 kern_return_t _kernelrpc_mach_port_move_member_trap_impl( ··· 423 411 mach_port_name_t after 424 412 ) 425 413 { 426 - struct mach_port_move_member_args args = { 427 - .task_right_name = target, 428 - .port_right_name = member, 429 - .pset_right_name = after 430 - }; 431 - return lkm_call(NR__kernelrpc_mach_port_move_member_trap, &args); 414 + int code = dserver_rpc_mach_port_move_member(target, member, after); 415 + 416 + if (code < 0) { 417 + __simple_printf("mach_port_move_member failed (internally): %d\n", code); 418 + __simple_abort(); 419 + } 420 + 421 + return code; 432 422 } 433 423 434 424 kern_return_t _kernelrpc_mach_port_insert_right_trap_impl( ··· 438 428 mach_msg_type_name_t polyPoly 439 429 ) 440 430 { 441 - struct mach_port_insert_right_args args = { 442 - .task_right_name = target, 443 - .port_name = name, 444 - .right_name = poly, 445 - .right_type = polyPoly 446 - }; 447 - return lkm_call(NR__kernelrpc_mach_port_insert_right_trap, &args); 431 + int code = dserver_rpc_mach_port_insert_right(target, name, poly, polyPoly); 432 + 433 + if (code < 0) { 434 + __simple_printf("mach_port_insert_right failed (internally): %d\n", code); 435 + __simple_abort(); 436 + } 437 + 438 + return code; 448 439 } 449 440 450 441 kern_return_t _kernelrpc_mach_port_insert_member_trap_impl( ··· 453 444 mach_port_name_t pset 454 445 ) 455 446 { 456 - struct mach_port_insert_member_args args = { 457 - .task_right_name = target, 458 - .port_right_name = name, 459 - .pset_right_name = pset 460 - }; 461 - return lkm_call(NR__kernelrpc_mach_port_insert_member_trap, &args); 447 + int code = dserver_rpc_mach_port_insert_member(target, name, pset); 448 + 449 + if (code < 0) { 450 + __simple_printf("mach_port_insert_member failed (internally): %d\n", code); 451 + __simple_abort(); 452 + } 453 + 454 + return code; 462 455 } 463 456 464 457 kern_return_t _kernelrpc_mach_port_extract_member_trap_impl( ··· 467 460 mach_port_name_t pset 468 461 ) 469 462 { 470 - struct mach_port_extract_member_args args = { 471 - .task_right_name = target, 472 - .port_right_name = name, 473 - .pset_right_name = pset 474 - }; 475 - return lkm_call(NR__kernelrpc_mach_port_extract_member_trap, &args); 463 + int code = dserver_rpc_mach_port_extract_member(target, name, pset); 464 + 465 + if (code < 0) { 466 + __simple_printf("mach_port_extract_member failed (internally): %d\n", code); 467 + __simple_abort(); 468 + } 469 + 470 + return code; 476 471 } 477 472 478 473 kern_return_t _kernelrpc_mach_port_construct_trap_impl( ··· 482 477 mach_port_name_t *name 483 478 ) 484 479 { 485 - struct mach_port_construct_args args = { 486 - .task_right_name = target, 487 - .options = options, 488 - .context = context, 489 - .port_right_name_out = name, 490 - }; 491 - return lkm_call(NR__kernelrpc_mach_port_construct_trap, &args); 480 + int code = dserver_rpc_mach_port_construct(target, options, context, name); 481 + 482 + if (code < 0) { 483 + __simple_printf("mach_port_construct failed (internally): %d\n", code); 484 + __simple_abort(); 485 + } 486 + 487 + return code; 492 488 } 493 489 494 490 kern_return_t _kernelrpc_mach_port_destruct_trap_impl( ··· 498 494 uint64_t guard 499 495 ) 500 496 { 501 - struct mach_port_destruct_args args = { 502 - .task_right_name = target, 503 - .port_right_name = name, 504 - .srdelta = srdelta, 505 - .guard = guard, 506 - }; 507 - return lkm_call(NR__kernelrpc_mach_port_destruct_trap, &args); 497 + int code = dserver_rpc_mach_port_destruct(target, name, srdelta, guard); 498 + 499 + if (code < 0) { 500 + __simple_printf("mach_port_destruct failed (internally): %d\n", code); 501 + __simple_abort(); 502 + } 503 + 504 + return code; 508 505 } 509 506 510 507 kern_return_t _kernelrpc_mach_port_guard_trap_impl( ··· 514 511 boolean_t strict 515 512 ) 516 513 { 517 - struct mach_port_guard_args args = { 518 - .task_right_name = target, 519 - .port_right_name = name, 520 - .guard = guard, 521 - .strict = strict, 522 - }; 523 - return lkm_call(NR__kernelrpc_mach_port_guard_trap, &args); 514 + int code = dserver_rpc_mach_port_guard(target, name, guard, strict); 515 + 516 + if (code < 0) { 517 + __simple_printf("mach_port_guard failed (internally): %d\n", code); 518 + __simple_abort(); 519 + } 520 + 521 + return code; 524 522 } 525 523 526 524 kern_return_t _kernelrpc_mach_port_unguard_trap_impl( ··· 529 527 uint64_t guard 530 528 ) 531 529 { 532 - struct mach_port_unguard_args args = { 533 - .task_right_name = target, 534 - .port_right_name = name, 535 - .guard = guard, 536 - }; 537 - return lkm_call(NR__kernelrpc_mach_port_unguard_trap, &args); 530 + int code = dserver_rpc_mach_port_unguard(target, name, guard); 531 + 532 + if (code < 0) { 533 + __simple_printf("mach_port_unguard failed (internally): %d\n", code); 534 + __simple_abort(); 535 + } 536 + 537 + return code; 538 538 } 539 539 540 540 kern_return_t thread_get_special_reply_port_impl(void) 541 541 { 542 - return lkm_call(NR_thread_get_special_reply_port, 0); 542 + unsigned int port_name; 543 + if (dserver_rpc_thread_get_special_reply_port(&port_name) != 0) { 544 + port_name = MACH_PORT_NULL; 545 + } 546 + return port_name; 543 547 }; 544 548 545 549 kern_return_t _kernelrpc_mach_port_request_notification_impl( ··· 552 556 mach_port_name_t* previous 553 557 ) 554 558 { 555 - struct mach_port_request_notification_args args = { 556 - .task_right_name = task, 557 - .port_right_name = name, 558 - .message_id = msgid, 559 - .make_send_count = sync, 560 - .notification_destination_port_name = notify, 561 - .message_type = notifyPoly, 562 - .previous_destination_port_name_out = previous, 563 - }; 564 - return lkm_call(NR__kernelrpc_mach_port_request_notification_trap, &args); 559 + int code = dserver_rpc_mach_port_request_notification(task, name, msgid, sync, notify, notifyPoly, previous); 560 + 561 + if (code < 0) { 562 + __simple_printf("mach_port_request_notification failed (internally): %d\n", code); 563 + __simple_abort(); 564 + } 565 + 566 + return code; 565 567 }; 566 568 567 569 kern_return_t _kernelrpc_mach_port_get_attributes_impl( ··· 572 574 mach_msg_type_number_t* port_info_outCnt 573 575 ) 574 576 { 575 - struct mach_port_get_attributes_args args = { 576 - .task_right_name = target, 577 - .port_right_name = name, 578 - .flavor = flavor, 579 - .info_out = port_info_out, 580 - .count_out = port_info_outCnt, 581 - }; 582 - return lkm_call(NR__kernelrpc_mach_port_get_attributes_trap, &args); 577 + int code = dserver_rpc_mach_port_get_attributes(target, name, flavor, port_info_out, port_info_outCnt); 578 + 579 + if (code < 0) { 580 + __simple_printf("mach_port_get_attributes failed (internally): %d\n", code); 581 + __simple_abort(); 582 + } 583 + 584 + return code; 583 585 }; 584 586 585 587 kern_return_t _kernelrpc_mach_port_type_impl( ··· 588 590 mach_port_type_t* ptype 589 591 ) 590 592 { 591 - struct mach_port_type_args args = { 592 - .task_right_name = task, 593 - .port_right_name = name, 594 - .port_type_out = ptype, 595 - }; 596 - return lkm_call(NR__kernelrpc_mach_port_type_trap, &args); 593 + int code = dserver_rpc_mach_port_type(task, name, ptype); 594 + 595 + if (code < 0) { 596 + __simple_printf("mach_port_type failed (internally): %d\n", code); 597 + __simple_abort(); 598 + } 599 + 600 + return code; 597 601 }; 598 602 599 603 kern_return_t macx_swapon_impl( ··· 670 674 671 675 mach_port_name_t task_self_trap_impl(void) 672 676 { 673 - __simple_printf("Got to task_self_trap_impl\n"); 674 677 unsigned int port_name; 675 678 if (dserver_rpc_task_self_trap(&port_name) != 0) { 676 - __simple_printf("task_self_trap_impl RPC failed\n"); 677 679 port_name = MACH_PORT_NULL; 678 680 } 679 - __simple_printf("Returning from task_self_trap_impl: %d\n", port_name); 680 - //__simple_abort(); 681 681 return port_name; 682 682 } 683 683 ··· 690 690 int pid, 691 691 mach_port_name_t *t) 692 692 { 693 - struct task_for_pid args = { 694 - .pid = pid, 695 - .task_port = t, 696 - }; 693 + int code = dserver_rpc_task_for_pid(target_tport, pid, t); 697 694 698 - return lkm_call(NR_task_for_pid_trap, &args); 695 + if (code < 0) { 696 + __simple_printf("task_for_pid failed (internally): %d\n", code); 697 + __simple_abort(); 698 + } 699 + 700 + return code; 699 701 } 700 702 701 703 kern_return_t task_name_for_pid_impl( ··· 703 705 int pid, 704 706 mach_port_name_t *tn) 705 707 { 706 - kern_return_t rv; 707 - struct task_name_for_pid args = { 708 - .task_port = target_tport, 709 - .pid = pid 710 - }; 708 + int code = dserver_rpc_task_name_for_pid(target_tport, pid, tn); 711 709 712 - rv = lkm_call(NR_task_name_for_pid_trap, &args); 713 - if (rv == KERN_SUCCESS) 714 - *tn = args.name_out; 710 + if (code < 0) { 711 + __simple_printf("task_name_for_pid failed (internally): %d\n", code); 712 + __simple_abort(); 713 + } 715 714 716 - return rv; 715 + return code; 717 716 } 718 717 719 718 kern_return_t pid_for_task_impl( 720 719 mach_port_name_t t, 721 720 int *x) 722 721 { 723 - struct pid_for_task args = { 724 - .task_port = t, 725 - .pid = x, 726 - }; 722 + int code = dserver_rpc_pid_for_task(t, x); 727 723 728 - return lkm_call(NR_pid_for_task_trap, &args); 724 + if (code < 0) { 725 + __simple_printf("pid_for_task failed (internally): %d\n", code); 726 + __simple_abort(); 727 + } 728 + 729 + return code; 729 730 } 730 731 731 732 kern_return_t bsdthread_terminate_trap_impl( ··· 734 735 mach_port_name_t thread, 735 736 mach_port_name_t sem) 736 737 { 737 - struct bsdthread_terminate_args args = { 738 - .stackaddr = stackaddr, 739 - .freesize = freesize, 740 - .port = thread, 741 - .sem = sem 742 - }; 743 - 744 - return lkm_call(NR_bsdthread_terminate_trap, &args); 738 + UNIMPLEMENTED_TRAP(); 739 + return KERN_FAILURE; 745 740 } 746 741 747 742 ··· 770 765 771 766 mach_port_name_t mk_timer_create_impl(void) 772 767 { 773 - return lkm_call(NR_mk_timer_create_trap, NULL); 768 + unsigned int port_name; 769 + if (dserver_rpc_mk_timer_create(&port_name) < 0) { 770 + port_name = MACH_PORT_NULL; 771 + } 772 + return port_name; 774 773 } 775 774 776 775 kern_return_t mk_timer_destroy_impl(mach_port_name_t name) 777 776 { 778 - struct mk_timer_destroy_args args = { 779 - .timer_port = name 780 - }; 777 + int code = dserver_rpc_mk_timer_destroy(name); 778 + 779 + if (code < 0) { 780 + __simple_printf("mk_timer_destroy failed (internally): %d\n", code); 781 + __simple_abort(); 782 + } 781 783 782 - return lkm_call(NR_mk_timer_destroy_trap, &args); 784 + return code; 783 785 } 784 786 785 787 kern_return_t mk_timer_arm_impl(mach_port_name_t name, uint64_t expire_time) 786 788 { 787 - struct mk_timer_arm_args args = { 788 - .timer_port = name, 789 - .expire_time = expire_time, 790 - }; 789 + int code = dserver_rpc_mk_timer_arm(name, expire_time); 791 790 792 - return lkm_call(NR_mk_timer_arm_trap, &args); 791 + if (code < 0) { 792 + __simple_printf("mk_timer_arm failed (internally): %d\n", code); 793 + __simple_abort(); 794 + } 795 + 796 + return code; 793 797 } 794 798 795 799 kern_return_t mk_timer_cancel_impl(mach_port_name_t name, uint64_t *result_time) 796 800 { 797 - struct mk_timer_cancel_args args = { 798 - .timer_port = name, 799 - .result_time = result_time, 800 - }; 801 + int code = dserver_rpc_mk_timer_cancel(name, result_time); 802 + 803 + if (code < 0) { 804 + __simple_printf("mk_timer_cancel failed (internally): %d\n", code); 805 + __simple_abort(); 806 + } 801 807 802 - return lkm_call(NR_mk_timer_cancel_trap, &args); 808 + return code; 803 809 } 804 810
+3
src/startup/mldr/elfcalls/dthreads.h
··· 50 50 #define DTHREAD_TSD_SLOT_PTR_MUNGE 7 51 51 #define DTHREAD_TSD_SLOT_MACH_SPECIAL_REPLY 8 52 52 53 + // see src/kernel/emulation/linux/mach/lkm.h 54 + #define DTHREAD_TSD_SLOT_DSERVER_RPC_FD 11 55 + 53 56 #define DTHREAD_START_TSD_BASE_SET 0x10000000 54 57 55 58 #define DTHREAD_CANCEL_ENABLE 0x01
+37 -4
src/startup/mldr/elfcalls/threads.c
··· 29 29 #include <sys/syscall.h> 30 30 #include <setjmp.h> 31 31 #include <sys/syscall.h> 32 + #include <sys/socket.h> 33 + #include <stdio.h> 34 + #include <fcntl.h> 32 35 33 36 #include "dthreads.h" 34 37 ··· 72 75 static dthread_t dthread_structure_init(dthread_t dthread, size_t guard_size, void* stack_addr, size_t stack_size, void* base_addr, size_t total_size) { 73 76 // the pthread signature is the address of the pthread XORed with the "pointer munge" token passed in by the kernel 74 77 // since the LKM doesn't pass in a token, it's always zero, so the signature is equal to just the address 75 - dthread->sig = dthread; 78 + dthread->sig = (uintptr_t)dthread; 76 79 77 80 dthread->tsd[DTHREAD_TSD_SLOT_PTHREAD_SELF] = dthread; 78 81 dthread->tsd[DTHREAD_TSD_SLOT_ERRNO] = &dthread->err_no; 79 - dthread->tsd[DTHREAD_TSD_SLOT_PTHREAD_QOS_CLASS] = DTHREAD_DEFAULT_PRIORITY; 82 + dthread->tsd[DTHREAD_TSD_SLOT_PTHREAD_QOS_CLASS] = (void*)(uintptr_t)(DTHREAD_DEFAULT_PRIORITY); 80 83 dthread->tsd[DTHREAD_TSD_SLOT_PTR_MUNGE] = 0; 84 + dthread->tsd[DTHREAD_TSD_SLOT_DSERVER_RPC_FD] = (void*)(intptr_t)-1; 81 85 dthread->tl_has_custom_stack = 0; 82 86 dthread->lock = (darwin_os_unfair_lock){0}; 83 87 ··· 145 149 .pth_obj_size = pth_obj_size, 146 150 .pth = NULL, // set later on 147 151 .callbacks = callbacks, 148 - .stack_addr = NULL, // set later on 152 + .stack_addr = 0, // set later on 149 153 .is_workqueue = real_entry_point == 0, // our `workq_kernreturn` sets `real_entry_point` to NULL; `bsdthread_create` actually passes a value 150 154 }; 151 155 pthread_attr_t attr; ··· 160 164 // 161 165 // otherwise, allocate them ourselves 162 166 if (pth == NULL || args.is_workqueue) { 163 - pth = dthread_structure_allocate(stack_size, DEFAULT_DTHREAD_GUARD_SIZE, &args.stack_addr); 167 + pth = dthread_structure_allocate(stack_size, DEFAULT_DTHREAD_GUARD_SIZE, (void**)&args.stack_addr); 164 168 } else if (!args.is_workqueue) { 165 169 // `arg2` is `stack_addr` for normal threads 166 170 args.stack_addr = arg2; ··· 199 203 200 204 dthread_t dthread = args.pth; 201 205 uintptr_t* flags = args.is_workqueue ? &args.arg2 : &args.arg3; 206 + 207 + // create a new dserver RPC socket 208 + int new_rpc_fd = socket(AF_UNIX, SOCK_DGRAM, 0); 209 + if (new_rpc_fd < 0) { 210 + // we can't do anything if we don't get our own separate connection to darlingserver 211 + fprintf(stderr, "Failed to create socket\n"); 212 + abort(); 213 + } 214 + 215 + // make it close-on-exec 216 + int fd_flags = fcntl(new_rpc_fd, F_GETFD); 217 + if (fd_flags < 0) { 218 + fprintf(stderr, "Failed to read socket FD flags\n"); 219 + exit(1); 220 + } 221 + if (fcntl(new_rpc_fd, F_SETFD, fd_flags | FD_CLOEXEC) < 0) { 222 + fprintf(stderr, "Failed to set close-on-exec flag on socket FD\n"); 223 + exit(1); 224 + } 225 + 226 + // auto-bind it 227 + sa_family_t family = AF_UNIX; 228 + if (bind(new_rpc_fd, (const struct sockaddr*)&family, sizeof(family)) < 0) { 229 + fprintf(stderr, "Failed to autobind socket\n"); 230 + exit(1); 231 + } 232 + 233 + // the socket is ready; assign it now 234 + dthread->tsd[DTHREAD_TSD_SLOT_DSERVER_RPC_FD] = (void*)(intptr_t)new_rpc_fd; 202 235 203 236 // checkin with darlingserver on this new thread 204 237 if (dserver_rpc_checkin(false) < 0) {
+10
src/startup/mldr/mldr.c
··· 466 466 exit(1); 467 467 } 468 468 469 + int fd_flags = fcntl(lr->kernfd, F_GETFD); 470 + if (fd_flags < 0) { 471 + fprintf(stderr, "Failed to read socket FD flags\n"); 472 + exit(1); 473 + } 474 + if (fcntl(lr->kernfd, F_SETFD, fd_flags | FD_CLOEXEC) < 0) { 475 + fprintf(stderr, "Failed to set close-on-exec flag on socket FD\n"); 476 + exit(1); 477 + } 478 + 469 479 sa_family_t family = AF_UNIX; 470 480 if (bind(lr->kernfd, (const struct sockaddr*)&family, sizeof(family)) < 0) { 471 481 fprintf(stderr, "Failed to autobind socket\n");