| ... | @@ -1,14 +1,11 @@ | ... | @@ -1,14 +1,11 @@ |
| 1 | const assert = @import("../debug.zig").assert; | | |
| 2 | const builtin = @import("builtin"); | 1 | const builtin = @import("builtin"); |
| 3 | const arch = switch (builtin.arch) { | 2 | |
| 4 | builtin.Arch.x86_64 => @import("x86_64.zig"), | | |
| 5 | else => @compileError("unsupported arch"), | | |
| 6 | }; | | |
| 7 | pub use @import("syscall.zig"); | | |
| 8 | pub use @import("errno.zig"); | 3 | pub use @import("errno.zig"); |
| 9 | | 4 | |
| 10 | const std = @import("../../index.zig"); | 5 | const std = @import("../../index.zig"); |
| 11 | const c = std.c; | 6 | const c = std.c; |
| | 7 | |
| | 8 | const assert = std.debug.assert; |
| 12 | const maxInt = std.math.maxInt; | 9 | const maxInt = std.math.maxInt; |
| 13 | pub const Kevent = c.Kevent; | 10 | pub const Kevent = c.Kevent; |
| 14 | | 11 | |
| ... | @@ -546,19 +543,19 @@ pub fn getErrno(r: usize) usize { | ... | @@ -546,19 +543,19 @@ pub fn getErrno(r: usize) usize { |
| 546 | } | 543 | } |
| 547 | | 544 | |
| 548 | pub fn dup2(old: i32, new: i32) usize { | 545 | pub fn dup2(old: i32, new: i32) usize { |
| 549 | return arch.syscall2(SYS_dup2, @bitCast(usize, isize(old)), @bitCast(usize, isize(new))); | 546 | return errnoWrap(c.dup2(old, new)); |
| 550 | } | 547 | } |
| 551 | | 548 | |
| 552 | pub fn chdir(path: [*]const u8) usize { | 549 | pub fn chdir(path: [*]const u8) usize { |
| 553 | return arch.syscall1(SYS_chdir, @ptrToInt(path)); | 550 | return errnoWrap(c.chdir(path)); |
| 554 | } | 551 | } |
| 555 | | 552 | |
| 556 | pub fn execve(path: [*]const u8, argv: [*]const ?[*]const u8, envp: [*]const ?[*]const u8) usize { | 553 | pub fn execve(path: [*]const u8, argv: [*]const ?[*]const u8, envp: [*]const ?[*]const u8) usize { |
| 557 | return arch.syscall3(SYS_execve, @ptrToInt(path), @ptrToInt(argv), @ptrToInt(envp)); | 554 | return errnoWrap(c.execve(path, argv, envp)); |
| 558 | } | 555 | } |
| 559 | | 556 | |
| 560 | pub fn fork() usize { | 557 | pub fn fork() usize { |
| 561 | return arch.syscall0(SYS_fork); | 558 | return errnoWrap(c.fork()); |
| 562 | } | 559 | } |
| 563 | | 560 | |
| 564 | pub fn access(path: [*]const u8, mode: u32) usize { | 561 | pub fn access(path: [*]const u8, mode: u32) usize { |
| ... | @@ -566,7 +563,7 @@ pub fn access(path: [*]const u8, mode: u32) usize { | ... | @@ -566,7 +563,7 @@ pub fn access(path: [*]const u8, mode: u32) usize { |
| 566 | } | 563 | } |
| 567 | | 564 | |
| 568 | pub fn getcwd(buf: [*]u8, size: usize) usize { | 565 | pub fn getcwd(buf: [*]u8, size: usize) usize { |
| 569 | return arch.syscall2(SYS___getcwd, @ptrToInt(buf), size); | 566 | return if (c.getcwd(buf, size) == null) @bitCast(usize, -isize(c._errno().*)) else 0; |
| 570 | } | 567 | } |
| 571 | | 568 | |
| 572 | pub fn getdents(fd: i32, dirp: [*]u8, count: usize) usize { | 569 | pub fn getdents(fd: i32, dirp: [*]u8, count: usize) usize { |
| ... | @@ -578,40 +575,48 @@ pub fn getdirentries(fd: i32, buf_ptr: [*]u8, buf_len: usize, basep: *i64) usize | ... | @@ -578,40 +575,48 @@ pub fn getdirentries(fd: i32, buf_ptr: [*]u8, buf_len: usize, basep: *i64) usize |
| 578 | } | 575 | } |
| 579 | | 576 | |
| 580 | pub fn isatty(fd: i32) bool { | 577 | pub fn isatty(fd: i32) bool { |
| 581 | var wsz: winsize = undefined; | 578 | return c.isatty(fd) != 0; |
| 582 | return arch.syscall3(SYS_ioctl, @bitCast(usize, isize(fd)), TIOCGWINSZ, @ptrToInt(&wsz)) == 0; | | |
| 583 | } | 579 | } |
| 584 | | 580 | |
| 585 | pub fn readlink(noalias path: [*]const u8, noalias buf_ptr: [*]u8, buf_len: usize) usize { | 581 | pub fn readlink(noalias path: [*]const u8, noalias buf_ptr: [*]u8, buf_len: usize) usize { |
| 586 | return arch.syscall3(SYS_readlink, @ptrToInt(path), @ptrToInt(buf_ptr), buf_len); | 582 | return errnoWrap(c.readlink(path, buf_ptr, buf_len)); |
| 587 | } | 583 | } |
| 588 | | 584 | |
| 589 | pub fn mkdir(path: [*]const u8, mode: u32) usize { | 585 | pub fn mkdir(path: [*]const u8, mode: u32) usize { |
| 590 | return arch.syscall2(SYS_mkdir, @ptrToInt(path), mode); | 586 | return errnoWrap(c.mkdir(path, mode)); |
| 591 | } | 587 | } |
| 592 | | 588 | |
| 593 | pub fn mmap(address: ?*u8, length: usize, prot: usize, flags: usize, fd: i32, offset: isize) usize { | 589 | pub fn mmap(address: ?[*]u8, length: usize, prot: usize, flags: u32, fd: i32, offset: isize) usize { |
| 594 | return arch.syscall6(SYS_mmap, @ptrToInt(address), length, prot, flags, @bitCast(usize, isize(fd)), @bitCast(usize, offset)); | 590 | const ptr_result = c.mmap( |
| | 591 | @ptrCast(*c_void, address), |
| | 592 | length, |
| | 593 | @bitCast(c_int, @intCast(c_uint, prot)), |
| | 594 | @bitCast(c_int, c_uint(flags)), |
| | 595 | fd, |
| | 596 | offset, |
| | 597 | ); |
| | 598 | const isize_result = @bitCast(isize, @ptrToInt(ptr_result)); |
| | 599 | return errnoWrap(isize_result); |
| 595 | } | 600 | } |
| 596 | | 601 | |
| 597 | pub fn munmap(address: usize, length: usize) usize { | 602 | pub fn munmap(address: usize, length: usize) usize { |
| 598 | return arch.syscall2(SYS_munmap, address, length); | 603 | return errnoWrap(c.munmap(@intToPtr(*c_void, address), length)); |
| 599 | } | 604 | } |
| 600 | | 605 | |
| 601 | pub fn read(fd: i32, buf: [*]u8, count: usize) usize { | 606 | pub fn read(fd: i32, buf: [*]u8, nbyte: usize) usize { |
| 602 | return arch.syscall3(SYS_read, @bitCast(usize, isize(fd)), @ptrToInt(buf), count); | 607 | return errnoWrap(c.read(fd, @ptrCast(*c_void, buf), nbyte)); |
| 603 | } | 608 | } |
| 604 | | 609 | |
| 605 | pub fn rmdir(path: [*]const u8) usize { | 610 | pub fn rmdir(path: [*]const u8) usize { |
| 606 | return arch.syscall1(SYS_rmdir, @ptrToInt(path)); | 611 | return errnoWrap(c.rmdir(path)); |
| 607 | } | 612 | } |
| 608 | | 613 | |
| 609 | pub fn symlink(existing: [*]const u8, new: [*]const u8) usize { | 614 | pub fn symlink(existing: [*]const u8, new: [*]const u8) usize { |
| 610 | return arch.syscall2(SYS_symlink, @ptrToInt(existing), @ptrToInt(new)); | 615 | return errnoWrap(c.symlink(existing, new)); |
| 611 | } | 616 | } |
| 612 | | 617 | |
| 613 | pub fn pread(fd: i32, buf: [*]u8, count: usize, offset: usize) usize { | 618 | pub fn pread(fd: i32, buf: [*]u8, nbyte: usize, offset: u64) usize { |
| 614 | return arch.syscall4(SYS_pread, @bitCast(usize, isize(fd)), @ptrToInt(buf), count, offset); | 619 | return errnoWrap(c.pread(fd, @ptrCast(*c_void, buf), nbyte, offset)); |
| 615 | } | 620 | } |
| 616 | | 621 | |
| 617 | pub fn preadv(fd: i32, iov: [*]const iovec, count: usize, offset: usize) usize { | 622 | pub fn preadv(fd: i32, iov: [*]const iovec, count: usize, offset: usize) usize { |
| ... | @@ -622,16 +627,17 @@ pub fn pipe(fd: *[2]i32) usize { | ... | @@ -622,16 +627,17 @@ pub fn pipe(fd: *[2]i32) usize { |
| 622 | return pipe2(fd, 0); | 627 | return pipe2(fd, 0); |
| 623 | } | 628 | } |
| 624 | | 629 | |
| 625 | pub fn pipe2(fd: *[2]i32, flags: usize) usize { | 630 | pub fn pipe2(fd: *[2]i32, flags: u32) usize { |
| 626 | return arch.syscall2(SYS_pipe2, @ptrToInt(fd), flags); | 631 | comptime assert(i32.bit_count == c_int.bit_count); |
| | 632 | return errnoWrap(c.pipe2(@ptrCast(*[2]c_int, fd), flags)); |
| 627 | } | 633 | } |
| 628 | | 634 | |
| 629 | pub fn write(fd: i32, buf: [*]const u8, count: usize) usize { | 635 | pub fn write(fd: i32, buf: [*]const u8, nbyte: usize) usize { |
| 630 | return arch.syscall3(SYS_write, @bitCast(usize, isize(fd)), @ptrToInt(buf), count); | 636 | return errnoWrap(c.write(fd, @ptrCast(*const c_void, buf), nbyte)); |
| 631 | } | 637 | } |
| 632 | | 638 | |
| 633 | pub fn pwrite(fd: i32, buf: [*]const u8, count: usize, offset: usize) usize { | 639 | pub fn pwrite(fd: i32, buf: [*]const u8, nbyte: usize, offset: u64) usize { |
| 634 | return arch.syscall4(SYS_pwrite, @bitCast(usize, isize(fd)), @ptrToInt(buf), count, offset); | 640 | return errnoWrap(c.pwrite(fd, @ptrCast(*const c_void, buf), nbyte, offset)); |
| 635 | } | 641 | } |
| 636 | | 642 | |
| 637 | pub fn pwritev(fd: i32, iov: [*]const iovec_const, count: usize, offset: usize) usize { | 643 | pub fn pwritev(fd: i32, iov: [*]const iovec_const, count: usize, offset: usize) usize { |
| ... | @@ -639,11 +645,11 @@ pub fn pwritev(fd: i32, iov: [*]const iovec_const, count: usize, offset: usize) | ... | @@ -639,11 +645,11 @@ pub fn pwritev(fd: i32, iov: [*]const iovec_const, count: usize, offset: usize) |
| 639 | } | 645 | } |
| 640 | | 646 | |
| 641 | pub fn rename(old: [*]const u8, new: [*]const u8) usize { | 647 | pub fn rename(old: [*]const u8, new: [*]const u8) usize { |
| 642 | return arch.syscall2(SYS_rename, @ptrToInt(old), @ptrToInt(new)); | 648 | return errnoWrap(c.rename(old, new)); |
| 643 | } | 649 | } |
| 644 | | 650 | |
| 645 | pub fn open(path: [*]const u8, flags: u32, perm: usize) usize { | 651 | pub fn open(path: [*]const u8, flags: u32, mode: usize) usize { |
| 646 | return arch.syscall3(SYS_open, @ptrToInt(path), flags, perm); | 652 | return errnoWrap(c.open(path, @bitCast(c_int, flags), mode)); |
| 647 | } | 653 | } |
| 648 | | 654 | |
| 649 | pub fn create(path: [*]const u8, perm: usize) usize { | 655 | pub fn create(path: [*]const u8, perm: usize) usize { |
| ... | @@ -655,20 +661,19 @@ pub fn openat(dirfd: i32, path: [*]const u8, flags: usize, mode: usize) usize { | ... | @@ -655,20 +661,19 @@ pub fn openat(dirfd: i32, path: [*]const u8, flags: usize, mode: usize) usize { |
| 655 | } | 661 | } |
| 656 | | 662 | |
| 657 | pub fn close(fd: i32) usize { | 663 | pub fn close(fd: i32) usize { |
| 658 | return arch.syscall1(SYS_close, @bitCast(usize, isize(fd))); | 664 | return errnoWrap(c.close(fd)); |
| 659 | } | 665 | } |
| 660 | | 666 | |
| 661 | pub fn lseek(fd: i32, offset: isize, ref_pos: usize) usize { | 667 | pub fn lseek(fd: i32, offset: isize, whence: c_int) usize { |
| 662 | return arch.syscall3(SYS_lseek, @bitCast(usize, isize(fd)), @bitCast(usize, offset), ref_pos); | 668 | return errnoWrap(c.lseek(fd, offset, whence)); |
| 663 | } | 669 | } |
| 664 | | 670 | |
| 665 | pub fn exit(status: i32) noreturn { | 671 | pub fn exit(code: i32) noreturn { |
| 666 | _ = arch.syscall1(SYS_exit, @bitCast(usize, isize(status))); | 672 | c.exit(code); |
| 667 | unreachable; | | |
| 668 | } | 673 | } |
| 669 | | 674 | |
| 670 | pub fn getrandom(buf: [*]u8, count: usize, flags: u32) usize { | 675 | pub fn getrandom(buf: [*]u8, count: usize, flags: u32) usize { |
| 671 | return arch.syscall3(SYS_getrandom, @ptrToInt(buf), count, usize(flags)); | 676 | return errnoWrap(c.getrandom(buf, count, flags)); |
| 672 | } | 677 | } |
| 673 | | 678 | |
| 674 | pub fn kill(pid: i32, sig: i32) usize { | 679 | pub fn kill(pid: i32, sig: i32) usize { |
| ... | @@ -676,15 +681,16 @@ pub fn kill(pid: i32, sig: i32) usize { | ... | @@ -676,15 +681,16 @@ pub fn kill(pid: i32, sig: i32) usize { |
| 676 | } | 681 | } |
| 677 | | 682 | |
| 678 | pub fn unlink(path: [*]const u8) usize { | 683 | pub fn unlink(path: [*]const u8) usize { |
| 679 | return arch.syscall1(SYS_unlink, @ptrToInt(path)); | 684 | return errnoWrap(c.unlink(path)); |
| 680 | } | 685 | } |
| 681 | | 686 | |
| 682 | pub fn waitpid(pid: i32, status: *i32, options: i32) usize { | 687 | pub fn waitpid(pid: i32, status: *i32, options: u32) usize { |
| 683 | return arch.syscall4(SYS_wait4, @bitCast(usize, isize(pid)), @ptrToInt(status), @bitCast(usize, isize(options)), 0); | 688 | comptime assert(i32.bit_count == c_int.bit_count); |
| | 689 | return errnoWrap(c.waitpid(pid, @ptrCast(*c_int, status), @bitCast(c_int, options))); |
| 684 | } | 690 | } |
| 685 | | 691 | |
| 686 | pub fn nanosleep(req: *const timespec, rem: ?*timespec) usize { | 692 | pub fn nanosleep(req: *const timespec, rem: ?*timespec) usize { |
| 687 | return arch.syscall2(SYS_nanosleep, @ptrToInt(req), @ptrToInt(rem)); | 693 | return errnoWrap(c.nanosleep(req, rem)); |
| 688 | } | 694 | } |
| 689 | | 695 | |
| 690 | pub fn setuid(uid: u32) usize { | 696 | pub fn setuid(uid: u32) usize { |
| ... | @@ -696,11 +702,11 @@ pub fn setgid(gid: u32) usize { | ... | @@ -696,11 +702,11 @@ pub fn setgid(gid: u32) usize { |
| 696 | } | 702 | } |
| 697 | | 703 | |
| 698 | pub fn setreuid(ruid: u32, euid: u32) usize { | 704 | pub fn setreuid(ruid: u32, euid: u32) usize { |
| 699 | return arch.syscall2(SYS_setreuid, ruid, euid); | 705 | return errnoWrap(c.setreuid(ruid, euid)); |
| 700 | } | 706 | } |
| 701 | | 707 | |
| 702 | pub fn setregid(rgid: u32, egid: u32) usize { | 708 | pub fn setregid(rgid: u32, egid: u32) usize { |
| 703 | return arch.syscall2(SYS_setregid, rgid, egid); | 709 | return errnoWrap(c.setregid(rgid, egid)); |
| 704 | } | 710 | } |
| 705 | | 711 | |
| 706 | const NSIG = 32; | 712 | const NSIG = 32; |
| ... | @@ -745,26 +751,16 @@ pub const sigset_t = extern struct { | ... | @@ -745,26 +751,16 @@ pub const sigset_t = extern struct { |
| 745 | }; | 751 | }; |
| 746 | | 752 | |
| 747 | pub fn raise(sig: i32) usize { | 753 | pub fn raise(sig: i32) usize { |
| 748 | // TODO have a chat with the freebsd folks and make sure there's no bug in | 754 | return errnoWrap(c.raise(sig)); |
| 749 | // their libc. musl-libc blocks signals in between these calls because | | |
| 750 | // if a signal handler runs and forks between the gettid and sending the | | |
| 751 | // signal, the parent will get 2 signals, one from itself and one from the child | | |
| 752 | // if the protection does not belong here, then it belongs in abort(), | | |
| 753 | // like it does in freebsd's libc. | | |
| 754 | var id: usize = undefined; | | |
| 755 | const rc = arch.syscall1(SYS_thr_self, @ptrToInt(&id)); | | |
| 756 | if (getErrno(rc) != 0) return rc; | | |
| 757 | return arch.syscall2(SYS_thr_kill, id, @bitCast(usize, isize(sig))); | | |
| 758 | } | 755 | } |
| 759 | | 756 | |
| 760 | pub const Stat = c.Stat; | 757 | pub const Stat = c.Stat; |
| 761 | pub const dirent = c.dirent; | 758 | pub const dirent = c.dirent; |
| 762 | pub const timespec = c.timespec; | 759 | pub const timespec = c.timespec; |
| 763 | | 760 | |
| 764 | pub fn fstat(fd: i32, stat_buf: *Stat) usize { | 761 | pub fn fstat(fd: i32, buf: *c.Stat) usize { |
| 765 | return arch.syscall2(SYS_fstat, @bitCast(usize, isize(fd)), @ptrToInt(stat_buf)); | 762 | return errnoWrap(c.fstat(fd, buf)); |
| 766 | } | 763 | } |
| 767 | | | |
| 768 | pub const iovec = extern struct { | 764 | pub const iovec = extern struct { |
| 769 | iov_base: [*]u8, | 765 | iov_base: [*]u8, |
| 770 | iov_len: usize, | 766 | iov_len: usize, |