Improving pthread support

This commit is contained in:
Ali Mashtizadeh 2015-01-27 15:01:19 -08:00
parent dd0a1d5612
commit 289412b585
3 changed files with 77 additions and 9 deletions

View File

@ -11,6 +11,7 @@
#define ENOTDIR 0xBAD7
#define ENAMETOOLONG 0xBAD8
#define ENOSYS 0xBAD9
#define EAGAIN 0xBADA
#endif /* __ERRNO_H__ */

View File

@ -2,12 +2,12 @@
#ifndef __PTHREAD_H__
#define __PTHREAD_H__
typedef uint64_t pthread_t;
typedef uint64_t pthread_attr_t;
typedef uint64_t pthread_barrier_t;
typedef uint64_t pthread_barrierattr_t;
typedef uint64_t pthread_mutex_t;
typedef uint64_t pthread_mutexattr_t;
typedef struct pthread *pthread_t;
typedef struct pthread_attr *pthread_attr_t;
typedef struct pthread_barrier *pthread_barrier_t;
typedef struct pthread_barrierattr *pthread_barrierattr_t;
typedef struct pthread_mutex *pthread_mutex_t;
typedef struct pthread_mutexattr *pthread_mutexattr_t;
pthread_t pthread_self(void);
int pthread_create(pthread_t *thread, const pthread_attr_t *attr,

View File

@ -1,34 +1,101 @@
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <errno.h>
#include <pthread.h>
#include <syscall.h>
#include <sys/syscall.h>
struct pthread_attr {
uint64_t _unused;
};
struct pthread {
uint64_t tid;
int errno;
// Initialization
void *(*entry)(void *);
void *arg;
// Termination
void *result;
};
pthread_t
pthread_self(void)
{
// XXX Implement
return NULL;
}
void
pthreadCreateHelper(void *arg)
{
struct pthread *thr = (struct pthread *)arg;
OSThreadExit((uint64_t)(thr->entry)(thr->arg));
}
int
pthread_create(pthread_t *thread, const pthread_attr_t *attr,
void *(*start_routine)(void *), void *arg)
{
uint64_t status;
struct pthread *thr;
thr = malloc(sizeof(*thr));
if (!thr) {
return EAGAIN;
}
memset(thr, 0, sizeof(*thr));
thr->entry = start_routine;
thr->arg = arg;
status = OSThreadCreate((uintptr_t)&pthreadCreateHelper, (uint64_t)thr);
if (SYSCALL_ERRCODE(status) != 0) {
free(thr);
return SYSCALL_ERRCODE(status);
}
thr->tid = SYSCALL_VALUE(status);
*thread = thr;
return 0;
}
void
pthread_exit(void *value_ptr)
{
OSThreadExit(value_ptr);
struct pthread *thr = pthread_self();
thr->result = value_ptr;
OSThreadExit(0);
}
int
pthread_join(pthread_t thread, void **value_ptr)
{
uint64_t value = OSThreadWait(thread);
struct pthread *thr = thread;
uint64_t status = OSThreadWait(thr->tid);
if (status != 0) {
return status;
}
*value_ptr = (void *)value;
*value_ptr = (void *)thr->result;
// Cleanup
free(thr);
return 0;
}
void