pthread.cpp 1.4 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859
  1. #include <AK/Atomic.h>
  2. #include <AK/StdLibExtras.h>
  3. #include <Kernel/Syscall.h>
  4. #include <pthread.h>
  5. #include <unistd.h>
  6. #include <stdio.h>
  7. extern "C" {
  8. int pthread_create(pthread_t* thread, pthread_attr_t* attributes, void* (*start_routine)(void*), void* argument_to_start_routine)
  9. {
  10. if (!thread)
  11. return -EINVAL;
  12. UNUSED_PARAM(attributes);
  13. int rc = create_thread(start_routine, argument_to_start_routine);
  14. if (rc < 0)
  15. return rc;
  16. *thread = rc;
  17. return 0;
  18. }
  19. void pthread_exit(void* value_ptr)
  20. {
  21. exit_thread(value_ptr);
  22. }
  23. int pthread_join(pthread_t thread, void** exit_value_ptr)
  24. {
  25. int rc = syscall(SC_join_thread, thread, exit_value_ptr);
  26. __RETURN_WITH_ERRNO(rc, rc, -1);
  27. }
  28. int pthread_mutex_init(pthread_mutex_t* mutex, const pthread_mutexattr_t* attributes)
  29. {
  30. // FIXME: Implement mutex attributes
  31. UNUSED_PARAM(attributes);
  32. *mutex = 0;
  33. return 0;
  34. }
  35. int pthread_mutex_lock(pthread_mutex_t* mutex)
  36. {
  37. auto* atomic = reinterpret_cast<Atomic<u32>*>(mutex);
  38. for (;;) {
  39. u32 expected = false;
  40. if (atomic->compare_exchange_strong(expected, true, AK::memory_order_acq_rel))
  41. return 0;
  42. sched_yield();
  43. }
  44. }
  45. int pthread_mutex_unlock(pthread_mutex_t* mutex)
  46. {
  47. auto* atomic = reinterpret_cast<Atomic<u32>*>(mutex);
  48. atomic->store(false, AK::memory_order_release);
  49. return 0;
  50. }
  51. }