diff --git a/src/Makefile.in b/src/Makefile.in index 08387f8c37eeb83c66b4bd4fa0f5b4a5aa52f590..015c5ae89e5bf48dae4fc0bd232a7e56578f2019 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -1,5 +1,5 @@ # -# $Id: Makefile.in,v 1.271 2001/09/02 01:36:14 marcus Exp $ +# $Id: Makefile.in,v 1.272 2001/09/18 22:59:56 hubbe Exp $ # # This line is needed on some machines. @@ -384,7 +384,7 @@ install_interactive: pike hilfe pike-module aclocal # tidy up a bit tidy: -rm -f *.fail *.o *.obj *.pp *.protos core y.output y.tab.c y.tab.h - -rm -f $(TMP_BINDIR)/core *.o *.i *.i~ testsuite + -rm -f $(TMP_BINDIR)/core *.o *.i *.i~ testsuite dynloadtest* # make clean clean: tidy @@ -440,6 +440,19 @@ just_verify: module_testsuites testsuite master-stamp if test "$(TESTARGS)" = "" ; then args="-a" ; else args="$(TESTARGS)" ; fi; \ $(RUNPIKE) $(TMP_BINDIR)/test_pike.pike $$args +# Testsuite for dynamic loading debugging +test_dlopen: dynloadtest.sh + sh ./dynloadtest.sh + +dynloadtest.sh: $(SRCDIR)/test_dynamic_loading.in + m4 "$<" >"$@" + +dynloadtest.c: dynamic_load.c + +dynloadtest: dynloadtest.o @EXTRA_OBJS@ fdlib.o port.o + $(LD) $(LDFLAGS) dynloadtest.o @EXTRA_OBJS@ fdlib.o port.o $(LIBS) -o dynloadtest + + tinstall: aclocal master-stamp aclocal -rm -rf test-install $(RUNPIKE) $(TMP_BINDIR)/install.pike $(INSTALLARGS) pike_name="test-pike" lib_prefix="$(lib_prefix)" TMP_LIBDIR="$(TMP_LIBDIR)" LIBDIR_SRC="$(LIBDIR_SRC)" SRCDIR="$(SRCDIR)" prefix="./test-install" MANDIR_SRC="$(MANDIR_SRC)" man_prefix="$(man_prefix)" fakeroot="$(buildroot)" PIKE_MODULE_RELOC="$(PIKE_MODULE_RELOC)" diff --git a/src/dynamic_load.c b/src/dynamic_load.c index 8b03cc8ba97b87f353c2da2f582cbc0ec0c4c6b4..46e373c55702620898d216c1987c5926169bb695 100644 --- a/src/dynamic_load.c +++ b/src/dynamic_load.c @@ -1,4 +1,10 @@ -#ifndef TESTING +#ifdef TESTING +#define NO_PIKE_INCLUDES +#define CREATE_MAIN +#define NO_PIKE_GUTS +#endif + +#ifndef NO_PIKE_INCLUDES # include "global.h" # include "interpret.h" # include "constants.h" @@ -9,7 +15,7 @@ # include "main.h" # include "constants.h" -RCSID("$Id: dynamic_load.c,v 1.55 2001/09/11 05:42:20 hubbe Exp $"); +RCSID("$Id: dynamic_load.c,v 1.56 2001/09/18 22:59:56 hubbe Exp $"); #else /* TESTING */ @@ -292,7 +298,7 @@ static void *dlclose(void *module) #define RTLD_GLOBAL 0 #endif -#ifndef TESTING +#ifndef NO_PIKE_GUTS #if defined(HAVE_DLOPEN) || defined(USE_DLD) || defined(USE_HPUX_DL) || defined(USE_LOADLIBRARY) #define USE_DYNAMIC_MODULES @@ -471,7 +477,9 @@ void free_dynamic_load(void) } -#else /* TESTING */ +#endif /* NO_PIKE_GUTS */ + +#ifdef CREATE_MAIN #include <stdio.h> int main() @@ -496,4 +504,4 @@ int main() fprintf(stderr,"testfunc returned!\n"); exit(1); } -#endif +#endif /* CREATE_MAIN */ diff --git a/src/fdlib.c b/src/fdlib.c index 5bba2d2b48c13f33d8ee3f8fc9a7a046606d24a8..e5090d64a0697573acd466488112717993a4e373 100644 --- a/src/fdlib.c +++ b/src/fdlib.c @@ -3,7 +3,7 @@ #include "pike_error.h" #include <math.h> -RCSID("$Id: fdlib.c,v 1.48 2001/04/23 19:06:53 marcus Exp $"); +RCSID("$Id: fdlib.c,v 1.49 2001/09/18 22:59:56 hubbe Exp $"); #ifdef HAVE_WINSOCK_H @@ -25,6 +25,38 @@ int first_free_handle; #define FDDEBUG(X) #endif +#ifdef PIKE_DEBUG +static int IsValidHandle(HANDLE h) +{ + __try { + HANDLE ret; + if(DuplicateHandle(GetCurrentProcess(), + h, + GetCurrentProcess(), + &ret, + 0, + 0, + DUPLICATE_SAME_ACCESS)) + { + CloseHandle(ret); + } + } + + __except (1) { + return 0; + } + + return 1; +} + +PMOD_EXPORT HANDLE CheckValidHandle(HANDLE h) +{ + if(!IsValidHandle(h)) + fatal("Invalid handle!\n"); + return h; +} +#endif + PMOD_EXPORT char *debug_fd_info(int fd) { if(fd<0) diff --git a/src/test_dynamic_loading.in b/src/test_dynamic_loading.in new file mode 100644 index 0000000000000000000000000000000000000000..b0976102884200763cf3033d0ef7e9c20503fbff --- /dev/null +++ b/src/test_dynamic_loading.in @@ -0,0 +1,192 @@ +#!/bin/sh +dnl This is a M4|sh script + +changequote([[,]]) +define([[TESTNUM]],0) + +define([[Tlow_test]],[[ + define([[TESTNUM]],incr(TESTNUM)) + echo "======= test TESTNUM =======" + $1 + if ./dynloadtest ; then + echo "Test TESTNUM ok!" + else + echo "Test TESTNUM failed!" + for c in MODC + do + echo ==================== $c ======================= + cat $c + echo ---------------------------------------------------------- + done + fi +]])dnl + + +define([[Tmodule]],[[ + define([[MODOBJ]],[[]]) + define([[MODC]],[[]]) + $2 + if make --no-print-directory \ + -f modules/dynamic_module_makefile \ + SRCDIR="`dirname '__file__'`" \ + TMP_BINDIR="`dirname '__file__'`/../bin" \ + MODULE_BASE=modules \ + OBJS="MODOBJ" \ + MODNAME=dynloadtestmod$1 \ + module.so + mv module.so dynloadtestmod$1.so ; then + : + else + echo Failed to compile test module! + fi + rm -f MODOBJ +]])dnl + +define([[Tmodulefile]],[[ +define([[MODOBJ]],MODOBJ dynloadtestmod$1.o) +define([[MODC]],MODC dynloadtestmod$1.c) +cat >dynloadtestmod$1.c <<EOF +#include "dynloadtest.h" +$2 +EOF +]])dnl + +define([[Tmod]],[[ + Tmodule([[]],[[ + Tmodulefile([[]],[[$1]]) + ]]) +]])dnl + +define([[Tprog]],[[ +rm -f dynloadtest dynloadtest.o dynloadtest.c +cat >dynloadtest.h <<EOF +$1 +EOF +cat >dynloadtest.c <<EOF +#include "dynloadtest.h" +$2 +EOF + +if make --no-print-directory dynloadtest ; then + : +else + echo "Failed to compile test program" + cat dynloadtest.c + exit 1 +fi + + +]])dnl + + +Tprog([[ +#ifdef __NT__ +#define EXPORT __declspec(dllexport) +#else +#define EXPORT +#endif + + extern int integer; + extern char * strptr; + int neg_func(int x); + int sub_one_func(int x); + extern int (*funcptr)(int); + int call_funcptr(int z); +]],[[ +#define NO_PIKE_GUTS +#include "dynamic_load.c" + +#line 1 + +int integer = 17; + +char *strptr="strptr"; + +int neg_func(int x) +{ + return -x; +} + +int sub_one_func(int x) +{ + return x-1; +} + +int (*funcptr)(int) = neg_func; + +int call_funcptr(int z) +{ + return funcptr(z); +} + +char **ARGV; +int main(int argc, char **argv) +{ + void *module,*fun; + ARGV=argv; + dlinit(); + module=dlopen("./dynloadtestmod.so",RTLD_NOW); + if(!module) + { + fprintf(stderr,"Failed to link dlmodtest.so: %s\n",dlerror()); + exit(1); + } + fun=dlsym(module,"foo"); + if(!fun) fun=dlsym(module,"_foo"); + if(!fun) + { + fprintf(stderr,"Failed to find function foo: %s\n",dlerror()); + exit(1); + } + exit( ((int (*)(void))fun)() ); +} + +DECLSPEC(noreturn) void debug_fatal(const char *fmt, ...) ATTRIBUTE((noreturn,format (printf, 1, 2))) +{ + va_list args; + va_start(args,fmt); + (void)VFPRINTF(stderr, fmt, args); + fflush(stderr); + abort(); +} + +]]) + + +define([[TTest]],[[Tlow_test(Tmod([[$1]]))]]) + +TTest( [[ EXPORT int foo() { return 0; } ]] ) +TTest( [[ EXPORT int foo() { exit(0); } ]] ) +TTest( [[ EXPORT int foo() { return integer != 17; } ]] ) +TTest( [[ EXPORT int foo() { return strcmp(strptr,"strptr"); } ]] ) +TTest( [[ EXPORT int foo() { return neg_func(-18) != 18; } ]] ) +TTest( [[ EXPORT int foo() { return sub_one_func(-18) != -19; } ]] ) +TTest( [[ EXPORT int foo() { return call_funcptr(-18) != 18; } ]] ) + +TTest( [[ +EXPORT int foo() +{ + funcptr=sub_one_func; + return call_funcptr(-18) != -19; +} +]] ) + +TTest( [[ +EXPORT int foo() +{ + funcptr=sub_one_func; + return call_funcptr(-18) != sub_one_func(-18); +} +]] ) + +TTest( [[ + +int bar(int q) { return 4711; } + +EXPORT int foo() +{ + funcptr=bar; + return call_funcptr(-18) != 4711; +} +]] ) + diff --git a/src/threads.c b/src/threads.c index 247b3f97acdc9ac688da526e8d156d0a64bce49c..3000ed13770b82936f920789673c1756a657b4f0 100644 --- a/src/threads.c +++ b/src/threads.c @@ -1,5 +1,5 @@ #include "global.h" -RCSID("$Id: threads.c,v 1.163 2001/09/06 00:20:59 hubbe Exp $"); +RCSID("$Id: threads.c,v 1.164 2001/09/18 22:59:57 hubbe Exp $"); PMOD_EXPORT int num_threads = 1; PMOD_EXPORT int threads_disabled = 0; @@ -81,36 +81,7 @@ int low_nt_create_thread(unsigned Pike_stack_size, #ifdef PIKE_DEBUG -static int IsValidHandle(HANDLE h) -{ - __try { - HANDLE ret; - if(DuplicateHandle(GetCurrentProcess(), - h, - GetCurrentProcess(), - &ret, - 0, - 0, - DUPLICATE_SAME_ACCESS)) - { - CloseHandle(ret); - } - } - - __except (1) { - return 0; - } - - return 1; -} - -PMOD_EXPORT HANDLE CheckValidHandle(HANDLE h) -{ - if(!IsValidHandle(h)) - fatal("Invalid handle!\n"); - return h; -} - +PMOD_EXPORT HANDLE CheckValidHandle(HANDLE h); #endif #endif @@ -1844,6 +1815,7 @@ void th_cleanup(void) destruct(Pike_interpreter.thread_id); free_object(Pike_interpreter.thread_id); Pike_interpreter.thread_id=0; + destruct_objects_to_destruct_cb(); } if(mutex_key)