start.S 1.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455
  1. /* -*- mode:c; c-basic-offset:4; tab-width:4; indent-tabs-mode:t; mode:auto-fill; fill-column:78; -*- */
  2. /* vim: set ts=4 sw=4 et tw=78 fo=cqt wm=0: */
  3. /* This is the canonical entry point, usually the first thing in the text
  4. segment. The SVR4/i386 ABI (pages 3-31, 3-32) says that when the entry
  5. point runs, most registers' values are unspecified, except for:
  6. %rdx Contains a function pointer to be registered with `atexit'.
  7. This is how the dynamic linker arranges to have DT_FINI
  8. functions called for shared libraries that have been loaded
  9. before this code runs.
  10. %rsp The stack contains the arguments and environment:
  11. 0(%rsp) argc
  12. 8(%rsp) argv[0]
  13. ...
  14. (8*argc)(%rsp) NULL
  15. (8*(argc+1))(%rsp) envp[0]
  16. ...
  17. NULL
  18. */
  19. .text
  20. .globl shim_start
  21. .type shim_start,@function
  22. shim_start:
  23. .cfi_startproc
  24. /* Clear the frame pointer. The ABI suggests this be done, to mark
  25. the outermost frame obviously. */
  26. xorq %rbp, %rbp
  27. movq %rsp, %rbp
  28. /* Extract the arguments as encoded on the stack and set up
  29. the arguments for shim_init (int, void *, void **),
  30. The arguments are passed via registers and on the stack:
  31. argc: %rdi
  32. argv: %rsi
  33. */
  34. /* Align the stack to a 16 byte boundary to follow the ABI. */
  35. andq $~15, %rsp
  36. movq %rdi, %rcx /* Possibly the stack has to be switched */
  37. movq 0(%rbp), %rdi /* Pop the argument count. */
  38. leaq 8(%rbp), %rsi /* argv starts just at the current stack top. */
  39. pushq %rdx
  40. movq shim_init@GOTPCREL(%rip), %r11
  41. call *%r11
  42. retq
  43. .cfi_endproc