Kernel Syscalls

Note on these
Args go in their normal registers, like arg1 in R0, as usual. Syscall # goes in IP (that's intra-procedural, not instruction pointer!), a.k.a R12.

As in all ARM (i.e. also on Android) the kernel entry is accomplished by the SVC command (SWI in some debuggers and ARM dialects). On the kernel end, a low level CPU exception handler (fleh_swi) is installed as part of the ExceptionVectorsBase, and - upon issuing a SWI/SVC - control is transferred to that address. This handler can check the syscall number to distinguish between POSIX calls (non negative) and Mach traps (negative).

Usage
MOV IP, #x // number from following list into Intraprocedural, a.k.a. r12 SVC 0x80  // Formerly, SWI (software interrupt)

For example:

(gdb) disass chown 0x30d2ad54 :	mov	r12, #16	      ; 0x10, being # of chown 0x30d2ad58 :	svc	0x00000080

Most of these are the same as you would find in the XNU open source kernel, with ARM idiosyncrasies aside (and #372, ledger)

sysent
The system call table in XNU is known as "sysent", and is no longer a public symbol, for obvious reasons (e.g. syscall hooking). It is fairly straightforward, however, to find the sysent and its calls. While i0nic proposes a heuristic of finding the sysent based on the exported kdebug symbol, this is unreliable, as the symbol is no longer exported. A better way is to home in on the pattern of the struct sysent entries itself, i.e - as defined in bsd/sys/sysent.h:

struct sysent {        /* system call table */ int16_t        sy_narg;        /* number of args */ int8_t         sy_resv;        /* reserved  */ int8_t         sy_flags;       /* flags */ sy_call_t      *sy_call;       /* implementing function */ sy_munge_t     *sy_arg_munge32; /* system call arguments munger for 32-bit process */ sy_munge_t     *sy_arg_munge64; /* system call arguments munger for 64-bit process */ int32_t        sy_return_type; /* system call return types */ uint16_t       sy_arg_bytes;   /* Total size of arguments in bytes for * 32-bit system calls */ };

Because system calls arguments are set in stone, it is straightforward to write code to find the signature of the first few syscalls (syscall, exit, fork..), and from there calculate the other sysent entries. A program to do so reliable on iOS has, in fact, been written, and produces the following output for iOS 6.0b1:

List of system calls from iOS 6.0b1
'''note: Even though a syscall is present in the table, it does not in any way imply it is functional. Auditing, for example, is not enabled in iOS (no CONFIG_AUDIT in the XNU build). Most of these syscalls are the same as those of OS X, with the exception of ledger (which actually makes a comeback in OS X Mountain Lion), and 434+ (CONFIG_EMBEDDED).

$ ./fsysent ~/Documents/projects/iOS.6.0b1.iPod4.kernel mach_trap_table offset in file (for patching purposes): 3064992 (0x2ec4a0) Sysent offset in file (for patching purposes): 3076288 (0x2ef0c0) This appears to be XNU 2107.1.78 Suppressing enosys (801e9d5c)

1. exit                801d32dc T 2. fork                 801d61d4 T 3. read                 801e9d7c T 4. write                801ea150 T 5. open                 800b12f0 T 6. close                801cb904 T 7. wait4                801d3f10 T 9. link                 800b1804 T 10. unlink              800b1f0c T 12. chdir               800b0be0 T 13. fchdir              800b0a70 T 14. mknod               800b13d8 T 15. chmod               800b2a5c T 16. chown               800b2bb8 T 18. getfsstat           800b080c T 20. getpid              801daa60 T 23. setuid              801dad14 T 24. getuid              801daae4 T 25. geteuid             801daaf4 T 26. ptrace              801e6924 T 27. recvmsg             802090f4 T 28. sendmsg             80208c3c T 29. recvfrom            80208d20 T 30. accept              802085f4 T 31. getpeername         802093c0 T 32. getsockname         80209310 T 33. access              800b23c8 T 34. chflags             800b2844 T 35. fchflags            800b290c T 36. sync                800b02a0 T 37. kill                801de620 T 39. getppid             801daa68 T 41. dup                 801c9a94 T 42. pipe                801ec3dc T 43. getegid             801dab6c T 46. sigaction           801dd73c T 47. getgid              801dab5c T 48. sigprocmask         801ddc80 T 49. getlogin            801db93c T 50. setlogin            801db9b4 T 51. acct                801c447c T 52. sigpending          801dde24 T 53. sigaltstack         801de564 T 54. ioctl               801ea514 T 55. reboot              801e6888 T 56. revoke              800b4320 T 57. symlink             800b1a74 T 58. readlink            800b2748 T 59. execve              801d2cb0 T 60. umask               800b42f8 T 61. chroot              800b0cb0 T 65. msync               801d6d24 T 66. vfork               801d586c T 73. munmap              801d6dd0 T 74. mprotect            801d6e04 T 75. madvise             801d6ebc T 78. mincore             801d6f28 T 79. getgroups           801dab7c T 80. setgroups           801db880 T 81. getpgrp             801daa70 T 82. setpgid             801dac1c T 83. setitimer           801e6370 T 85. swapon              8021a638 T 86. getitimer           801e6228 T 89. getdtablesize       801c966c T 90. dup2                801c9ec0 T 92. fcntl               801ca2d8 T 93. select              801ea7c0 T 95. fsync               800b3154 T 96. setpriority         801dbce8 T 97. socket              8020809c T 98. connect             80208614 T 100. getpriority         801dbbdc T 104. bind                80208168 T 105. setsockopt          80209228 T 106. listen              802082d4 T 111. sigsuspend          801dde4c T 116. gettimeofday        801e6038 T 117. getrusage           801dca80 T 118. getsockopt          8020928c T 120. readv               801ea008 T 121. writev              801ea3a8 T 122. settimeofday        801e6094 T 123. fchown              800b2cc8 T 124. fchmod              800b2b8c T 126. setreuid            801db060 T 127. setregid            801db3f4 T 128. rename              800b3344 T 131. flock               801cce8c T 132. mkfifo              800b16b4 T 133. sendto              80208960 T 134. shutdown            802091f8 T 135. socketpair          80208804 T 136. mkdir               800b3c38 T 137. rmdir               800b3c78 T 138. utimes              800b2d7c T 139. futimes             800b2f50 T 140. adjtime             801e6198 T 142. gethostuuid         801ebe9c T 147. setsid              801dabd8 T 151. getpgid             801daa78 T 152. setprivexec         801daa48 T 153. pread               801e9f6c T 154. pwrite              801ea2c8 T 157. statfs              800b0340 T 158. fstatfs             800b05f8 T 159. unmount             800afe08 T 165. quotactl            800b033c T 167. mount               800aefe8 T 169. csops               801d9824 T 170. 170 old table       801d9d10 T 173. waitid              801d4308 T 180. kdebug_trace        801c1d58 T 181. setgid              801db1f8 T 182. setegid             801db304 T 183. seteuid             801daf64 T 184. sigreturn           8021cfa8 T 185. chud                8021bcb8 T 187. fdatasync           800b31cc T 188. stat                800b24a4 T 189. fstat               801cbb98 T 190. lstat               800b25f0 T 191. pathconf            800b26e4 T 192. fpathconf           801cbbf4 T 194. getrlimit           801dc8c8 T 195. setrlimit           801dc190 T 196. getdirentries       800b3eb0 T 197. mmap                801d6814 T 199. lseek               800b1f84 T 200. truncate            800b2fd0 T 201. ftruncate           800b3090 T 202. __sysctl            801e0ccc T 203. mlock               801d7074 T 204. munlock             801d70cc T 205. undelete            800b1c0c T 216. mkcomplex           800b1224 T 220. getattrlist         8009afe0 T 221. setattrlist         8009b058 T 222. getdirentriesattr   800b4408 T 223. exchangedata        800b45c4 T 225. searchfs            800b4804 T 226. delete              800b1f48 T 227. copyfile            800b31e8 T 228. fgetattrlist        80098408 T 229. fsetattrlist        8009b760 T 230. poll                801eaf24 T 231. watchevent          801eb84c T 232. waitevent           801eb9f0 T 233. modwatch            801ebb60 T 234. getxattr            800b5478 T 235. fgetxattr           800b55b4 T 236. setxattr            800b56b4 T 237. fsetxattr           800b57c0 T 238. removexattr         800b58bc T 239. fremovexattr        800b5984 T 240. listxattr           800b5a44 T 241. flistxattr          800b5b28 T 242. fsctl               800b4cfc T 243. initgroups          801db6fc T 244. posix_spawn         801d1d74 T 245. ffsctl              800b539c T 250. minherit            801d6e84 T 266. shm_open            8020d2c0 T 267. shm_unlink          8020dda0 T 268. sem_open            8020c718 T 269. sem_close           8020ceb0 T 270. sem_unlink          8020cc78 T 271. sem_wait            8020cf08 T 272. sem_trywait         8020cfd0 T 273. sem_post            8020d074 T 274. sem_getvalue        8020d118 T 275. sem_init            8020d110 T 276. sem_destroy         8020d114 T 277. open_extended       800b1144 T 278. umask_extended      800b42a8 T 279. stat_extended       800b244c T 280. lstat_extended      800b2598 T 281. fstat_extended      801cb97c T 282. chmod_extended      800b294c T 283. fchmod_extended     800b2a90 T 284. access_extended     800b20bc T 285. settid              801db580 T 286. gettid              801dab04 T 287. setsgroups          801db890 T 288. getsgroups          801dabd0 T 289. setwgroups          801db894 T 290. getwgroups          801dabd4 T 291. mkfifo_extended     800b1610 T 292. mkdir_extended      800b3a4c T 294. shared_region_check_np 8021ab68 T 296. vm_pressure_monitor 8021b2cc T 297. psynch_rw_longrdlock 8021415c T 298. psynch_rw_yieldwrlock 80214408 T 299. psynch_rw_downgrade 80214410 T 300. psynch_rw_upgrade   8021440c T 301. psynch_mutexwait    80211374 T 302. psynch_mutexdrop    80212338 T 303. psynch_cvbroad      8021238c T 304. psynch_cvsignal     80212970 T 305. psynch_cvwait       80212df8 T 306. psynch_rw_rdlock    80213530 T 307. psynch_rw_wrlock    80214160 T 308. psynch_rw_unlock    80214414 T 309. psynch_rw_unlock2   8021470c T 310. getsid              801daaa8 T 311. settid_with_pid     801db620 T 312. psynch_cvclrprepost 80213430 T 313. aio_fsync           801c4e60 T 314. aio_return          801c5038 T 315. aio_suspend         801c52c0 T 316. aio_cancel          801c49d8 T 317. aio_error           801c4db4 T 318. aio_read            801c5018 T 319. aio_write           801c54d4 T 320. lio_listio          801c54f4 T 322. iopolicysys         801dcc74 T 323. process_policy      80218edc T 324. mlockall            801d7108 T 325. munlockall          801d710c T 327. issetugid           801dad04 T 328. __pthread_kill      801de298 T 329. __pthread_sigmask   801de2f8 T 330. __sigwait           801de3a8 T 331. __disable_threadsignal 801ddf74 T 332. __pthread_markcancel 801ddf90 T 333. __pthread_canceled  801ddfd8 T 334. __semwait_signal    801de178 T 336. proc_info           80216dc0 T 338. stat64              800b24f0 T 339. fstat64             801cbbd4 T 340. lstat64             800b263c T 341. stat64_extended     800b2540 T 342. lstat64_extended    800b268c T 343. fstat64_extended    801cbbb8 T 344. getdirentries64     800b4268 T 345. statfs64            800b0660 T 346. fstatfs64           800b07a8 T 347. getfsstat64         800b09b8 T 348. __pthread_chdir     800b0ca8 T 349. __pthread_fchdir    800b0bd8 T 350. audit               801c0a18 T 351. auditon             801c0a1c T 353. getauid             801c0a20 T 354. setauid             801c0a24 T 357. getaudit_addr       801c0a28 T 358. setaudit_addr       801c0a2c T 359. auditctl            801c0a30 T 360. bsdthread_create    80215260 T 361. bsdthread_terminate 802154d8 T 362. kqueue              801cddec T 363. kevent              801cde6c T 364. lchown              800b2cb0 T 365. stack_snapshot      801c41a0 T 366. bsdthread_register  8021553c T 367. workq_open          80216190 T 368. workq_kernreturn    802165f8 T 369. kevent64            801ce104 T 370. __old_semwait_signal 801de04c T 371. __old_semwait_signal_nocancel 801de080 T 372. thread_selfid       80216afc T 373. ledger              801ebf04 T 380. __mac_execve        801d2cd0 T 381. __mac_syscall       8027b874 T 382. __mac_get_file      8027b51c T 383. __mac_set_file      8027b764 T 384. __mac_get_link      8027b640 T 385. __mac_set_link      8027b864 T 386. __mac_get_proc      8027b010 T 387. __mac_set_proc      8027b0d0 T 388. __mac_get_fd        8027b3c8 T 389. __mac_set_fd        8027b650 T 390. __mac_get_pid       8027af44 T 391. __mac_get_lcid      8027b184 T 392. __mac_get_lctx      8027b248 T 393. __mac_set_lctx      8027b304 T 394. setlcid             801dba7c T 395. getlcid             801dbb64 T 396. read_nocancel       801e9d9c T 397. write_nocancel      801ea170 T 398. open_nocancel       800b1368 T 399. close_nocancel      801cb920 T 400. wait4_nocancel      801d3f30 T 401. recvmsg_nocancel    80209114 T 402. sendmsg_nocancel    80208c5c T 403. recvfrom_nocancel   80208d40 T 404. accept_nocancel     80208314 T 405. msync_nocancel      801d6d3c T 406. fcntl_nocancel      801ca2f8 T 407. select_nocancel     801ea7dc T 408. fsync_nocancel      800b31c4 T 409. connect_nocancel    8020862c T 410. sigsuspend_nocancel 801ddf08 T 411. readv_nocancel      801ea028 T 412. writev_nocancel     801ea3c8 T 413. sendto_nocancel     80208980 T 414. pread_nocancel      801e9f8c T 415. pwrite_nocancel     801ea2e8 T 416. waitid_nocancel     801d4324 T 417. poll_nocancel       801eaf44 T 420. sem_wait_nocancel   8020cf24 T 421. aio_suspend_nocancel 801c52e0 T 422. __sigwait_nocancel  801de3e0 T 423. __semwait_signal_nocancel 801de1ac T 424. __mac_mount         800af00c T 425. __mac_get_mount     8027ba6c T 426. __mac_getfsstat     800b0830 T 427. fsgetpath           800b5c0c T 428. audit_session_self  801c0a0c T 429. audit_session_join  801c0a10 T 430. fileport_makeport   801ccf70 T 431. fileport_makefd     801cd0f4 T 432. audit_session_port  801c0a14 T 433. pid_suspend         8021a950 T 434. pid_resume          8021a9c0 T 435. pid_hibernate       8021aa2c T 436. pid_shutdown_sockets 8021aa84 T 438. shared_region_map_and_slide_np 8021b118 T 439. kas_info            8021b314 T             ; Provides ASLR information to user space (JB: Hint, Hint!) 440. memorystatus_control 801e4aa4 T            ; Controls memory status  (JetSam)

Mach
XNU also supports the Mach personality, which is distinct from that of the UNIX syscalls discussed above. Mach syscalls (on 32-bit systems like iOS) are encoded as negative numbers, which is clever, since POSIX system calls are all non-negative. For example, consider mach_msg_trap:

_mach_msg_trap: 0001a8b4       e1a0c00d        mov     ip, sp 0001a8b8        e92d0170        push    {r4, r5, r6, r8} 0001a8bc       e89c0070        ldm     ip, {r4, r5, r6} 0001a8c0       e3e0c01e        mvn     ip, #30 @ 0x1e    ; Move NEGATIVE -30 into IP (R12) 0001a8c4       ef000080        svc     0x00000080        ; issue a supervisor call 0001a8c8       e8bd0170        pop     {r4, r5, r6, r8} 0001a8cc       e12fff1e        bx      lr .. _semaphore_signal_all_trap: 0001a8f8       e3e0c021        mvn     ip, #33 @ 0x21   ; NEGATIVE -33 into IP (R12) 0001a8fc       ef000080        svc     0x00000080 0001a900       e12fff1e        bx      lr

Mach system calls are commonly known as "traps", and are maintained in a Mach Trap table. iOS's fleh_swi handler (the kernel entry point on the other side of the "SWI" or "SVC" command) checks the system call number - if it is negative, it is flipped (2's complement), and interpreted as Mach trap instead.

mach_trap_table
In iOS 5.x, the mach_trap_table is not far from the page_size export, and right next to the trap names. kern_invalid is the equivalent of ENOSYS. All the traps are ARM Thumb. The joker binary can be used to find the Mach trap table, as well. The following shows iOS 6.0.b1's table:

$ ./joker -ls mach kernel.iPod4.iOS6.0b1 This is an ARM binary. Applying iOS kernel signatures mach_trap_table offset in file (for patching purposes): 3064992 (0x2ec4a0) Kern invalid should be 0x80027ec1. Ignoring those ..This appears to be XNU 2107.1.78 10 _kernelrpc_mach_vm_allocate_trap        80014460 T 12 _kernelrpc_mach_vm_deallocate_trap       800144cc T 14 _kernelrpc_mach_vm_protect_trap          80014510 T 16 _kernelrpc_mach_port_allocate_trap       80014564 T 17 _kernelrpc_mach_port_destroy_trap        800145b4 T 18 _kernelrpc_mach_port_deallocate_trap     800145f0 T 19 _kernelrpc_mach_port_mod_refs_trap       8001462c T 20 _kernelrpc_mach_port_move_member_trap    8001466c T 21 _kernelrpc_mach_port_insert_right_trap   800146b0 T 22 _kernelrpc_mach_port_insert_member_trap  80014710 T 23 _kernelrpc_mach_port_extract_member_trap 80014754 T 26 mach_reply_port                          8001b5b4 T 27 thread_self_trap                         8001b598 T 28 task_self_trap                           8001b578 T 29 host_self_trap                           80019910 T 31 mach_msg_trap                            80014ec0 T 32 mach_msg_overwrite_trap                  80014d20 T 33 semaphore_signal_trap                    80027188 T 34 semaphore_signal_all_trap                8002720c T 35 semaphore_signal_thread_trap             80027114 T 36 semaphore_wait_trap                      800274b0 T 37 semaphore_wait_signal_trap               80027658 T 38 semaphore_timedwait_trap                 80027598 T 39 semaphore_timedwait_signal_trap          8002773c T 44 task_name_for_pid                        8021a838 T 45 task_for_pid                             8021a688 T 46 pid_for_task                             8021a63c T 48 macx_swapon                              8021b414 T 49 macx_swapoff                             8021b668 T 51 macx_triggers                            8021b3f4 T 52 macx_backing_store_suspend               8021b370 T 53 macx_backing_store_recovery              8021b318 T 58 pfz_exit                                 80027818 T 59 swtch_pri                                800278e4 T 60 swtch                                    8002781c T 61 thread_switch                            80027ad4 T 62 clock_sleep_trap                         80017520 T 89 mach_timebase_info_trap                  80016658 T 90 mach_wait_until_trap                     80016d20 T 91 mk_timer_create_trap                     8001f2f4 T 92 mk_timer_destroy_trap                    8001f500 T 93 mk_timer_arm_trap                        8001f544 T 94 mk_timer_cancel_trap                     8001f5c8 T 100 iokit_user_client_trap                   8026c11c T