strnlen_user.S 1.2 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  1. /*
  2. * Copy to/from userspace with optional address space checking.
  3. *
  4. * Copyright 2004-2006 Atmel Corporation
  5. *
  6. * This program is free software; you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License version 2 as
  8. * published by the Free Software Foundation.
  9. */
  10. #include <asm/page.h>
  11. #include <asm/thread_info.h>
  12. #include <asm/processor.h>
  13. #include <asm/asm.h>
  14. .text
  15. .align 1
  16. .global strnlen_user
  17. .type strnlen_user, "function"
  18. strnlen_user:
  19. branch_if_kernel r8, __strnlen_user
  20. sub r8, r11, 1
  21. add r8, r12
  22. retcs 0
  23. brmi adjust_length /* do a closer inspection */
  24. .global __strnlen_user
  25. .type __strnlen_user, "function"
  26. __strnlen_user:
  27. mov r10, r12
  28. 10: ld.ub r8, r12++
  29. cp.w r8, 0
  30. breq 2f
  31. sub r11, 1
  32. brne 10b
  33. sub r12, -1
  34. 2: sub r12, r10
  35. retal r12
  36. .type adjust_length, "function"
  37. adjust_length:
  38. cp.w r12, 0 /* addr must always be < TASK_SIZE */
  39. retmi 0
  40. pushm lr
  41. lddpc lr, _task_size
  42. sub r11, lr, r12
  43. mov r9, r11
  44. call __strnlen_user
  45. cp.w r12, r9
  46. brgt 1f
  47. popm pc
  48. 1: popm pc, r12=0
  49. .align 2
  50. _task_size:
  51. .long TASK_SIZE
  52. .section .fixup, "ax"
  53. .align 1
  54. 19: retal 0
  55. .section __ex_table, "a"
  56. .align 2
  57. .long 10b, 19b