summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog17
-rw-r--r--thread.c6
-rw-r--r--thread_pthread.ci89
-rw-r--r--thread_pthread.h9
-rw-r--r--thread_win32.ci33
-rw-r--r--version.h6
6 files changed, 124 insertions, 36 deletions
diff --git a/ChangeLog b/ChangeLog
index 168bb48abd..05f6baf9d7 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,20 @@
+Fri Feb 9 05:08:17 2007 Koichi Sasada <ko1@atdot.net>
+
+ * thread.c, thread_pthread.ci, thread_win32.ci (thread_start_func_1):
+ move cleanup function to thread_start_func_2().
+
+ * thread.c, thread_pthread.ci, thread_win32.ci:
+ add more destruct functions.
+ (native_thread_destroy() and native_mutex_destroy())
+
+ * thread_pthread.ci, thread_pthread.h: make native_mutex_* functions
+ (check error, etc), it's not macro any more.
+
+ * thread_win32.ci (thread_start_func_1): store some values before
+ running thread (to release these after running thread).
+
+ * thread_win32.ci (native_thread_create): fix spaces.
+
Thu Feb 8 22:44:04 2007 Masaki Suketa <masaki.suketa@nifty.ne.jp>
* ext/win32ole/win32ole.c (ole_set_safe_array, ole_variant2val,
diff --git a/thread.c b/thread.c
index a241a41e2c..96ffd2a863 100644
--- a/thread.c
+++ b/thread.c
@@ -247,6 +247,8 @@ thread_cleanup_func(void *th_ptr)
rb_thread_t *th = th_ptr;
th->status = THREAD_KILLED;
th->machine_stack_start = th->machine_stack_end = 0;
+ native_mutex_destroy(&th->interrupt_lock);
+ native_thread_destroy(th);
}
static int
@@ -258,7 +260,6 @@ thread_start_func_2(rb_thread_t *th, VALUE *stack_start)
rb_thread_t *join_th;
th->machine_stack_start = stack_start;
th->thgroup = th->vm->thgroup_default;
-
thread_debug("thread start: %p\n", th);
native_mutex_lock(&th->vm->global_interpreter_lock);
@@ -297,6 +298,7 @@ thread_start_func_2(rb_thread_t *th, VALUE *stack_start)
}
st_delete_wrap(th->vm->living_threads, th->self);
}
+ thread_cleanup_func(th);
native_mutex_unlock(&th->vm->global_interpreter_lock);
return 0;
}
@@ -318,7 +320,6 @@ thread_create_core(VALUE klass, VALUE args, VALUE (*fn)(ANYARGS), void *arg)
th->first_func_arg = arg;
native_mutex_initialize(&th->interrupt_lock);
-
/* kick thread */
st_insert(th->vm->living_threads, thval, (st_data_t) th->thread_id);
native_thread_create(th);
@@ -2082,6 +2083,7 @@ mutex_free(void *ptr)
if (mutex->th) {
native_mutex_unlock(&mutex->lock);
}
+ native_mutex_destroy(&mutex->lock);
}
ruby_xfree(ptr);
}
diff --git a/thread_pthread.ci b/thread_pthread.ci
index 56abaa7d57..20f24b0b91 100644
--- a/thread_pthread.ci
+++ b/thread_pthread.ci
@@ -12,10 +12,59 @@
#ifdef THREAD_SYSTEM_DEPENDENT_IMPLEMENTATION
-#define native_mutex_initialize(lock) do { \
- pthread_mutex_t _lock = PTHREAD_MUTEX_INITIALIZER; \
- ((*lock) = _lock); \
-} while (0)
+void
+native_mutex_lock(pthread_mutex_t *lock)
+{
+ int r;
+ r = pthread_mutex_trylock(lock);
+ if (r == EBUSY) {
+ r = pthread_mutex_lock(lock);
+
+ if (r != 0) {
+ rb_bug("pthread_mutex_lock: %d", r);
+ }
+ }
+}
+
+void
+native_mutex_unlock(pthread_mutex_t *lock)
+{
+ int r;
+ if ((r = pthread_mutex_unlock(lock)) != 0) {
+ rb_bug("native_mutex_unlock return non-zero: %d", r);
+ }
+}
+
+inline int
+native_mutex_trylock(pthread_mutex_t *lock)
+{
+ int r;
+ if ((r = pthread_mutex_trylock(lock)) != 0) {
+ if (r == EBUSY) {
+ return EBUSY;
+ }
+ else {
+ rb_bug("native_mutex_unlock return non-zero: %d", r);
+ }
+ }
+ return 0;
+}
+
+void
+native_mutex_initialize(pthread_mutex_t *lock)
+{
+ if (pthread_mutex_init(lock, 0) != 0) {
+ rb_bug("native_mutex_initialize return non-zero");
+ }
+}
+
+void
+native_mutex_destroy(pthread_mutex_t *lock)
+{
+ if (pthread_mutex_destroy(lock) != 0) {
+ rb_bug("native_mutex_destroy return non-zero");
+ }
+}
#define native_cleanup_push pthread_cleanup_push
#define native_cleanup_pop pthread_cleanup_pop
@@ -40,9 +89,13 @@ Init_native_thread()
posix_signal(SIGVTALRM, null_func);
}
-NOINLINE(static int
- thread_start_func_2(rb_thread_t *th, VALUE *stack_start));
-void static thread_cleanup_func(void *th_ptr);
+NOINLINE(static int thread_start_func_2(rb_thread_t *th, VALUE *stack_start));
+
+static void
+native_thread_destroy(rb_thread_t *th)
+{
+ pthread_cond_destroy(&th->native_thread_data.sleep_cond);
+}
#define USE_THREAD_CACHE 0
@@ -55,16 +108,9 @@ thread_start_func_1(void *th_ptr)
{
rb_thread_t *th = th_ptr;
VALUE stack_start;
- /* ignore self and klass */
-
- native_cleanup_push(thread_cleanup_func, th);
/* run */
thread_start_func_2(th, &stack_start);
-
- /* cleanup */
- thread_cleanup_func(th);
- native_cleanup_pop(0);
}
#if USE_THREAD_CACHE
if (1) {
@@ -171,6 +217,9 @@ use_cached_thread(rb_thread_t *th)
return result;
}
+#define CHECK_ERR(expr) \
+ { int err; if ((err = (expr)) != 0) { printf("err: %d - " #expr, err); exit(1); }}
+
static int
native_thread_create(rb_thread_t *th)
{
@@ -190,16 +239,20 @@ native_thread_create(rb_thread_t *th)
#endif
thread_debug("create: %p, stack size: %ld\n", th, stack_size);
- pthread_attr_init(&attr);
+ CHECK_ERR(pthread_attr_init(&attr));
+
#ifdef PTHREAD_STACK_MIN
- pthread_attr_setstacksize(&attr, stack_size);
+ CHECK_ERR(pthread_attr_setstacksize(&attr, stack_size));
#endif
- pthread_attr_setinheritsched(&attr, PTHREAD_INHERIT_SCHED);
- pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
+
+ CHECK_ERR(pthread_attr_setinheritsched(&attr, PTHREAD_INHERIT_SCHED));
+ CHECK_ERR(pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED));
err = pthread_create(&th->thread_id, &attr, thread_start_func_1, th);
+ CHECK_ERR(pthread_attr_destroy(&attr));
if (err != 0) {
+ st_delete_wrap(th->vm->living_threads, th->self);
th->status = THREAD_KILLED;
rb_raise(rb_eThreadError, "can't create Thread (%d)", err);
}
diff --git a/thread_pthread.h b/thread_pthread.h
index 29306e0e19..1ef4dfb2ca 100644
--- a/thread_pthread.h
+++ b/thread_pthread.h
@@ -16,9 +16,12 @@
typedef pthread_t rb_thread_id_t;
typedef pthread_mutex_t rb_thread_lock_t;
-#define native_mutex_lock pthread_mutex_lock
-#define native_mutex_unlock pthread_mutex_unlock
-#define native_mutex_trylock pthread_mutex_trylock
+void native_mutex_lock(pthread_mutex_t *lock);
+void native_mutex_unlock(pthread_mutex_t *lock);
+void native_mutex_destroy(pthread_mutex_t *lock);
+int native_mutex_trylock(pthread_mutex_t *lock);
+void native_mutex_initialize(pthread_mutex_t *lock);
+void native_mutex_destroy(pthread_mutex_t *lock);
typedef struct native_thread_data_struct {
void *signal_thread_list;
diff --git a/thread_win32.ci b/thread_win32.ci
index dd9a24aad1..29a8efd42c 100644
--- a/thread_win32.ci
+++ b/thread_win32.ci
@@ -201,29 +201,42 @@ native_mutex_initialize(rb_thread_lock_t *lock)
#endif
}
+void
+native_mutex_destroy(rb_thread_lock_t *lock)
+{
+ CloseHandle(lock);
+}
+
+
NOINLINE(static int
thread_start_func_2(rb_thread_t *th, VALUE *stack_start));
-void static thread_cleanup_func(void *th_ptr);
+
+static void
+native_thread_destroy(rb_thread_t *th)
+{
+ CloseHandle(th->native_thread_data.interrupt_event);
+}
static unsigned int _stdcall
thread_start_func_1(void *th_ptr)
{
rb_thread_t *th = th_ptr;
VALUE stack_start;
+ HANDLE thread_id = th->thread_id;
+ HANDLE interrupt_event;
/* run */
- th->native_thread_data.interrupt_event = CreateEvent(0, TRUE, FALSE, 0);
+ interrupt_event = th->native_thread_data.interrupt_event = CreateEvent(0, TRUE, FALSE, 0);
thread_debug("thread created (th: %p, thid: %p, event: %p)\n", th,
th->thread_id, th->native_thread_data.interrupt_event);
thread_start_func_2(th, &stack_start);
- thread_cleanup_func(th);
/* native_mutex_unlock(&GET_VM()->global_interpreter_lock); */
thread_debug("close handle - intr: %p, thid: %p\n",
- th->native_thread_data.interrupt_event, th->thread_id);
- CloseHandle(th->native_thread_data.interrupt_event);
- CloseHandle(th->thread_id);
+ interrupt_event, thread_id);
+ CloseHandle(interrupt_event);
+ CloseHandle(thread_id);
thread_debug("thread deleted (th: %p)\n", th);
return 0;
}
@@ -246,11 +259,11 @@ w32_create_thread(DWORD stack_size, void *func, void *val)
static int
native_thread_create(rb_thread_t *th)
{
- size_t stack_size = 4 * 1024 - sizeof(int); /* 4KB */
+ size_t stack_size = 4 * 1024; /* 4KB */
+ th->thread_id = w32_create_thread(stack_size, thread_start_func_1, th);
- if ((th->thread_id =
- w32_create_thread(stack_size, thread_start_func_1, th))
- == 0) {
+ if ((th->thread_id) == 0) {
+ st_delete_wrap(th->vm->living_threads, th->self);
rb_raise(rb_eThreadError, "can't create Thread (%d)", errno);
}
if (THREAD_DEBUG) {
diff --git a/version.h b/version.h
index f7d4737dbd..f3b406ebe8 100644
--- a/version.h
+++ b/version.h
@@ -1,7 +1,7 @@
#define RUBY_VERSION "1.9.0"
-#define RUBY_RELEASE_DATE "2007-02-08"
+#define RUBY_RELEASE_DATE "2007-02-09"
#define RUBY_VERSION_CODE 190
-#define RUBY_RELEASE_CODE 20070208
+#define RUBY_RELEASE_CODE 20070209
#define RUBY_PATCHLEVEL 0
#define RUBY_VERSION_MAJOR 1
@@ -9,7 +9,7 @@
#define RUBY_VERSION_TEENY 0
#define RUBY_RELEASE_YEAR 2007
#define RUBY_RELEASE_MONTH 2
-#define RUBY_RELEASE_DAY 8
+#define RUBY_RELEASE_DAY 9
RUBY_EXTERN const char ruby_version[];
RUBY_EXTERN const char ruby_release_date[];