diff --git a/bochs-testing/plugin-test/Makefile b/bochs-testing/plugin-test/Makefile new file mode 100644 index 000000000..7ec96bb93 --- /dev/null +++ b/bochs-testing/plugin-test/Makefile @@ -0,0 +1,7 @@ +SUBDIRS = test1-static test2-dynamic test3-twomodules test4-interdep + +all: + for i in $(SUBDIRS); do make -C $$i all; done + +clean: + for i in $(SUBDIRS); do make -C $$i clean; done diff --git a/bochs-testing/plugin-test/test1-static/Makefile b/bochs-testing/plugin-test/test1-static/Makefile new file mode 100644 index 000000000..ec02d77bc --- /dev/null +++ b/bochs-testing/plugin-test/test1-static/Makefile @@ -0,0 +1,18 @@ +CXX=g++ +CXXFLAGS=-Wall -g +LIBTOOL=libtool + +all: uselib + +uselib: uselib.cc libmodule1.la + $(LIBTOOL) $(CXX) $(CXXFLAGS) -o uselib uselib.cc libmodule1.la + +libmodule1.la: module1.lo + $(LIBTOOL) $(CXX) -o libmodule1.la module1.lo + +%.lo: %.cc + $(LIBTOOL) $(CXX) -c $< + +clean: + -libtool rm libmodule1.la module1.lo uselib.exe uselib + rm -rf .libs diff --git a/bochs-testing/plugin-test/test1-static/README b/bochs-testing/plugin-test/test1-static/README new file mode 100644 index 000000000..46aab2e4d --- /dev/null +++ b/bochs-testing/plugin-test/test1-static/README @@ -0,0 +1,4 @@ +test1-static + +Use libtool to build module1 as a static library, and then use it in +uselib.cc. diff --git a/bochs-testing/plugin-test/test1-static/module1.cc b/bochs-testing/plugin-test/test1-static/module1.cc new file mode 100644 index 000000000..adc9324b5 --- /dev/null +++ b/bochs-testing/plugin-test/test1-static/module1.cc @@ -0,0 +1,8 @@ +#include "module1.h" + +const char *module_name = "AddModule"; + +int operate (int a, int b) +{ + return a + b; +} diff --git a/bochs-testing/plugin-test/test1-static/module1.h b/bochs-testing/plugin-test/test1-static/module1.h new file mode 100644 index 000000000..cb3419b4a --- /dev/null +++ b/bochs-testing/plugin-test/test1-static/module1.h @@ -0,0 +1,2 @@ +extern const char *module_name; +extern int operate (int a, int b); diff --git a/bochs-testing/plugin-test/test1-static/uselib.cc b/bochs-testing/plugin-test/test1-static/uselib.cc new file mode 100644 index 000000000..ae079ba1e --- /dev/null +++ b/bochs-testing/plugin-test/test1-static/uselib.cc @@ -0,0 +1,13 @@ +#include +#include "module1.h" + +int main () +{ + printf ("start\n"); + printf ("Module name is '%s'\n", module_name); + int a=5, b=12; + int c = operate (a, b); + printf ("operate(%d,%d) = %d\n", a, b, c); + printf ("stop\n"); + return 0; +} diff --git a/bochs-testing/plugin-test/test2-dynamic/Makefile b/bochs-testing/plugin-test/test2-dynamic/Makefile new file mode 100644 index 000000000..460bf71d4 --- /dev/null +++ b/bochs-testing/plugin-test/test2-dynamic/Makefile @@ -0,0 +1,22 @@ +CXX=g++ +CXXFLAGS=-Wall -g +LIBTOOL=libtool +RPATH=`pwd`/lib + +all: uselib + +uselib: uselib.cc libmodule1.la + $(LIBTOOL) $(CXX) $(CXXFLAGS) -o uselib uselib.cc libmodule1.la + +libmodule1.la: module1.lo + $(LIBTOOL) $(CXX) -no-undefined -o libmodule1.la module1.lo -rpath ${RPATH} + mkdir -p lib bin + $(LIBTOOL) cp libmodule1.la ${RPATH} + +%.lo: %.cc + $(LIBTOOL) $(CXX) -c $< + +clean: + -libtool rm libmodule1.la module1.lo + rm -rf *.o uselib.exe bin lib uselib uselib.exe + rm -rf .libs diff --git a/bochs-testing/plugin-test/test2-dynamic/README b/bochs-testing/plugin-test/test2-dynamic/README new file mode 100644 index 000000000..be44e317d --- /dev/null +++ b/bochs-testing/plugin-test/test2-dynamic/README @@ -0,0 +1,38 @@ +test2-dynamic + +In this directory I use the same source code as test1-static, but +I try to build a shared library instead. To build a shared library +for libmodule1.la, first I add the -rpath variable. This makes libtool +attempt to build shared libraries, but it gives this warning: + +libtool: link: warning: undefined symbols not allowed in i686-pc-cygwin shared libraries + +Then it proceeds to build only static libraries. So I add -no-undefined to +the link of libmodule1.la. This makes it actually build a shared library. +When it does the libtool install step, I see that these files were installed: + +-rwxr-xr-x 1 bryce unknown 668055 Oct 11 02:40 bin/cygmodule1-0.dll +-rw-r--r-- 1 bryce unknown 664 Oct 11 02:40 lib/libmodule1.a +-rw-r--r-- 1 bryce unknown 2946 Oct 11 02:40 lib/libmodule1.dll.a +-rw-r--r-- 1 bryce unknown 728 Oct 11 02:40 lib/libmodule1.la + +File types are +bin/cygmodule1-0.dll: MS Windows PE Intel 80386 console DLL +lib/libmodule1.a: current ar archive +lib/libmodule1.dll.a: current ar archive +lib/libmodule1.la: ASCII English text + +But, trying to link with this shared library fails. + +libtool g++ -Wall -g -o uselib uselib.cc libmodule1.la +g++ -Wall -g -o .libs/uselib uselib.cc .libs/libimp-cygmodule1-0.a -Wl,--rpath -Wl,/home/bryce/plugin-test/test2-dynamic/lib +Warning: resolving _module_name by linking to __imp__module_name (auto-import) +fu000001.o(.idata$3+0xc): undefined reference to `_libs_libimp_cygmodule1_0_a_iname' +nmth000000.o(.idata$4+0x0): undefined reference to `_nm__module_name' +collect2: ld returned 1 exit status +make: *** [uselib] Error 1 + +Then I finally read about __declspec(dllexport) and __declspec(dllimport). +When compiling the module I add __declspec(dllexport) on data and functions. +When using the module, the prototypes for say __declspec(dllimport). +Now it works! diff --git a/bochs-testing/plugin-test/test2-dynamic/module1.cc b/bochs-testing/plugin-test/test2-dynamic/module1.cc new file mode 100644 index 000000000..5b2984c4a --- /dev/null +++ b/bochs-testing/plugin-test/test2-dynamic/module1.cc @@ -0,0 +1,9 @@ +#define DLLINTERFACE __declspec(dllexport) +#include "module1.h" + +const char *module_name = "AddModule"; + +int operate (int a, int b) +{ + return a + b; +} diff --git a/bochs-testing/plugin-test/test2-dynamic/module1.h b/bochs-testing/plugin-test/test2-dynamic/module1.h new file mode 100644 index 000000000..d5b6636a6 --- /dev/null +++ b/bochs-testing/plugin-test/test2-dynamic/module1.h @@ -0,0 +1,6 @@ +#ifndef DLLINTERFACE +#define DLLINTERFACE __declspec(dllimport) +#endif + +DLLINTERFACE extern const char * module_name; +DLLINTERFACE extern int operate (int a, int b); diff --git a/bochs-testing/plugin-test/test2-dynamic/uselib.cc b/bochs-testing/plugin-test/test2-dynamic/uselib.cc new file mode 100644 index 000000000..ae079ba1e --- /dev/null +++ b/bochs-testing/plugin-test/test2-dynamic/uselib.cc @@ -0,0 +1,13 @@ +#include +#include "module1.h" + +int main () +{ + printf ("start\n"); + printf ("Module name is '%s'\n", module_name); + int a=5, b=12; + int c = operate (a, b); + printf ("operate(%d,%d) = %d\n", a, b, c); + printf ("stop\n"); + return 0; +} diff --git a/bochs-testing/plugin-test/test3-twomodules/Makefile b/bochs-testing/plugin-test/test3-twomodules/Makefile new file mode 100644 index 000000000..3d51a2004 --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/Makefile @@ -0,0 +1,27 @@ +CXX=g++ +CXXFLAGS=-Wall -g +LIBTOOL=libtool +RPATH=`pwd`/lib + +all: uselib + +uselib: uselib.cc libmodule1.la libmodule2.la + $(LIBTOOL) $(CXX) $(CXXFLAGS) -o uselib uselib.cc libmodule1.la libmodule2.la + +libmodule1.la: module1.lo + $(LIBTOOL) $(CXX) -no-undefined -o libmodule1.la module1.lo -rpath ${RPATH} + mkdir -p lib bin + $(LIBTOOL) cp libmodule1.la ${RPATH} + +libmodule2.la: module2.lo + $(LIBTOOL) $(CXX) -no-undefined -o libmodule2.la module2.lo -rpath ${RPATH} + mkdir -p lib bin + $(LIBTOOL) cp libmodule2.la ${RPATH} + +%.lo: %.cc + $(LIBTOOL) $(CXX) -c $< + +clean: + -libtool rm libmodule1.la module1.lo libmodule2.la module2.lo + rm -rf *.o uselib.exe bin lib uselib uselib.exe + rm -rf .libs diff --git a/bochs-testing/plugin-test/test3-twomodules/README b/bochs-testing/plugin-test/test3-twomodules/README new file mode 100644 index 000000000..7c4da00a7 --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/README @@ -0,0 +1,8 @@ +test3 + +Add a second module + +module1 exports module_name and operate(int,int). +module2 exports n_operations + +Both are used in uselib.cc. They don't use each other's symbols. diff --git a/bochs-testing/plugin-test/test3-twomodules/module1.cc b/bochs-testing/plugin-test/test3-twomodules/module1.cc new file mode 100644 index 000000000..1f3cb54b0 --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/module1.cc @@ -0,0 +1,11 @@ +#define DLLINTERFACE __declspec(dllexport) +#include "module1.h" +#undef DLLINTERFACE +#include "module2.h" + +const char *module_name = "AddModule"; + +int operate (int a, int b) +{ + return a + b; +} diff --git a/bochs-testing/plugin-test/test3-twomodules/module1.h b/bochs-testing/plugin-test/test3-twomodules/module1.h new file mode 100644 index 000000000..ee9f30df6 --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/module1.h @@ -0,0 +1,7 @@ +#ifndef DLLINTERFACE +#define DLLINTERFACE __declspec(dllimport) +#endif + +DLLINTERFACE extern const char * module_name; +DLLINTERFACE extern int operate (int a, int b); + diff --git a/bochs-testing/plugin-test/test3-twomodules/module2.cc b/bochs-testing/plugin-test/test3-twomodules/module2.cc new file mode 100644 index 000000000..2c1d51dee --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/module2.cc @@ -0,0 +1,12 @@ +#include + +#define DLLINTERFACE __declspec(dllexport) +#include "module2.h" +#undef DLLINTERFACE + +int n_operations = 0; + +void operation_occurred () { + printf ("module2: operation_occurred\n"); + n_operations++; +} diff --git a/bochs-testing/plugin-test/test3-twomodules/module2.h b/bochs-testing/plugin-test/test3-twomodules/module2.h new file mode 100644 index 000000000..84e80e425 --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/module2.h @@ -0,0 +1,7 @@ +#ifndef DLLINTERFACE +#define DLLINTERFACE __declspec(dllimport) +#endif + +DLLINTERFACE extern int n_operations; +DLLINTERFACE void operation_occurred (); + diff --git a/bochs-testing/plugin-test/test3-twomodules/uselib.cc b/bochs-testing/plugin-test/test3-twomodules/uselib.cc new file mode 100644 index 000000000..e9b867fe9 --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/uselib.cc @@ -0,0 +1,17 @@ +#include +#include "module1.h" +#include "module2.h" + +int main () +{ + printf ("start\n"); + printf ("at first, n_operations = %d\n", n_operations); + printf ("Module name is '%s'\n", module_name); + int a=5, b=12; + int c = operate (a, b); + operation_occurred (); + printf ("operate(%d,%d) = %d\n", a, b, c); + printf ("stop\n"); + printf ("at end, n_operations = %d\n", n_operations); + return 0; +} diff --git a/bochs-testing/plugin-test/test3-twomodules/uselib.h b/bochs-testing/plugin-test/test3-twomodules/uselib.h new file mode 100644 index 000000000..b1177cced --- /dev/null +++ b/bochs-testing/plugin-test/test3-twomodules/uselib.h @@ -0,0 +1 @@ +extern int n_operations; diff --git a/bochs-testing/plugin-test/test4-interdep/Makefile b/bochs-testing/plugin-test/test4-interdep/Makefile new file mode 100644 index 000000000..d09276192 --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/Makefile @@ -0,0 +1,27 @@ +CXX=g++ +CXXFLAGS=-Wall -g +LIBTOOL=libtool +RPATH=`pwd`/lib + +all: uselib + +uselib: uselib.cc libmodule1.la libmodule2.la + $(LIBTOOL) $(CXX) $(CXXFLAGS) -o uselib uselib.cc libmodule1.la libmodule2.la + +libmodule1.la: module1.lo libmodule2.la + $(LIBTOOL) $(CXX) -no-undefined -o libmodule1.la module1.lo -rpath ${RPATH} libmodule2.la + mkdir -p lib bin + $(LIBTOOL) cp libmodule1.la ${RPATH} + +libmodule2.la: module2.lo + $(LIBTOOL) $(CXX) -no-undefined -o libmodule2.la module2.lo -rpath ${RPATH} + mkdir -p lib bin + $(LIBTOOL) cp libmodule2.la ${RPATH} + +%.lo: %.cc + $(LIBTOOL) $(CXX) -c $< + +clean: + -libtool rm libmodule1.la module1.lo libmodule2.la module2.lo + rm -rf *.o uselib.exe bin lib uselib uselib.exe + rm -rf .libs diff --git a/bochs-testing/plugin-test/test4-interdep/README b/bochs-testing/plugin-test/test4-interdep/README new file mode 100644 index 000000000..9b0cb1b61 --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/README @@ -0,0 +1,17 @@ +test4-interdep + +Can one module reference objects in another module? Yes. + +module1 exports module_name and operate(int,int). +module2 exports n_operations and operation_occurred(). + +uselib.cc uses symbols and functions from both modules. +Module1 calls operation_occurred() in module2. + +To do this, module2 must be built first. Then module1 is linked +against module2 so that the missing symbols are available. Then, +uselib is linked against both. + +This shows that we can chain libraries. I haven't seen any way to +resolve a circular dependency, where mod1 depends on mod2 and vice +versa, in win32 DLLs. Probably those are not supported. diff --git a/bochs-testing/plugin-test/test4-interdep/module1.cc b/bochs-testing/plugin-test/test4-interdep/module1.cc new file mode 100644 index 000000000..ef5d2dc78 --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/module1.cc @@ -0,0 +1,12 @@ +#define DLLINTERFACE __declspec(dllexport) +#include "module1.h" +#undef DLLINTERFACE +#include "module2.h" + +const char *module_name = "AddModule"; + +int operate (int a, int b) +{ + operation_occurred (); + return a + b; +} diff --git a/bochs-testing/plugin-test/test4-interdep/module1.h b/bochs-testing/plugin-test/test4-interdep/module1.h new file mode 100644 index 000000000..ee9f30df6 --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/module1.h @@ -0,0 +1,7 @@ +#ifndef DLLINTERFACE +#define DLLINTERFACE __declspec(dllimport) +#endif + +DLLINTERFACE extern const char * module_name; +DLLINTERFACE extern int operate (int a, int b); + diff --git a/bochs-testing/plugin-test/test4-interdep/module2.cc b/bochs-testing/plugin-test/test4-interdep/module2.cc new file mode 100644 index 000000000..2c1d51dee --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/module2.cc @@ -0,0 +1,12 @@ +#include + +#define DLLINTERFACE __declspec(dllexport) +#include "module2.h" +#undef DLLINTERFACE + +int n_operations = 0; + +void operation_occurred () { + printf ("module2: operation_occurred\n"); + n_operations++; +} diff --git a/bochs-testing/plugin-test/test4-interdep/module2.h b/bochs-testing/plugin-test/test4-interdep/module2.h new file mode 100644 index 000000000..84e80e425 --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/module2.h @@ -0,0 +1,7 @@ +#ifndef DLLINTERFACE +#define DLLINTERFACE __declspec(dllimport) +#endif + +DLLINTERFACE extern int n_operations; +DLLINTERFACE void operation_occurred (); + diff --git a/bochs-testing/plugin-test/test4-interdep/uselib.cc b/bochs-testing/plugin-test/test4-interdep/uselib.cc new file mode 100644 index 000000000..2ac056456 --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/uselib.cc @@ -0,0 +1,16 @@ +#include +#include "module1.h" +#include "module2.h" + +int main () +{ + printf ("start\n"); + printf ("at first, n_operations = %d\n", n_operations); + printf ("Module name is '%s'\n", module_name); + int a=5, b=12; + int c = operate (a, b); + printf ("operate(%d,%d) = %d\n", a, b, c); + printf ("stop\n"); + printf ("at end, n_operations = %d\n", n_operations); + return 0; +} diff --git a/bochs-testing/plugin-test/test4-interdep/uselib.h b/bochs-testing/plugin-test/test4-interdep/uselib.h new file mode 100644 index 000000000..b1177cced --- /dev/null +++ b/bochs-testing/plugin-test/test4-interdep/uselib.h @@ -0,0 +1 @@ +extern int n_operations;