asmttpd icon indicating copy to clipboard operation
asmttpd copied to clipboard

if you want to port on Mac OS : Syscall

Open smougel opened this issue 10 years ago • 22 comments

http://www.opensource.apple.com/source/xnu/xnu-1456.1.26/bsd/kern/syscalls.master

smougel avatar Feb 03 '14 22:02 smougel

Thanks. I don't have a mac at the moment, so it could be a while. Is there a cross assembler or some sort of development environment for mac that will work on Linux?

nemasu avatar Feb 04 '14 03:02 nemasu

nasm -f macho -o output should create a mach-o style binary. GNU assembler/linker should be able to do this if the option wasn't disabled by your distro (some do this to save space on the binary). As long as the mac is the same micro-architecture as where you're developing it, you should be able to create binaries with just a change of format, not a cross compiler.

DavidJFelix avatar Feb 04 '14 18:02 DavidJFelix

I was hacking on this a little, I'll upstream some of my patches. The first step was to get everything to build, which I have.

nickdesaulniers avatar May 19 '15 22:05 nickdesaulniers

syscall IDs used:

name Linux Apple same fn signature
write 1 4 :white_check_mark:
open 2 5 :white_check_mark:
close 3 6 :white_check_mark:
lseek 8 199
mmap 9 197
sigaction 13 46 :white_check_mark:
select 23 93
nanosleep 35 334?
sendfile 40 337
socket 41 97
accept 43 30
sendto 44 133
recvfrom 45 29
bind 49 104
listen 50 106
setsockopts 54 105
clone 56 360?
exit 60 1
getdents 78 196?
exit_group 231 :x:

note getdents defined but not used??

nickdesaulniers avatar May 20 '15 21:05 nickdesaulniers

I think we should use the preprocessor to check for OS specific symbols and have conditional assembling. example

nickdesaulniers avatar May 20 '15 22:05 nickdesaulniers

looks like the system call number need to be shifted. I have verified this, will try to find more info as to why: https://filippo.io/making-system-calls-from-assembly-in-mac-os-x/ edit: see also: http://dustin.schultz.io/blog/2010/11/15/mac-os-x-64-bit-assembly-system-calls/

nickdesaulniers avatar Jan 20 '16 07:01 nickdesaulniers

I'm able to get the usage warning printing! w00t

nickdesaulniers avatar Jan 20 '16 18:01 nickdesaulniers

does linux pass command line args on the stack? https://github.com/nemasu/asmttpd/blob/master/main.asm#L53-L58

When I inspect the registers on entry, %rdi is argc and %rsi is argv. The current code looks like it pulls them off the stack. Calling print_line with start_text blows away %rdi and %rsi.

nickdesaulniers avatar Jan 20 '16 18:01 nickdesaulniers

argv and argc are passed on the stack.

But for Linux system calls it uses registers first, then stack:

https://github.com/nemasu/asmttpd/blob/master/main.asm#L28

Which is what I use internally too.

nemasu avatar Jan 21 '16 02:01 nemasu

argv and argc are passed on the stack.

right, but it doesn't look to be the case for Mach-O binaries. Asking an friend who's an LLVM dev to confirm.

I'll need this for OSX's equivalent to nanosleep: https://opensource.apple.com/source/Libc/Libc-583/gen/nanosleep.c

nickdesaulniers avatar Jan 21 '16 18:01 nickdesaulniers

err, they're passed on the stack for 32b programs on Linux/OSX and in %rdi and %rsi for 64b programs.

The makefile makes it looks like you're compiling a 64b binary, so why are argc/argv being popped off the stack?

nickdesaulniers avatar Jan 21 '16 21:01 nickdesaulniers

According to the AMD64 ABi doc, http://www.x86-64.org/documentation/abi.pdf, page 29, argv and argc are passed on the stack.

nemasu avatar Jan 21 '16 22:01 nemasu

If we take a look at the dissasembly on OSX:

Disassembly of section .text:

0000000100000f60 <_main>:
#include <stdio.h>
int main (int argc, char** argv) {
   100000f60:   55                      push   %rbp
   100000f61:   48 89 e5                mov    %rsp,%rbp
  puts(argv[0]);
   100000f64:   48 8b 3e                mov    (%rsi),%rdi [hello! taking argv[0] from %rsi and putting in %rdi for puts]
   100000f67:   e8 04 00 00 00          callq  100000f70 <_main+0x10>
   100000f6c:   31 c0                   xor    %eax,%eax
}

even on Linux:

00000000004004f0 <main>:
#include <stdio.h>
int main (int argc, char** argv) {
  puts(argv[0]);
  4004f0:   50                      push   %rax
  4004f1:   48 8b 3e                mov    (%rsi),%rdi [SAME!!]
  4004f4:   e8 c7 fe ff ff          callq  4003c0 <puts@plt>
  4004f9:   31 c0                   xor    %eax,%eax
}

Unless _start is pulling things off the stack and into registers before calling into _main.

nickdesaulniers avatar Feb 29 '16 01:02 nickdesaulniers

Unless _start is pulling things off the stack and into registers before calling into _main.

That MUST be the case. Without the -osx_min_version flag to ld, arguments are indeed passed on stack to _start. Ok, I'll carry on.

nickdesaulniers avatar Feb 29 '16 03:02 nickdesaulniers

For my reference, man syscall and /usr/include/sys/syscall.h are helpful!

nickdesaulniers avatar Feb 29 '16 03:02 nickdesaulniers

Looks like _start is defined in /usr/lib/crt1.o, which should be linked against, according to man 1 ld.

nickdesaulniers avatar Mar 05 '16 06:03 nickdesaulniers

I've got a lot more of this working. The real work will be pthread_create (processes and threads are created with clone(2) on Linux, not so on OSX), and nanosleep (nanosleep(2) on Linux, __semwait_signal on OSX). I think I'll need to link against libc for OSX to get the address of clock_sem.

nickdesaulniers avatar Mar 06 '16 23:03 nickdesaulniers

pthread_create:

  • proc_info
  • bsdthread_create
  • thread_selfid

pthread_join:

  • __disable_threadsignal
  • __semwait_signal

nickdesaulniers avatar Mar 06 '16 23:03 nickdesaulniers

gcc on mac works, so you can use as as assembler.

DmitryHetman avatar Feb 07 '17 15:02 DmitryHetman

as - Portable GNU assembler.

DmitryHetman avatar Feb 07 '17 15:02 DmitryHetman

What is your point? Both comments seem unrelated. See my comment about nanosleep and clone. Also, I sold off my last piece of Mac hardware, so I will no longer be pursuing this issue. :(

nickdesaulniers avatar Feb 08 '17 00:02 nickdesaulniers