macOS 10.13 High Sierra 에서는 기본적인 dyld 는 start 함수가 함수의 시작점이 된다
어셈블러로 start 함수를 작성하여 다른 라이브러리 import 없이 프로그램을 실행할 수 있다
코드 작성
hello2.s
.macosx_version_min 10, 7 .globl start .text
start: mov $0x2000004, %rax mov $1, %rdi movabs $msg, %rsi mov $len, %rdx syscall
mov $0x2000001, %rax mov $0x0, %rdi syscall
.data
msg: .ascii "Hello, World!\n" len = . - msg |
macOS 10.8 부터는 ld 에서 강제적으로 main 함수를 호출하고 있어 macosx_version_min 을 10.7 로 강제로 세팅한다
ld 코드 확인 ( https://opensource.apple.com/source/ld64/ld64-274.2/src/ld/Options.cpp.auto.html )
void Options::reconfigureDefaults() { .................
switch ( fOutputKind ) {
case Options::kDynamicExecutable:
if ( fEntryPointLoadCommandForceOn ) {
fEntryPointLoadCommand = true;
if ( fEntryName == NULL )
fEntryName = "_main";
}
else if ( fEntryPointLoadCommandForceOff ) {
fNeedsThreadLoadCommand = true;
if ( fEntryName == NULL )
fEntryName = "start";
}
else {
if ( minOS(ld::mac10_8, ld::iOS_6_0) || fTargetIOSSimulator ) {
fEntryPointLoadCommand = true;
if ( fEntryName == NULL )
fEntryName = "_main";
if ( strcmp(fEntryName, "start") == 0 ) {
warning("Ignoring '-e start' because entry point 'start' is not used for the targeted OS version");
fEntryName = "_main";
}
}
else {
fNeedsThreadLoadCommand = true;
if ( fEntryName == NULL )
fEntryName = "start";
}
}
break;
.....................
|
macos 10.8 부터 강제로 _main 으로 점프하게 되어 있으며 ld 옵션 -e 옵션으로 지정해 주는 것도 막고 있다.
빌드 방법
as -c hello2.s -o hello2.o
ld -macosx_version_min 10.7 -o hello2 hello2.o
10.8 이상에서는
Undefined symbols for architecture x86_64: "_main", referenced from: implicit entry/start for main executable ld: symbol(s) not found for inferred architecture x86_64 |
_main 함수가 없다는 에러가 발생한다
혹은 no_new_main 옵션을 추가하면 최신 버전에서도 빌드가 잘 된다
ld -macosx_version_min 10.13 -no_new_main -o hello2 hello2.o
해당 옵션은 man page 에서는 보이지 않는다.
아래에 구현되어 있다
else if ( strcmp(arg, "-new_main") == 0 ) { fEntryPointLoadCommandForceOn = true; cannotBeUsedWithBitcode(arg); } else if ( strcmp(arg, "-no_new_main") == 0 ) { fEntryPointLoadCommandForceOff = true; cannotBeUsedWithBitcode(arg); } |
참조: https://stackoverflow.com/questions/24841283/how-can-i-set-a-custom-c-entry-point-with-clang-on-os-x-mavericks