From 4a59c05f1b9804e16c5b56274409037c92839ddc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Grubbstr=C3=B6m=20=28Grubba=29?= <grubba@grubba.org> Date: Mon, 30 Sep 2002 20:45:22 +0200 Subject: [PATCH] Thread.Condition()->wait() now requires an argument. Rev: lib/7.2/modules/Thread.pmod:1.1 Rev: src/threads.c:1.186 --- .gitattributes | 1 + lib/7.2/modules/Thread.pmod | 24 ++++++++++ src/threads.c | 89 ++++++++++++++++--------------------- 3 files changed, 63 insertions(+), 51 deletions(-) create mode 100644 lib/7.2/modules/Thread.pmod diff --git a/.gitattributes b/.gitattributes index 7fc3c44859..cb818003cf 100644 --- a/.gitattributes +++ b/.gitattributes @@ -45,6 +45,7 @@ testfont binary /lib/7.2/modules/LR.pmod/rule.pike foreign_ident /lib/7.2/modules/LR.pmod/scanner.pike foreign_ident /lib/7.2/modules/Protocols.pmod/LDAP.pmod/client.pike foreign_ident +/lib/7.2/modules/Thread.pmod foreign_ident /lib/7.2/modules/__default.pmod foreign_ident /lib/7.2/modules/system.pmod foreign_ident /lib/master.pike.in foreign_ident diff --git a/lib/7.2/modules/Thread.pmod b/lib/7.2/modules/Thread.pmod new file mode 100644 index 0000000000..448f08c542 --- /dev/null +++ b/lib/7.2/modules/Thread.pmod @@ -0,0 +1,24 @@ +#pike 7.3 + +// +// $Id: Thread.pmod,v 1.1 2002/09/30 18:45:20 grubba Exp $ +// +// Pike 7.2 backward compatibility layer. +// + +inherit Thread; + +class Condition +{ + inherit Thread::Condition; + + // Old-style wait(). + void wait(void|Mutex m) + { + if (!m) { + m = Mutex(); + m->lock(); + } + ::wait(); + } +} diff --git a/src/threads.c b/src/threads.c index 8488f011e6..e6fd8e13e1 100644 --- a/src/threads.c +++ b/src/threads.c @@ -1,5 +1,5 @@ #include "global.h" -RCSID("$Id: threads.c,v 1.185 2002/09/29 13:52:08 nilsson Exp $"); +RCSID("$Id: threads.c,v 1.186 2002/09/30 18:45:22 grubba Exp $"); PMOD_EXPORT int num_threads = 1; PMOD_EXPORT int threads_disabled = 0; @@ -1247,8 +1247,7 @@ void exit_mutex_key_obj(struct object *o) *! @[Mutex] */ -/*! @decl void wait() - *! @decl void wait(Thread.MutexKey mutex_key) +/*! @decl void wait(Thread.MutexKey mutex_key) *! *! Wait for contition. *! @@ -1258,72 +1257,60 @@ void exit_mutex_key_obj(struct object *o) *! waiting for the condition in one atomic operation. After waiting *! for the condition the mutex referenced by mutex_key will be re-locked. *! + *! @note + *! In Pike 7.2 and earlier it was possible to call @[wait()] + *! without arguments. This possibility was removed in Pike 7.3, + *! since it lead to programs with deadlocks. + *! *! @seealso *! @[Mutex->lock()] */ void f_cond_wait(INT32 args) { + struct object *key; + struct mutex_storage *mut; COND_T *c; if(threads_disabled) Pike_error("Cannot wait for conditions when threads are disabled!\n"); + + get_all_args("condition->wait", args, "%o", &key); + if ((key->prog != mutex_key) || + (!(OB2KEY(key)->initialized)) || + (!(mut = OB2KEY(key)->mut))) { + Pike_error("Bad argument 1 to condition->wait()\n"); + } + if(args > 1) { pop_n_elems(args - 1); args = 1; } - c=THIS_COND; - - if((args > 0) && !UNSAFE_IS_ZERO(Pike_sp-1)) - { - struct object *key; - struct mutex_storage *mut; - - if(Pike_sp[-1].type != T_OBJECT) - Pike_error("Bad argument 1 to condition->wait()\n"); - - key=Pike_sp[-1].u.object; - - if(key->prog != mutex_key) - Pike_error("Bad argument 1 to condition->wait()\n"); + c = THIS_COND; - if (OB2KEY(key)->initialized) { - - mut = OB2KEY(key)->mut; - if(!mut) - Pike_error("Bad argument 1 to condition->wait()\n"); - - /* Unlock mutex */ - mut->key=0; - OB2KEY(key)->mut=0; - co_signal(& mut->condition); + /* Unlock mutex */ + mut->key=0; + OB2KEY(key)->mut=0; + co_signal(& mut->condition); - /* Wait and allow mutex operations */ - SWAP_OUT_CURRENT_THREAD(); - co_wait_interpreter(c); - SWAP_IN_CURRENT_THREAD(); - - /* Lock mutex */ - while(mut->key) { - SWAP_OUT_CURRENT_THREAD(); - co_wait_interpreter(& mut->condition); - SWAP_IN_CURRENT_THREAD(); - check_threads_etc(); - } - mut->key=key; - OB2KEY(key)->mut=mut; - - pop_n_elems(args); - return; - } - } - + /* Wait and allow mutex operations */ SWAP_OUT_CURRENT_THREAD(); co_wait_interpreter(c); SWAP_IN_CURRENT_THREAD(); - - pop_n_elems(args); + + /* Lock mutex */ + while(mut->key) { + SWAP_OUT_CURRENT_THREAD(); + co_wait_interpreter(& mut->condition); + SWAP_IN_CURRENT_THREAD(); + check_threads_etc(); + } + mut->key=key; + OB2KEY(key)->mut=mut; + + pop_stack(); + return; } /*! @decl void signal() @@ -1850,9 +1837,9 @@ void th_init(void) START_NEW_PROGRAM_ID(THREAD_CONDITION); ADD_STORAGE(COND_T); - /* function(void|object(mutex_key):void) */ + /* function(object(mutex_key):void) */ ADD_FUNCTION("wait",f_cond_wait, - tFunc(tOr(tVoid,tObjIs_THREAD_MUTEX_KEY),tVoid),0); + tFunc(tObjIs_THREAD_MUTEX_KEY,tVoid),0); /* function(:void) */ ADD_FUNCTION("signal",f_cond_signal,tFunc(tNone,tVoid),0); /* function(:void) */ -- GitLab