vdso.h 1.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. /* SPDX-License-Identifier: GPL-2.0-or-later */
  2. /*
  3. * Copyright (C) 2015 Imagination Technologies
  4. * Author: Alex Smith <[email protected]>
  5. */
  6. #include <asm/sgidefs.h>
  7. #ifndef __ASSEMBLY__
  8. #include <asm/asm.h>
  9. #include <asm/page.h>
  10. #include <asm/vdso.h>
  11. static inline unsigned long get_vdso_base(void)
  12. {
  13. unsigned long addr;
  14. /*
  15. * We can't use cpu_has_mips_r6 since it needs the cpu_data[]
  16. * kernel symbol.
  17. */
  18. #ifdef CONFIG_CPU_MIPSR6
  19. /*
  20. * lapc <symbol> is an alias to addiupc reg, <symbol> - .
  21. *
  22. * We can't use addiupc because there is no label-label
  23. * support for the addiupc reloc
  24. */
  25. __asm__("lapc %0, _start \n"
  26. : "=r" (addr) : :);
  27. #else
  28. /*
  29. * Get the base load address of the VDSO. We have to avoid generating
  30. * relocations and references to the GOT because ld.so does not peform
  31. * relocations on the VDSO. We use the current offset from the VDSO base
  32. * and perform a PC-relative branch which gives the absolute address in
  33. * ra, and take the difference. The assembler chokes on
  34. * "li %0, _start - .", so embed the offset as a word and branch over
  35. * it.
  36. *
  37. */
  38. __asm__(
  39. " .set push \n"
  40. " .set noreorder \n"
  41. " bal 1f \n"
  42. " nop \n"
  43. " .word _start - . \n"
  44. "1: lw %0, 0($31) \n"
  45. " " STR(PTR_ADDU) " %0, $31, %0 \n"
  46. " .set pop \n"
  47. : "=r" (addr)
  48. :
  49. : "$31");
  50. #endif /* CONFIG_CPU_MIPSR6 */
  51. return addr;
  52. }
  53. static inline const struct vdso_data *get_vdso_data(void)
  54. {
  55. return (const struct vdso_data *)(get_vdso_base() - PAGE_SIZE);
  56. }
  57. #ifdef CONFIG_CLKSRC_MIPS_GIC
  58. static inline void __iomem *get_gic(const struct vdso_data *data)
  59. {
  60. return (void __iomem *)((unsigned long)data & PAGE_MASK) - PAGE_SIZE;
  61. }
  62. #endif /* CONFIG_CLKSRC_MIPS_GIC */
  63. #endif /* __ASSEMBLY__ */