From 36b3c56a062b700f1a13f98fe52419f3f5fd498c Mon Sep 17 00:00:00 2001 From: Andrew Galante Date: Wed, 26 Jul 2017 13:59:08 -0700 Subject: [PATCH 001/134] Prevent writeback of a const char* array through a director when using the byte[] %typemap. --- Lib/java/java.swg | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/Lib/java/java.swg b/Lib/java/java.swg index b49826ba0..56516439d 100644 --- a/Lib/java/java.swg +++ b/Lib/java/java.swg @@ -1366,12 +1366,12 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) %apply SWIGTYPE & { SWIGTYPE (CLASS::*const&) } /* String & length */ -%typemap(jni) (char *STRING, size_t LENGTH) "jbyteArray" -%typemap(jtype) (char *STRING, size_t LENGTH) "byte[]" -%typemap(jstype) (char *STRING, size_t LENGTH) "byte[]" -%typemap(javain) (char *STRING, size_t LENGTH) "$javainput" -%typemap(freearg) (char *STRING, size_t LENGTH) "" -%typemap(in) (char *STRING, size_t LENGTH) { +%typemap(jni) (const char *STRING, size_t LENGTH) "jbyteArray" +%typemap(jtype) (const char *STRING, size_t LENGTH) "byte[]" +%typemap(jstype) (const char *STRING, size_t LENGTH) "byte[]" +%typemap(javain) (const char *STRING, size_t LENGTH) "$javainput" +%typemap(freearg) (const char *STRING, size_t LENGTH) "" +%typemap(in) (const char *STRING, size_t LENGTH) { if ($input) { $1 = ($1_ltype) JCALL2(GetByteArrayElements, jenv, $input, 0); $2 = ($2_type) JCALL1(GetArrayLength, jenv, $input); @@ -1380,10 +1380,10 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) $2 = 0; } } -%typemap(argout) (char *STRING, size_t LENGTH) { +%typemap(argout) (const char *STRING, size_t LENGTH) { if ($input) JCALL3(ReleaseByteArrayElements, jenv, $input, (jbyte *)$1, 0); } -%typemap(directorin, descriptor="[B", noblock=1) (char *STRING, size_t LENGTH) { +%typemap(directorin, descriptor="[B", noblock=1) (const char *STRING, size_t LENGTH) { $input = 0; if ($1) { $input = JCALL1(NewByteArray, jenv, (jsize)$2); @@ -1392,9 +1392,10 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) } Swig::LocalRefGuard $1_refguard(jenv, $input); } +%typemap(javadirectorin, descriptor="[B") (const char *STRING, size_t LENGTH) "$jniinput" +%apply (const char *STRING, size_t LENGTH) { (char *STRING, size_t LENGTH) } %typemap(directorargout, noblock=1) (char *STRING, size_t LENGTH) { if ($input && $1) JCALL4(GetByteArrayRegion, jenv, $input, 0, (jsize)$2, (jbyte *)$1); } -%typemap(javadirectorin, descriptor="[B") (char *STRING, size_t LENGTH) "$jniinput" %apply (char *STRING, size_t LENGTH) { (char *STRING, int LENGTH) } /* java keywords */ From 575b250b249cc4ba5a98dfb36f767256a16c1007 Mon Sep 17 00:00:00 2001 From: Andrew Galante Date: Tue, 20 Feb 2018 10:36:09 -0800 Subject: [PATCH 002/134] Don't write-back buffer into Java array when calling const-ptr c function --- Lib/java/java.swg | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Lib/java/java.swg b/Lib/java/java.swg index 56516439d..138e47bab 100644 --- a/Lib/java/java.swg +++ b/Lib/java/java.swg @@ -1381,7 +1381,7 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) } } %typemap(argout) (const char *STRING, size_t LENGTH) { - if ($input) JCALL3(ReleaseByteArrayElements, jenv, $input, (jbyte *)$1, 0); + if ($input) JCALL3(ReleaseByteArrayElements, jenv, $input, (jbyte *)$1, JNI_ABORT); } %typemap(directorin, descriptor="[B", noblock=1) (const char *STRING, size_t LENGTH) { $input = 0; @@ -1394,6 +1394,9 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) } %typemap(javadirectorin, descriptor="[B") (const char *STRING, size_t LENGTH) "$jniinput" %apply (const char *STRING, size_t LENGTH) { (char *STRING, size_t LENGTH) } +%typemap(argout) (char *STRING, size_t LENGTH) { + if ($input) JCALL3(ReleaseByteArrayElements, jenv, $input, (jbyte *)$1, 0); +} %typemap(directorargout, noblock=1) (char *STRING, size_t LENGTH) { if ($input && $1) JCALL4(GetByteArrayRegion, jenv, $input, 0, (jsize)$2, (jbyte *)$1); } %apply (char *STRING, size_t LENGTH) { (char *STRING, int LENGTH) } From 300fc6f66972121c8704fb4774b5865b61e7889a Mon Sep 17 00:00:00 2001 From: Andrew Galante Date: Tue, 20 Feb 2018 10:45:39 -0800 Subject: [PATCH 003/134] Add comment for non-const version --- Lib/java/java.swg | 1 + 1 file changed, 1 insertion(+) diff --git a/Lib/java/java.swg b/Lib/java/java.swg index 138e47bab..5657ca134 100644 --- a/Lib/java/java.swg +++ b/Lib/java/java.swg @@ -1394,6 +1394,7 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) } %typemap(javadirectorin, descriptor="[B") (const char *STRING, size_t LENGTH) "$jniinput" %apply (const char *STRING, size_t LENGTH) { (char *STRING, size_t LENGTH) } +/* Enable write-back for non-const version */ %typemap(argout) (char *STRING, size_t LENGTH) { if ($input) JCALL3(ReleaseByteArrayElements, jenv, $input, (jbyte *)$1, 0); } From db34df38f3d5ab3c0b35f57d581f7f327dc7dfee Mon Sep 17 00:00:00 2001 From: Sylvain Joubert Date: Mon, 23 Apr 2018 13:57:19 +0200 Subject: [PATCH 004/134] [Java] Suppress deprecation warning on finalize method Java 9 deprecates the finalize method. For now just suppress the deprecation warning. Fixes #1237 --- Examples/test-suite/java_director.i | 1 + Examples/test-suite/java_throws.i | 1 + Lib/java/java.swg | 1 + 3 files changed, 3 insertions(+) diff --git a/Examples/test-suite/java_director.i b/Examples/test-suite/java_director.i index 03d733d6a..6b2cb6dfe 100644 --- a/Examples/test-suite/java_director.i +++ b/Examples/test-suite/java_director.i @@ -7,6 +7,7 @@ %module(directors="1") java_director %typemap(javafinalize) SWIGTYPE %{ + @SuppressWarnings("deprecation") protected void finalize() { // System.out.println("Finalizing " + this); delete(); diff --git a/Examples/test-suite/java_throws.i b/Examples/test-suite/java_throws.i index bb5c6e48f..c137da804 100644 --- a/Examples/test-suite/java_throws.i +++ b/Examples/test-suite/java_throws.i @@ -192,6 +192,7 @@ try { // Need to handle the checked exception in NoExceptTest.delete() %typemap(javafinalize) SWIGTYPE %{ + @SuppressWarnings("deprecation") protected void finalize() { try { delete(); diff --git a/Lib/java/java.swg b/Lib/java/java.swg index 19e597bd9..bcab5a6fd 100644 --- a/Lib/java/java.swg +++ b/Lib/java/java.swg @@ -1273,6 +1273,7 @@ SWIG_JAVABODY_PROXY(protected, protected, SWIGTYPE) SWIG_JAVABODY_TYPEWRAPPER(protected, protected, protected, SWIGTYPE) %typemap(javafinalize) SWIGTYPE %{ + @SuppressWarnings("deprecation") protected void finalize() { delete(); } From 1f46d9b7b9d6b0e22a23d54a2d6e5695e6d95e76 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 19 Feb 2019 21:23:16 +0000 Subject: [PATCH 005/134] Fix regression parsing gcc preprocessor linemarkers These are preprocessor statement in the form: # linenum filename flags Closes #1475 --- CHANGES.current | 5 +++++ Examples/test-suite/common.mk | 1 + .../test-suite/errors/pp_unknowndirective3.i | 14 ++++++++++++++ .../errors/pp_unknowndirective3.stderr | 4 ++++ Examples/test-suite/preproc_gcc_output.h | 13 +++++++++++++ Examples/test-suite/preproc_gcc_output.i | 12 ++++++++++++ .../python/preproc_gcc_output_runme.py | 5 +++++ Source/Preprocessor/cpp.c | 17 ++++++++++++++++- 8 files changed, 70 insertions(+), 1 deletion(-) create mode 100644 Examples/test-suite/errors/pp_unknowndirective3.i create mode 100644 Examples/test-suite/errors/pp_unknowndirective3.stderr create mode 100644 Examples/test-suite/preproc_gcc_output.h create mode 100644 Examples/test-suite/preproc_gcc_output.i create mode 100644 Examples/test-suite/python/preproc_gcc_output_runme.py diff --git a/CHANGES.current b/CHANGES.current index 6d7b0ca46..2d26fc4ff 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,11 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-19: wsfulton + #1475 Fix regression parsing gcc preprocessor linemarkers in the form: + + # linenum filename flags + 2019-02-18: jakecobb [Python] #945 #1234 Elements in std::vector memory access fix. diff --git a/Examples/test-suite/common.mk b/Examples/test-suite/common.mk index 5a72ba730..3d4edd47b 100644 --- a/Examples/test-suite/common.mk +++ b/Examples/test-suite/common.mk @@ -707,6 +707,7 @@ C_TEST_CASES += \ preproc \ preproc_constants_c \ preproc_defined \ + preproc_gcc_output \ preproc_include \ preproc_line_file \ register_par \ diff --git a/Examples/test-suite/errors/pp_unknowndirective3.i b/Examples/test-suite/errors/pp_unknowndirective3.i new file mode 100644 index 000000000..77dfd5bb5 --- /dev/null +++ b/Examples/test-suite/errors/pp_unknowndirective3.i @@ -0,0 +1,14 @@ +%module xxx + +// Testing is_digits detecting gcc linemarkers + +// These are valid +# 1 "/usr/include/stdc-predef.h" 1 3 4 +# 123 "header1.h" + +// These are invalid +#a1 'a.h' +#1b 'b.h' +#1c1 'c.h' +#d1d 'd.h' + diff --git a/Examples/test-suite/errors/pp_unknowndirective3.stderr b/Examples/test-suite/errors/pp_unknowndirective3.stderr new file mode 100644 index 000000000..35bff8a80 --- /dev/null +++ b/Examples/test-suite/errors/pp_unknowndirective3.stderr @@ -0,0 +1,4 @@ +pp_unknowndirective3.i:10: Error: Unknown SWIG preprocessor directive: a1 (if this is a block of target language code, delimit it with %{ and %}) +pp_unknowndirective3.i:11: Error: Unknown SWIG preprocessor directive: 1b (if this is a block of target language code, delimit it with %{ and %}) +pp_unknowndirective3.i:12: Error: Unknown SWIG preprocessor directive: 1c1 (if this is a block of target language code, delimit it with %{ and %}) +pp_unknowndirective3.i:13: Error: Unknown SWIG preprocessor directive: d1d (if this is a block of target language code, delimit it with %{ and %}) diff --git a/Examples/test-suite/preproc_gcc_output.h b/Examples/test-suite/preproc_gcc_output.h new file mode 100644 index 000000000..cc5065d12 --- /dev/null +++ b/Examples/test-suite/preproc_gcc_output.h @@ -0,0 +1,13 @@ +# 1 "header1.h" +# 1 "" +# 1 "" +# 1 "/usr/include/stdc-predef.h" 1 3 4 +# 1 "" 2 +# 1 "header1.h" +# 18 "header1.h" +void header1_function_a(int a); +# 1 "header2.h" 1 +# 13 "header2.h" +void header2_function(int x); +# 20 "header1.h" 2 +void header1_function_b(int b); diff --git a/Examples/test-suite/preproc_gcc_output.i b/Examples/test-suite/preproc_gcc_output.i new file mode 100644 index 000000000..b4db9e70a --- /dev/null +++ b/Examples/test-suite/preproc_gcc_output.i @@ -0,0 +1,12 @@ +%module preproc_gcc_output +// Testcase for Github issue #1475 using the output of gcc -E + +// The file below was generated using 'gcc -E header1.h' +// where header1.h included header2.h +%include "preproc_gcc_output.h" + +%{ +void header1_function_a(int a) {} +void header2_function(int x) {} +void header1_function_b(int b) {} +%} diff --git a/Examples/test-suite/python/preproc_gcc_output_runme.py b/Examples/test-suite/python/preproc_gcc_output_runme.py new file mode 100644 index 000000000..66ff7d21a --- /dev/null +++ b/Examples/test-suite/python/preproc_gcc_output_runme.py @@ -0,0 +1,5 @@ +import preproc_gcc_output + +preproc_gcc_output.header1_function_a(99) +preproc_gcc_output.header1_function_b(99) +preproc_gcc_output.header2_function(99) diff --git a/Source/Preprocessor/cpp.c b/Source/Preprocessor/cpp.c index af1775007..557b5482b 100644 --- a/Source/Preprocessor/cpp.c +++ b/Source/Preprocessor/cpp.c @@ -109,6 +109,19 @@ static String *cpp_include(const_String_or_char_ptr fn, int sysfile) { return s; } +static int is_digits(const String *str) { + const char *s = Char(str); + int isdigits = (*s != 0); + while (*s) { + if (!isdigit(*s)) { + isdigits = 0; + break; + } + s++; + } + return isdigits; +} + List *Preprocessor_depend(void) { return dependencies; } @@ -1484,7 +1497,7 @@ String *Preprocessor_parse(String *s) { Putc(c, id); break; - case 42: /* Strip any leading space before preprocessor value */ + case 42: /* Strip any leading space after the preprocessor directive (before preprocessor value) */ if (isspace(c)) { if (c == '\n') { Ungetc(c, s); @@ -1804,6 +1817,8 @@ String *Preprocessor_parse(String *s) { Swig_error(Getfile(s), Getline(id), "cpp debug: level = %d, startlevel = %d\n", level, start_level); } else if (Equal(id, "")) { /* Null directive */ + } else if (is_digits(id)) { + /* A gcc linemarker of the form '# linenum filename flags' (resulting from running gcc -E) */ } else { /* Ignore unknown preprocessor directives which are inside an inactive * conditional (github issue #394). */ From 32b963ef1caccf7bc941e16c9a6fc7abe8c8fd8d Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 19 Feb 2019 22:54:08 +0000 Subject: [PATCH 006/134] Re-organise Python method creation and docstring functions declarations MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fix ‘PyMethodDef* SWIG_PythonGetProxyDoc(const char*)’ declared ‘static’ but never defined [-Wunused-function] Closes #1448 (again) --- Lib/python/pyinit.swg | 16 ++++++++++++++++ Lib/python/pyrun.swg | 6 ------ 2 files changed, 16 insertions(+), 6 deletions(-) diff --git a/Lib/python/pyinit.swg b/Lib/python/pyinit.swg index f5be6d599..dfbf40b34 100644 --- a/Lib/python/pyinit.swg +++ b/Lib/python/pyinit.swg @@ -8,6 +8,22 @@ %fragment(""); // For offsetof #endif +%insert(runtime) %{ +#ifdef __cplusplus +extern "C" { +#endif + +/* Method creation and docstring support functions */ + +SWIGINTERN PyMethodDef *SWIG_PythonGetProxyDoc(const char *name); +SWIGINTERN PyObject *SWIG_PyInstanceMethod_New(PyObject *SWIGUNUSEDPARM(self), PyObject *func); +SWIGINTERN PyObject *SWIG_PyStaticMethod_New(PyObject *SWIGUNUSEDPARM(self), PyObject *func); + +#ifdef __cplusplus +} +#endif +%} + %init %{ #ifdef __cplusplus diff --git a/Lib/python/pyrun.swg b/Lib/python/pyrun.swg index 693cd6d46..ad1b81963 100644 --- a/Lib/python/pyrun.swg +++ b/Lib/python/pyrun.swg @@ -213,12 +213,6 @@ SWIG_Python_UnpackTuple(PyObject *args, const char *name, Py_ssize_t min, Py_ssi extern "C" { #endif -/* Method creation and docstring support functions */ - -SWIGINTERN PyMethodDef *SWIG_PythonGetProxyDoc(const char *name); -SWIGINTERN PyObject *SWIG_PyInstanceMethod_New(PyObject *SWIGUNUSEDPARM(self), PyObject *func); -SWIGINTERN PyObject *SWIG_PyStaticMethod_New(PyObject *SWIGUNUSEDPARM(self), PyObject *func); - /* The python void return value */ SWIGRUNTIMEINLINE PyObject * From 1c03af9b96c5c3e2eb5afd2f2e93e4381bfa2261 Mon Sep 17 00:00:00 2001 From: Zackery Spytz Date: Thu, 21 Feb 2019 02:11:51 -0700 Subject: [PATCH 007/134] Fix some rejections of valid floating-point literals Some valid floating-point literals were giving "Error: Syntax error in input(1)". --- CHANGES.current | 3 +++ Examples/test-suite/primitive_types.i | 4 ++++ Source/Swig/scanner.c | 6 ++++++ 3 files changed, 13 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 2d26fc4ff..5456429ef 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,9 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-21: ZackerySpytz + #1480 Fix some rejections of valid floating-point literals. + 2019-02-19: wsfulton #1475 Fix regression parsing gcc preprocessor linemarkers in the form: diff --git a/Examples/test-suite/primitive_types.i b/Examples/test-suite/primitive_types.i index 637934377..a71f62a4f 100644 --- a/Examples/test-suite/primitive_types.i +++ b/Examples/test-suite/primitive_types.i @@ -630,6 +630,10 @@ macro(size_t, pfx, sizet) float val_float(float x) { return x; } + + float val_float_3(float f = 0e1f, float f2 = 020e0f, float f3 = 0.3e4f) { + return f + f2 + f3; + } %} diff --git a/Source/Swig/scanner.c b/Source/Swig/scanner.c index 964336621..908bc747f 100644 --- a/Source/Swig/scanner.c +++ b/Source/Swig/scanner.c @@ -1160,6 +1160,8 @@ static int look(Scanner *s) { return SWIG_TOKEN_INT; if (isdigit(c)) state = 84; + else if ((c == 'e') || (c == 'E')) + state = 82; else if ((c == 'x') || (c == 'X')) state = 85; else if ((c == 'b') || (c == 'B')) @@ -1181,6 +1183,10 @@ static int look(Scanner *s) { return SWIG_TOKEN_INT; if (isdigit(c)) state = 84; + else if (c == '.') + state = 81; + else if ((c == 'e') || (c == 'E')) + state = 82; else if ((c == 'l') || (c == 'L')) { state = 87; } else if ((c == 'u') || (c == 'U')) { From 1e571417b69df15dc928e2e39b2b404773c3386f Mon Sep 17 00:00:00 2001 From: Zachary Hensley Date: Thu, 21 Feb 2019 09:24:10 -0600 Subject: [PATCH 008/134] Updated java std_map to support Obj derivatives by importing original for use in class --- Lib/java/std_map.i | 3 +++ 1 file changed, 3 insertions(+) diff --git a/Lib/java/std_map.i b/Lib/java/std_map.i index 4b891e74a..a7202bc06 100644 --- a/Lib/java/std_map.i +++ b/Lib/java/std_map.i @@ -51,6 +51,9 @@ template > class map { %typemap(javabase) std::map< K, T, C > "java.util.AbstractMap<$typemap(jboxtype, K), $typemap(jboxtype, T)>" +%typemap(javaimports) std::map< K, T, C > + "import java.lang.Object;" + %proxycode %{ public int size() { From 2786bf37a148090d98e5c9f3126148f10ec67f89 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 21 Feb 2019 17:57:11 +0000 Subject: [PATCH 009/134] Fix multiple definitions of swig::container_owner_attribute --- Lib/python/pycontainer.swg | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Lib/python/pycontainer.swg b/Lib/python/pycontainer.swg index 5c2a981ee..ef2f725af 100644 --- a/Lib/python/pycontainer.swg +++ b/Lib/python/pycontainer.swg @@ -43,7 +43,7 @@ %fragment("reference_container_owner", "header", fragment="container_owner_attribute_init") { namespace swig { - PyObject* container_owner_attribute() { + static PyObject* container_owner_attribute() { static PyObject* attr = SWIG_Python_str_FromChar("__swig_container"); return attr; } From e6035d625a4737de4c9406b1f5d16cdcf8d48b5f Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Wed, 20 Feb 2019 23:44:01 -0800 Subject: [PATCH 010/134] Java 9 deprecation warning fixes for test-suite and examples --- Examples/java/variables/runme.java | 2 +- Examples/test-suite/doxygen_translate.i | 4 ++++ Examples/test-suite/doxygen_translate_all_tags.i | 4 ++++ Examples/test-suite/java/li_std_list_runme.java | 8 ++++---- Examples/test-suite/java/li_std_vector_runme.java | 8 ++++---- Examples/test-suite/java/long_long_runme.java | 6 +++--- 6 files changed, 20 insertions(+), 12 deletions(-) diff --git a/Examples/java/variables/runme.java b/Examples/java/variables/runme.java index 361a30fa6..a53cc543c 100644 --- a/Examples/java/variables/runme.java +++ b/Examples/java/variables/runme.java @@ -76,7 +76,7 @@ public class runme { System.out.println( " Trying to set 'status'" ); try { Method m = example.class.getDeclaredMethod("setStatus", new Class[] {Integer.class}); - m.invoke(example.class, new Object[] {new Integer(0)} ); + m.invoke(example.class, new Object[] {Integer.valueOf(0)} ); System.out.println( "Hey, what's going on?!?! This shouldn't work" ); } catch (NoSuchMethodException e) { diff --git a/Examples/test-suite/doxygen_translate.i b/Examples/test-suite/doxygen_translate.i index 348b2e9a8..bb0af1c14 100644 --- a/Examples/test-suite/doxygen_translate.i +++ b/Examples/test-suite/doxygen_translate.i @@ -1,5 +1,9 @@ %module doxygen_translate +#if defined(SWIGJAVA) +%javamethodmodifiers function "@Deprecated\npublic" +#endif + %inline %{ /** diff --git a/Examples/test-suite/doxygen_translate_all_tags.i b/Examples/test-suite/doxygen_translate_all_tags.i index ba348fd50..6e96a57c5 100644 --- a/Examples/test-suite/doxygen_translate_all_tags.i +++ b/Examples/test-suite/doxygen_translate_all_tags.i @@ -1,5 +1,9 @@ %module doxygen_translate_all_tags +#if defined(SWIGJAVA) +%javamethodmodifiers func02 "@Deprecated\npublic" +#endif + %inline %{ /** diff --git a/Examples/test-suite/java/li_std_list_runme.java b/Examples/test-suite/java/li_std_list_runme.java index e45b8968b..94bcada02 100644 --- a/Examples/test-suite/java/li_std_list_runme.java +++ b/Examples/test-suite/java/li_std_list_runme.java @@ -47,11 +47,11 @@ public class li_std_list_runme { } catch (java.util.NoSuchElementException e) { } - if (v1.remove(new Integer(123))) throw new RuntimeException("v1 test (13) failed"); - if (!v1.remove(new Integer(456))) throw new RuntimeException("v1 test (14) failed"); + if (v1.remove(Integer.valueOf(123))) throw new RuntimeException("v1 test (13) failed"); + if (!v1.remove(Integer.valueOf(456))) throw new RuntimeException("v1 test (14) failed"); if (!v1.isEmpty()) throw new RuntimeException("v1 test (15) failed"); if (v1.size() != 0) throw new RuntimeException("v1 test (16) failed"); - if (v1.remove(new Integer(456))) throw new RuntimeException("v1 test (17) failed"); + if (v1.remove(Integer.valueOf(456))) throw new RuntimeException("v1 test (17) failed"); if (new IntList(3).size() != 3) throw new RuntimeException("constructor initial size test failed"); for (int n : new IntList(10, 999)) @@ -136,7 +136,7 @@ public class li_std_list_runme { v9.add(60); v9.add(70); if (v9.size() != 7) throw new RuntimeException("v9 test (1) failed"); - if (!v9.remove(new Integer(60))) throw new RuntimeException("v9 test (2) failed"); + if (!v9.remove(Integer.valueOf(60))) throw new RuntimeException("v9 test (2) failed"); if (v9.size() != 6) throw new RuntimeException("v9 test (3) failed"); v9.addFirst(-10); v9.addLast(80); diff --git a/Examples/test-suite/java/li_std_vector_runme.java b/Examples/test-suite/java/li_std_vector_runme.java index d23bbe7cd..ba0648562 100644 --- a/Examples/test-suite/java/li_std_vector_runme.java +++ b/Examples/test-suite/java/li_std_vector_runme.java @@ -48,11 +48,11 @@ public class li_std_vector_runme { } catch (java.util.NoSuchElementException e) { } - if (v1.remove(new Integer(123))) throw new RuntimeException("v1 test (13) failed"); - if (!v1.remove(new Integer(456))) throw new RuntimeException("v1 test (14) failed"); + if (v1.remove(Integer.valueOf(123))) throw new RuntimeException("v1 test (13) failed"); + if (!v1.remove(Integer.valueOf(456))) throw new RuntimeException("v1 test (14) failed"); if (!v1.isEmpty()) throw new RuntimeException("v1 test (15) failed"); if (v1.size() != 0) throw new RuntimeException("v1 test (16) failed"); - if (v1.remove(new Integer(456))) throw new RuntimeException("v1 test (17) failed"); + if (v1.remove(Integer.valueOf(456))) throw new RuntimeException("v1 test (17) failed"); if (new IntVector(3).size() != 3) throw new RuntimeException("constructor initial size test failed"); for (int n : new IntVector(10, 999)) @@ -137,7 +137,7 @@ public class li_std_vector_runme { v9.add(60); v9.add(70); if (v9.size() != 7) throw new RuntimeException("v9 test (1) failed"); - if (!v9.remove(new Integer(60))) throw new RuntimeException("v9 test (2) failed"); + if (!v9.remove(Integer.valueOf(60))) throw new RuntimeException("v9 test (2) failed"); if (v9.size() != 6) throw new RuntimeException("v9 test (3) failed"); IntVector v10 = new IntVector(java.util.Arrays.asList(10, 20, 30, 40, 50)); diff --git a/Examples/test-suite/java/long_long_runme.java b/Examples/test-suite/java/long_long_runme.java index 76aa0705d..65a0e79b3 100644 --- a/Examples/test-suite/java/long_long_runme.java +++ b/Examples/test-suite/java/long_long_runme.java @@ -84,14 +84,14 @@ public class long_long_runme { ArrayList bigIntegers = new ArrayList(); for (int i=0; i Date: Thu, 21 Feb 2019 13:44:24 -0800 Subject: [PATCH 011/134] Add changes entry for Java finalize suppression --- CHANGES.current | 3 +++ 1 file changed, 3 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 2d26fc4ff..492dffa6a 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,9 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-21: wsfulton + #1240 Suppress Java 9 deprecation warnings on finalize method. + 2019-02-19: wsfulton #1475 Fix regression parsing gcc preprocessor linemarkers in the form: From c3d652c785328e67d14141266e4ae6198124cc95 Mon Sep 17 00:00:00 2001 From: Zackery Spytz Date: Fri, 22 Feb 2019 06:28:53 -0700 Subject: [PATCH 012/134] Fix the handling of director classes with final methods Generated SwigDirector_* classes were attempting to override methods marked as final. In addition, give a warning if the destructor of a director class is final. Closes #564. --- CHANGES.current | 3 ++ Doc/Manual/Warnings.html | 1 + Examples/test-suite/cpp11_final_directors.i | 18 +++++++ .../python/cpp11_final_directors_runme.py | 11 ++++ Source/CParse/parser.y | 51 ++++++++++++++++--- Source/Include/swigwarn.h | 1 + Source/Modules/lang.cxx | 9 +++- 7 files changed, 87 insertions(+), 7 deletions(-) create mode 100644 Examples/test-suite/cpp11_final_directors.i create mode 100644 Examples/test-suite/python/cpp11_final_directors_runme.py diff --git a/CHANGES.current b/CHANGES.current index 492dffa6a..5bf15a778 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,9 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-22: ZackerySpytz + #1483 Fix compilation failures when a director class has final methods. + 2019-02-21: wsfulton #1240 Suppress Java 9 deprecation warnings on finalize method. diff --git a/Doc/Manual/Warnings.html b/Doc/Manual/Warnings.html index bff20801e..8b2ab2b95 100644 --- a/Doc/Manual/Warnings.html +++ b/Doc/Manual/Warnings.html @@ -535,6 +535,7 @@ example.i(4) : Syntax error in input(1).
  • 522. Use of an illegal constructor name 'name' in %extend is deprecated, the constructor name should be 'name'.
  • 523. Use of an illegal destructor name 'name' in %extend is deprecated, the destructor name should be 'name'.
  • 524. Experimental target language. Target language language specified by lang is an experimental language. Please read about SWIG experimental languages, htmllink. +
  • 525. The director base class 'name' or the destructor of director base class 'name' is marked as final.

    18.9.6 Doxygen comments (560-599)

    diff --git a/Examples/test-suite/cpp11_final_directors.i b/Examples/test-suite/cpp11_final_directors.i new file mode 100644 index 000000000..d724543ea --- /dev/null +++ b/Examples/test-suite/cpp11_final_directors.i @@ -0,0 +1,18 @@ +%module(directors="1") cpp11_final_directors + +%warnfilter(SWIGWARN_PARSE_KEYWORD) final; + +%director Derived; + +%inline %{ +struct Base { + virtual void basemeth() final {} + virtual ~Base() {} +}; + +struct Derived : Base { + virtual int derivedmeth() final { return 1; } + virtual int meth() { return 2; } + virtual ~Derived() {} +}; +%} diff --git a/Examples/test-suite/python/cpp11_final_directors_runme.py b/Examples/test-suite/python/cpp11_final_directors_runme.py new file mode 100644 index 000000000..2e5f8af96 --- /dev/null +++ b/Examples/test-suite/python/cpp11_final_directors_runme.py @@ -0,0 +1,11 @@ +import cpp11_final_directors + +class Derived2(cpp11_final_directors.Derived): + + def meth(self): + return 3 + + +b = Derived2() +if b.meth() != 3: + raise RuntimeError diff --git a/Source/CParse/parser.y b/Source/CParse/parser.y index f20f1db2f..4046e480e 100644 --- a/Source/CParse/parser.y +++ b/Source/CParse/parser.y @@ -1552,6 +1552,7 @@ static String *add_qualifier_to_declarator(SwigType *type, SwigType *qualifier) Parm *throws; String *throwf; String *nexcept; + String *final; } dtype; struct { const char *type; @@ -1567,6 +1568,7 @@ static String *add_qualifier_to_declarator(SwigType *type, SwigType *qualifier) ParmList *throws; String *throwf; String *nexcept; + String *final; } decl; Parm *tparms; struct { @@ -3189,6 +3191,7 @@ c_decl : storage_class type declarator cpp_const initializer c_decl_tail { Setattr($$,"throws",$4.throws); Setattr($$,"throw",$4.throwf); Setattr($$,"noexcept",$4.nexcept); + Setattr($$,"final",$4.final); if ($5.val && $5.type) { /* store initializer type as it might be different to the declared type */ SwigType *valuetype = NewSwigType($5.type); @@ -3266,6 +3269,7 @@ c_decl : storage_class type declarator cpp_const initializer c_decl_tail { Setattr($$,"throws",$4.throws); Setattr($$,"throw",$4.throwf); Setattr($$,"noexcept",$4.nexcept); + Setattr($$,"final",$4.final); if (!$9) { if (Len(scanner_ccode)) { String *code = Copy(scanner_ccode); @@ -3330,6 +3334,7 @@ c_decl_tail : SEMI { Setattr($$,"throws",$3.throws); Setattr($$,"throw",$3.throwf); Setattr($$,"noexcept",$3.nexcept); + Setattr($$,"final",$3.final); if ($4.bitfield) { Setattr($$,"bitfield", $4.bitfield); } @@ -3638,6 +3643,7 @@ c_constructor_decl : storage_class type LPAREN parms RPAREN ctor_end { Setattr($$,"throws",$6.throws); Setattr($$,"throw",$6.throwf); Setattr($$,"noexcept",$6.nexcept); + Setattr($$,"final",$6.final); err = 0; } } @@ -4704,6 +4710,7 @@ cpp_constructor_decl : storage_class type LPAREN parms RPAREN ctor_end { Setattr($$,"throws",$6.throws); Setattr($$,"throw",$6.throwf); Setattr($$,"noexcept",$6.nexcept); + Setattr($$,"final",$6.final); if (Len(scanner_ccode)) { String *code = Copy(scanner_ccode); Setattr($$,"code",code); @@ -4740,6 +4747,7 @@ cpp_destructor_decl : NOT idtemplate LPAREN parms RPAREN cpp_end { Setattr($$,"throws",$6.throws); Setattr($$,"throw",$6.throwf); Setattr($$,"noexcept",$6.nexcept); + Setattr($$,"final",$6.final); if ($6.val) Setattr($$,"value",$6.val); if ($6.qualifier) @@ -4760,6 +4768,7 @@ cpp_destructor_decl : NOT idtemplate LPAREN parms RPAREN cpp_end { Setattr($$,"throws",$7.throws); Setattr($$,"throw",$7.throwf); Setattr($$,"noexcept",$7.nexcept); + Setattr($$,"final",$7.final); if ($7.val) Setattr($$,"value",$7.val); if (Len(scanner_ccode)) { @@ -4941,6 +4950,7 @@ cpp_end : cpp_const SEMI { $$.throws = $1.throws; $$.throwf = $1.throwf; $$.nexcept = $1.nexcept; + $$.final = $1.final; } | cpp_const EQUAL default_delete SEMI { Clear(scanner_ccode); @@ -4951,6 +4961,7 @@ cpp_end : cpp_const SEMI { $$.throws = $1.throws; $$.throwf = $1.throwf; $$.nexcept = $1.nexcept; + $$.final = $1.final; } | cpp_const LBRACE { skip_balanced('{','}'); @@ -4961,6 +4972,7 @@ cpp_end : cpp_const SEMI { $$.throws = $1.throws; $$.throwf = $1.throwf; $$.nexcept = $1.nexcept; + $$.final = $1.final; } ; @@ -4973,6 +4985,7 @@ cpp_vend : cpp_const SEMI { $$.throws = $1.throws; $$.throwf = $1.throwf; $$.nexcept = $1.nexcept; + $$.final = $1.final; } | cpp_const EQUAL definetype SEMI { Clear(scanner_ccode); @@ -4982,7 +4995,8 @@ cpp_vend : cpp_const SEMI { $$.bitfield = 0; $$.throws = $1.throws; $$.throwf = $1.throwf; - $$.nexcept = $1.nexcept; + $$.nexcept = $1.nexcept; + $$.final = $1.final; } | cpp_const LBRACE { skip_balanced('{','}'); @@ -4992,7 +5006,8 @@ cpp_vend : cpp_const SEMI { $$.bitfield = 0; $$.throws = $1.throws; $$.throwf = $1.throwf; - $$.nexcept = $1.nexcept; + $$.nexcept = $1.nexcept; + $$.final = $1.final; } ; @@ -5210,6 +5225,7 @@ def_args : EQUAL definetype { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } } | EQUAL definetype LBRACKET expr RBRACKET { @@ -5223,6 +5239,7 @@ def_args : EQUAL definetype { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } else { $$.val = NewStringf("%s[%s]",$2.val,$4.val); } @@ -5236,6 +5253,7 @@ def_args : EQUAL definetype { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } | COLON expr { $$.val = 0; @@ -5245,6 +5263,7 @@ def_args : EQUAL definetype { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } | empty { $$.val = 0; @@ -5254,6 +5273,7 @@ def_args : EQUAL definetype { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } ; @@ -6293,6 +6313,7 @@ definetype : { /* scanner_check_typedef(); */ } expr { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; scanner_ignore_typedef(); } | default_delete { @@ -6319,6 +6340,7 @@ deleted_definition : DELETE_KW { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } ; @@ -6333,6 +6355,7 @@ explicit_default : DEFAULT { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } ; @@ -6525,6 +6548,7 @@ valexpr : exprnum { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } | WCHARCONST { $$.val = NewString($1); @@ -6538,6 +6562,7 @@ valexpr : exprnum { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } /* grouping */ @@ -6892,18 +6917,18 @@ virt_specifier_seq : OVERRIDE { $$ = 0; } | FINAL { - $$ = 0; + $$ = NewString("1"); } | FINAL OVERRIDE { - $$ = 0; + $$ = NewString("1"); } | OVERRIDE FINAL { - $$ = 0; + $$ = NewString("1"); } ; virt_specifier_seq_opt : virt_specifier_seq { - $$ = 0; + $$ = $1; } | empty { $$ = 0; @@ -6914,31 +6939,37 @@ exception_specification : THROW LPAREN parms RPAREN { $$.throws = $3; $$.throwf = NewString("1"); $$.nexcept = 0; + $$.final = 0; } | NOEXCEPT { $$.throws = 0; $$.throwf = 0; $$.nexcept = NewString("true"); + $$.final = 0; } | virt_specifier_seq { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = $1; } | THROW LPAREN parms RPAREN virt_specifier_seq { $$.throws = $3; $$.throwf = NewString("1"); $$.nexcept = 0; + $$.final = $5; } | NOEXCEPT virt_specifier_seq { $$.throws = 0; $$.throwf = 0; $$.nexcept = NewString("true"); + $$.final = $2; } | NOEXCEPT LPAREN expr RPAREN { $$.throws = 0; $$.throwf = 0; $$.nexcept = $3.val; + $$.final = 0; } ; @@ -6946,6 +6977,7 @@ qualifiers_exception_specification : cv_ref_qualifier { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; $$.qualifier = $1.qualifier; $$.refqualifier = $1.refqualifier; } @@ -6968,6 +7000,7 @@ cpp_const : qualifiers_exception_specification { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; $$.qualifier = 0; $$.refqualifier = 0; } @@ -6980,6 +7013,7 @@ ctor_end : cpp_const ctor_initializer SEMI { $$.throws = $1.throws; $$.throwf = $1.throwf; $$.nexcept = $1.nexcept; + $$.final = $1.final; if ($1.qualifier) Swig_error(cparse_file, cparse_line, "Constructor cannot have a qualifier.\n"); } @@ -6990,6 +7024,7 @@ ctor_end : cpp_const ctor_initializer SEMI { $$.throws = $1.throws; $$.throwf = $1.throwf; $$.nexcept = $1.nexcept; + $$.final = $1.final; if ($1.qualifier) Swig_error(cparse_file, cparse_line, "Constructor cannot have a qualifier.\n"); } @@ -7001,6 +7036,7 @@ ctor_end : cpp_const ctor_initializer SEMI { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } | LPAREN parms RPAREN LBRACE { skip_balanced('{','}'); @@ -7010,6 +7046,7 @@ ctor_end : cpp_const ctor_initializer SEMI { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } | EQUAL definetype SEMI { $$.have_parms = 0; @@ -7017,6 +7054,7 @@ ctor_end : cpp_const ctor_initializer SEMI { $$.throws = 0; $$.throwf = 0; $$.nexcept = 0; + $$.final = 0; } | exception_specification EQUAL default_delete SEMI { $$.have_parms = 0; @@ -7024,6 +7062,7 @@ ctor_end : cpp_const ctor_initializer SEMI { $$.throws = $1.throws; $$.throwf = $1.throwf; $$.nexcept = $1.nexcept; + $$.final = $1.final; if ($1.qualifier) Swig_error(cparse_file, cparse_line, "Constructor cannot have a qualifier.\n"); } diff --git a/Source/Include/swigwarn.h b/Source/Include/swigwarn.h index fde82bd96..fbcea4dbd 100644 --- a/Source/Include/swigwarn.h +++ b/Source/Include/swigwarn.h @@ -211,6 +211,7 @@ #define WARN_LANG_EXTEND_CONSTRUCTOR 522 #define WARN_LANG_EXTEND_DESTRUCTOR 523 #define WARN_LANG_EXPERIMENTAL 524 +#define WARN_LANG_DIRECTOR_FINAL 525 /* -- Doxygen comments -- */ diff --git a/Source/Modules/lang.cxx b/Source/Modules/lang.cxx index f9af9723a..acb5e4348 100644 --- a/Source/Modules/lang.cxx +++ b/Source/Modules/lang.cxx @@ -2109,7 +2109,7 @@ int Language::classDirectorMethods(Node *n) { Node *item = Getitem(vtable, i); String *method = Getattr(item, "methodNode"); String *fqdname = Getattr(item, "fqdname"); - if (GetFlag(method, "feature:nodirector")) + if (GetFlag(method, "feature:nodirector") || GetFlag(method, "final")) continue; String *wrn = Getattr(method, "feature:warnfilter"); @@ -2198,6 +2198,13 @@ int Language::classDirector(Node *n) { String *using_protected_members_code = NewString(""); for (ni = Getattr(n, "firstChild"); ni; ni = nextSibling(ni)) { Node *nodeType = Getattr(ni, "nodeType"); + if (Cmp(nodeType, "destructor") == 0 && GetFlag(ni, "final")) { + String *classtype = Getattr(n, "classtype"); + Swig_warning(WARN_LANG_DIRECTOR_FINAL, input_file, line_number, "Destructor of director base class %s is marked as final.\n", classtype); + Delete(vtable); + Delete(using_protected_members_code); + return SWIG_OK; + } bool cdeclaration = (Cmp(nodeType, "cdecl") == 0); if (cdeclaration && !GetFlag(ni, "feature:ignore")) { if (isNonVirtualProtectedAccess(ni)) { From d812a4291c0ae61b407aab705a26e9f14eb55a75 Mon Sep 17 00:00:00 2001 From: Zachary Hensley Date: Fri, 22 Feb 2019 10:55:20 -0600 Subject: [PATCH 013/134] Handle review comments --- Lib/java/std_list.i | 2 +- Lib/java/std_map.i | 9 +++------ Lib/java/std_set.i | 10 +++++----- Lib/java/std_unordered_map.i | 6 +++--- Lib/java/std_unordered_set.i | 10 +++++----- 5 files changed, 17 insertions(+), 20 deletions(-) diff --git a/Lib/java/std_list.i b/Lib/java/std_list.i index 3ad6511ce..82ccde38b 100644 --- a/Lib/java/std_list.i +++ b/Lib/java/std_list.i @@ -43,7 +43,7 @@ namespace std { this(); java.util.ListIterator<$typemap(jboxtype, T)> it = listIterator(0); // Special case the "copy constructor" here to avoid lots of cross-language calls - for (Object o : c) { + for (java.lang.Object o : c) { it.add(($typemap(jboxtype, T))o); } } diff --git a/Lib/java/std_map.i b/Lib/java/std_map.i index a7202bc06..6d5ca1aac 100644 --- a/Lib/java/std_map.i +++ b/Lib/java/std_map.i @@ -51,16 +51,13 @@ template > class map { %typemap(javabase) std::map< K, T, C > "java.util.AbstractMap<$typemap(jboxtype, K), $typemap(jboxtype, T)>" -%typemap(javaimports) std::map< K, T, C > - "import java.lang.Object;" - %proxycode %{ public int size() { return sizeImpl(); } - public boolean containsKey(Object key) { + public boolean containsKey(java.lang.Object key) { if (!(key instanceof $typemap(jboxtype, K))) { return false; } @@ -68,7 +65,7 @@ template > class map { return containsImpl(($typemap(jboxtype, K))key); } - public $typemap(jboxtype, T) get(Object key) { + public $typemap(jboxtype, T) get(java.lang.Object key) { if (!(key instanceof $typemap(jboxtype, K))) { return null; } @@ -93,7 +90,7 @@ template > class map { } } - public $typemap(jboxtype, T) remove(Object key) { + public $typemap(jboxtype, T) remove(java.lang.Object key) { if (!(key instanceof $typemap(jboxtype, K))) { return null; } diff --git a/Lib/java/std_set.i b/Lib/java/std_set.i index 06c5a63e7..086d10c8a 100644 --- a/Lib/java/std_set.i +++ b/Lib/java/std_set.i @@ -59,7 +59,7 @@ class set { public boolean addAll(java.util.Collection collection) { boolean didAddElement = false; - for (Object object : collection) { + for (java.lang.Object object : collection) { didAddElement |= add(($typemap(jboxtype, T))object); } @@ -96,7 +96,7 @@ class set { } public boolean containsAll(java.util.Collection collection) { - for (Object object : collection) { + for (java.lang.Object object : collection) { if (!contains(object)) { return false; } @@ -105,7 +105,7 @@ class set { return true; } - public boolean contains(Object object) { + public boolean contains(java.lang.Object object) { if (!(object instanceof $typemap(jboxtype, T))) { return false; } @@ -115,14 +115,14 @@ class set { public boolean removeAll(java.util.Collection collection) { boolean didRemoveElement = false; - for (Object object : collection) { + for (java.lang.Object object : collection) { didRemoveElement |= remove(object); } return didRemoveElement; } - public boolean remove(Object object) { + public boolean remove(java.lang.Object object) { if (!(object instanceof $typemap(jboxtype, T))) { return false; } diff --git a/Lib/java/std_unordered_map.i b/Lib/java/std_unordered_map.i index 8f62d7290..283a9b464 100644 --- a/Lib/java/std_unordered_map.i +++ b/Lib/java/std_unordered_map.i @@ -57,7 +57,7 @@ template class unordered_map { return sizeImpl(); } - public boolean containsKey(Object key) { + public boolean containsKey(java.lang.Object key) { if (!(key instanceof $typemap(jboxtype, K))) { return false; } @@ -65,7 +65,7 @@ template class unordered_map { return containsImpl(($typemap(jboxtype, K))key); } - public $typemap(jboxtype, T) get(Object key) { + public $typemap(jboxtype, T) get(java.lang.Object key) { if (!(key instanceof $typemap(jboxtype, K))) { return null; } @@ -90,7 +90,7 @@ template class unordered_map { } } - public $typemap(jboxtype, T) remove(Object key) { + public $typemap(jboxtype, T) remove(java.lang.Object key) { if (!(key instanceof $typemap(jboxtype, K))) { return null; } diff --git a/Lib/java/std_unordered_set.i b/Lib/java/std_unordered_set.i index cdc116e49..1a7b03688 100644 --- a/Lib/java/std_unordered_set.i +++ b/Lib/java/std_unordered_set.i @@ -59,7 +59,7 @@ class unordered_set { public boolean addAll(java.util.Collection collection) { boolean didAddElement = false; - for (Object object : collection) { + for (java.lang.Object object : collection) { didAddElement |= add(($typemap(jboxtype, T))object); } @@ -96,7 +96,7 @@ class unordered_set { } public boolean containsAll(java.util.Collection collection) { - for (Object object : collection) { + for (java.lang.Object object : collection) { if (!contains(object)) { return false; } @@ -105,7 +105,7 @@ class unordered_set { return true; } - public boolean contains(Object object) { + public boolean contains(java.lang.Object object) { if (!(object instanceof $typemap(jboxtype, T))) { return false; } @@ -115,14 +115,14 @@ class unordered_set { public boolean removeAll(java.util.Collection collection) { boolean didRemoveElement = false; - for (Object object : collection) { + for (java.lang.Object object : collection) { didRemoveElement |= remove(object); } return didRemoveElement; } - public boolean remove(Object object) { + public boolean remove(java.lang.Object object) { if (!(object instanceof $typemap(jboxtype, T))) { return false; } From ff9e9f9f98e195764a1f7ec0c34d8c311a7fd6f8 Mon Sep 17 00:00:00 2001 From: Takashi Tamura Date: Sat, 29 Apr 2017 21:55:21 +0900 Subject: [PATCH 014/134] [ruby] check whether object is of RTypedData using RTYPEDDATA_P. --- Examples/test-suite/ruby/Makefile.in | 1 + Examples/test-suite/ruby/ruby_rdata_runme.rb | 7 +++++++ Examples/test-suite/ruby_rdata.i | 20 ++++++++++++++++++++ Lib/ruby/rubyrun.swg | 4 ++-- 4 files changed, 30 insertions(+), 2 deletions(-) create mode 100644 Examples/test-suite/ruby/ruby_rdata_runme.rb create mode 100644 Examples/test-suite/ruby_rdata.i diff --git a/Examples/test-suite/ruby/Makefile.in b/Examples/test-suite/ruby/Makefile.in index add65fe9f..6393026a4 100644 --- a/Examples/test-suite/ruby/Makefile.in +++ b/Examples/test-suite/ruby/Makefile.in @@ -26,6 +26,7 @@ CPP_TEST_CASES = \ ruby_keywords \ ruby_minherit_shared_ptr \ ruby_naming \ + ruby_rdata \ ruby_track_objects \ ruby_track_objects_directors \ std_containers \ diff --git a/Examples/test-suite/ruby/ruby_rdata_runme.rb b/Examples/test-suite/ruby/ruby_rdata_runme.rb new file mode 100644 index 000000000..b7f293077 --- /dev/null +++ b/Examples/test-suite/ruby/ruby_rdata_runme.rb @@ -0,0 +1,7 @@ +require 'swig_assert' +require 'ruby_rdata' + +include Ruby_rdata + +swig_assert_equal_simple(1, take_proc_or_cpp_obj_and_ret_1(Proc.new{})) +swig_assert_equal_simple(1, take_proc_or_cpp_obj_and_ret_1(C.new)) diff --git a/Examples/test-suite/ruby_rdata.i b/Examples/test-suite/ruby_rdata.i new file mode 100644 index 000000000..fb89f1276 --- /dev/null +++ b/Examples/test-suite/ruby_rdata.i @@ -0,0 +1,20 @@ +%module ruby_rdata + +%{ + + class C {}; + + int take_proc_or_cpp_obj_and_ret_1(VALUE obj) { + return 1; + } + + int take_proc_or_cpp_obj_and_ret_1(class C) { + return 1; + } + +%} + +class C {}; + +int take_proc_or_cpp_obj_and_ret_1(VALUE); +int take_proc_or_cpp_obj_and_ret_1(C); diff --git a/Lib/ruby/rubyrun.swg b/Lib/ruby/rubyrun.swg index b4dd9ddf0..4b2ffe4b4 100644 --- a/Lib/ruby/rubyrun.swg +++ b/Lib/ruby/rubyrun.swg @@ -247,7 +247,7 @@ typedef struct { SWIGRUNTIME swig_ruby_owntype SWIG_Ruby_AcquirePtr(VALUE obj, swig_ruby_owntype own) { swig_ruby_owntype oldown = {0, 0}; - if (TYPE(obj) == T_DATA) { + if (TYPE(obj) == T_DATA && !RTYPEDDATA_P(obj)) { oldown.datafree = RDATA(obj)->dfree; RDATA(obj)->dfree = own.datafree; } @@ -268,7 +268,7 @@ SWIG_Ruby_ConvertPtrAndOwn(VALUE obj, void **ptr, swig_type_info *ty, int flags, *ptr = 0; return (flags & SWIG_POINTER_NO_NULL) ? SWIG_NullReferenceError : SWIG_OK; } else { - if (TYPE(obj) != T_DATA) { + if (TYPE(obj) != T_DATA || (TYPE(obj) == T_DATA && RTYPEDDATA_P(obj))) { return SWIG_ERROR; } Data_Get_Struct(obj, void, vptr); From 72723d354a830c461131f91e35b90e1d85b74e00 Mon Sep 17 00:00:00 2001 From: Takashi Tamura Date: Sat, 29 Apr 2017 22:48:07 +0900 Subject: [PATCH 015/134] minor edit --- Examples/test-suite/ruby_rdata.i | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Examples/test-suite/ruby_rdata.i b/Examples/test-suite/ruby_rdata.i index fb89f1276..06af06f36 100644 --- a/Examples/test-suite/ruby_rdata.i +++ b/Examples/test-suite/ruby_rdata.i @@ -8,7 +8,7 @@ return 1; } - int take_proc_or_cpp_obj_and_ret_1(class C) { + int take_proc_or_cpp_obj_and_ret_1(C c) { return 1; } From a006091b0f7cff98abc650e0364c0814aa976e8f Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 22 Feb 2019 19:46:29 +0000 Subject: [PATCH 016/134] Add in a definition for RTYPEDDATA_P for Ruby<1.9.3 This definition ensures the SWIG wrappers keep compiling in older versions of Ruby given the previous change (which uses RTYPEDDATA_P and hence requires Ruby 1.9.3). The definition of RTYPEDDATA_P is such that the previous commit plus the definition should keep the behaviour the same as before. --- CHANGES.current | 3 +++ Lib/ruby/rubyhead.swg | 3 +++ 2 files changed, 6 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 492dffa6a..af7384dc1 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,9 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-22: tamuratak + #984 Add support for RTypedData introduced in Ruby 1.9.3. + 2019-02-21: wsfulton #1240 Suppress Java 9 deprecation warnings on finalize method. diff --git a/Lib/ruby/rubyhead.swg b/Lib/ruby/rubyhead.swg index 9960087c6..90f07cf68 100644 --- a/Lib/ruby/rubyhead.swg +++ b/Lib/ruby/rubyhead.swg @@ -91,6 +91,9 @@ #ifndef RSTRUCT_PTR # define RSTRUCT_PTR(x) RSTRUCT(x)->ptr #endif +#ifndef RTYPEDDATA_P +# define RTYPEDDATA_P(x) (TYPE(x) != T_DATA) +#endif From 132359b01dc648960c5ed33f36924c80fd4e5772 Mon Sep 17 00:00:00 2001 From: Zackery Spytz Date: Sat, 23 Feb 2019 04:03:08 -0700 Subject: [PATCH 017/134] Update the COPYRIGHT file --- COPYRIGHT | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/COPYRIGHT b/COPYRIGHT index baf15a5db..e6df73ff8 100644 --- a/COPYRIGHT +++ b/COPYRIGHT @@ -19,6 +19,7 @@ Active SWIG Developers: Oliver Buchtala (oliver.buchtala@gmail.com) (Javascript) Neha Narang (narangneha03@gmail.com) (Javascript) Simon Marchetto (simon.marchetto@scilab-enterprises.com) (Scilab) + Zackery Spytz (zspytz@gmail.com) (OCaml, SWIG core) Past SWIG developers and major contributors include: Dave Beazley (dave-swig@dabeaz.com) (SWIG core, Python, Tcl, Perl) @@ -28,7 +29,7 @@ Past SWIG developers and major contributors include: Mikel Bancroft (mikel@franz.com) (Allegro CL) Surendra Singhi (efuzzyone@netscape.net) (CLISP, CFFI) Marcelo Matus (mmatus@acms.arizona.edu) (SWIG core, Python, UTL[python,perl,tcl,ruby]) - Art Yerkes (ayerkes@speakeasy.net) (Ocaml) + Art Yerkes (ayerkes@speakeasy.net) (OCaml) Lyle Johnson (lyle@users.sourceforge.net) (Ruby) Charlie Savage (cfis@interserv.com) (Ruby) Thien-Thi Nguyen (ttn@glug.org) (build/test/misc) From 17d0610d00a0b84640d06e470e4baffa4a176e25 Mon Sep 17 00:00:00 2001 From: Zackery Spytz Date: Sat, 23 Feb 2019 04:05:03 -0700 Subject: [PATCH 018/134] [OCaml] Fix possible memory leaks in generated dispatch functions All paths now free argv. --- Source/Modules/ocaml.cxx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Source/Modules/ocaml.cxx b/Source/Modules/ocaml.cxx index 8b248bad2..7e59def7f 100644 --- a/Source/Modules/ocaml.cxx +++ b/Source/Modules/ocaml.cxx @@ -752,7 +752,7 @@ public: Printv(df->code, "argv = (CAML_VALUE *)malloc( argc * sizeof( CAML_VALUE ) );\n" "for( i = 0; i < argc; i++ ) {\n" " argv[i] = caml_list_nth(args,i);\n" "}\n", NIL); - Printv(df->code, dispatch, "\n", NIL); + Printv(df->code, dispatch, "\nfree(argv);\n", NIL); Node *sibl = n; while (Getattr(sibl, "sym:previousSibling")) sibl = Getattr(sibl, "sym:previousSibling"); From 2bf5200242d190fd336b5fccc43c45eb71084550 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 23 Feb 2019 16:25:58 +0000 Subject: [PATCH 019/134] Changes file entry for Java (const char *STRING, size_t LENGTH) typemaps. --- CHANGES.current | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index af7384dc1..56b311aa5 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,11 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-23: gtbX + [Java] #1035 Add (const char *STRING, size_t LENGTH) typemaps in addition to the non-const + typemaps (char *STRING, size_t LENGTH) which does not attempt to write back to the const + string. + 2019-02-22: tamuratak #984 Add support for RTypedData introduced in Ruby 1.9.3. From 613ff08150e6264a5a4a964f2badeb6bba221398 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 23 Feb 2019 16:39:21 +0000 Subject: [PATCH 020/134] Java: more replace Object with java.lang.Object --- CHANGES.current | 4 ++++ Lib/java/java.swg | 8 ++++---- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 56b311aa5..3de7275ec 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,10 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-23: zphensley42 + Use fully qualified name 'java.lang.Object' instead of 'Object' in generated code to + avoid clashes with wrapped C++ classes called 'Object'. + 2019-02-23: gtbX [Java] #1035 Add (const char *STRING, size_t LENGTH) typemaps in addition to the non-const typemaps (char *STRING, size_t LENGTH) which does not attempt to write back to the const diff --git a/Lib/java/java.swg b/Lib/java/java.swg index 6a6523eba..a5b7bbab1 100644 --- a/Lib/java/java.swg +++ b/Lib/java/java.swg @@ -160,7 +160,7 @@ SWIGINTERN jint SWIG_JavaIntFromSize_t(size_t size) { %typemap(jtype) jfloat "float" %typemap(jtype) jdouble "double" %typemap(jtype) jstring "String" -%typemap(jtype) jobject "Object" +%typemap(jtype) jobject "java.lang.Object" %typemap(jtype) jbooleanArray "boolean[]" %typemap(jtype) jcharArray "char[]" %typemap(jtype) jbyteArray "byte[]" @@ -169,7 +169,7 @@ SWIGINTERN jint SWIG_JavaIntFromSize_t(size_t size) { %typemap(jtype) jlongArray "long[]" %typemap(jtype) jfloatArray "float[]" %typemap(jtype) jdoubleArray "double[]" -%typemap(jtype) jobjectArray "Object[]" +%typemap(jtype) jobjectArray "java.lang.Object[]" %typemap(jstype) jboolean "boolean" %typemap(jstype) jchar "char" @@ -180,7 +180,7 @@ SWIGINTERN jint SWIG_JavaIntFromSize_t(size_t size) { %typemap(jstype) jfloat "float" %typemap(jstype) jdouble "double" %typemap(jstype) jstring "String" -%typemap(jstype) jobject "Object" +%typemap(jstype) jobject "java.lang.Object" %typemap(jstype) jbooleanArray "boolean[]" %typemap(jstype) jcharArray "char[]" %typemap(jstype) jbyteArray "byte[]" @@ -189,7 +189,7 @@ SWIGINTERN jint SWIG_JavaIntFromSize_t(size_t size) { %typemap(jstype) jlongArray "long[]" %typemap(jstype) jfloatArray "float[]" %typemap(jstype) jdoubleArray "double[]" -%typemap(jstype) jobjectArray "Object[]" +%typemap(jstype) jobjectArray "java.lang.Object[]" /* Non primitive types */ %typemap(jni) SWIGTYPE "jlong" From e8cc5929de91226f23ae3d4e31d35e6c53472e6a Mon Sep 17 00:00:00 2001 From: Zackery Spytz Date: Sun, 24 Feb 2019 08:04:45 -0700 Subject: [PATCH 021/134] Remove a useless warning filter Add cpp11_final_directors to Examples/test-suite/common.mk. --- Examples/test-suite/common.mk | 1 + Examples/test-suite/cpp11_final_directors.i | 2 -- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/Examples/test-suite/common.mk b/Examples/test-suite/common.mk index 3d4edd47b..7b4836a17 100644 --- a/Examples/test-suite/common.mk +++ b/Examples/test-suite/common.mk @@ -571,6 +571,7 @@ CPP11_TEST_CASES += \ cpp11_director_enums \ cpp11_directors \ cpp11_explicit_conversion_operators \ + cpp11_final_directors \ cpp11_final_override \ cpp11_function_objects \ cpp11_inheriting_constructors \ diff --git a/Examples/test-suite/cpp11_final_directors.i b/Examples/test-suite/cpp11_final_directors.i index d724543ea..2b001bd7b 100644 --- a/Examples/test-suite/cpp11_final_directors.i +++ b/Examples/test-suite/cpp11_final_directors.i @@ -1,7 +1,5 @@ %module(directors="1") cpp11_final_directors -%warnfilter(SWIGWARN_PARSE_KEYWORD) final; - %director Derived; %inline %{ From 83ea2280e2e99ecafa2e3d2e041548a2f02aa19b Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 25 Feb 2019 19:27:23 +0000 Subject: [PATCH 022/134] Fix Python compile errors with overloading and varargs Fixes wrapping overloaded functions/constructors where a vararg function is declared after a non-vararg function. This is a long standing bug in the Python layer exposed since fastunpack was turned on by default. --- CHANGES.current | 4 ++ .../test-suite/go/varargs_overload_runme.go | 36 +++++++++++++++ .../ocaml/varargs_overload_runme.ml | 16 ++++++- .../python/varargs_overload_runme.py | 32 ++++++++++++++ .../scilab/varargs_overload_runme.sci | 22 +++++++++- Examples/test-suite/varargs_overload.i | 44 +++++++++++++++++++ Source/Modules/emit.cxx | 27 +++++++++++- Source/Modules/python.cxx | 20 +-------- Source/Modules/swigmod.h | 3 +- Source/Swig/parms.c | 16 +++++++ Source/Swig/swigparm.h | 1 + 11 files changed, 199 insertions(+), 22 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 3de7275ec..23455b289 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,10 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-25: wsfulton + [Python] Fix compile errors wrapping overloaded functions/constructors where a vararg + function is declared after a non-vararg function. + 2019-02-23: zphensley42 Use fully qualified name 'java.lang.Object' instead of 'Object' in generated code to avoid clashes with wrapped C++ classes called 'Object'. diff --git a/Examples/test-suite/go/varargs_overload_runme.go b/Examples/test-suite/go/varargs_overload_runme.go index 52fc1b0e9..5978be005 100644 --- a/Examples/test-suite/go/varargs_overload_runme.go +++ b/Examples/test-suite/go/varargs_overload_runme.go @@ -35,4 +35,40 @@ func main() { if varargs_overload.Vararg_over4("Hello", 123) != "Hello" { panic(8) } + + + // Same as above but non-vararg function declared first + + if varargs_overload.Vararg_over6("Hello") != "Hello" { + panic(0) + } + if varargs_overload.Vararg_over6(2) != "2" { + panic(1) + } + + if varargs_overload.Vararg_over7("Hello") != "Hello" { + panic(2) + } + if varargs_overload.Vararg_over7(2, 2.2) != "2 2.2" { + panic(3) + } + + if varargs_overload.Vararg_over8("Hello") != "Hello" { + panic(4) + } + if varargs_overload.Vararg_over8(2, 2.2, "hey") != "2 2.2 hey" { + panic(5) + } + + if varargs_overload.Vararg_over9("Hello") != "Hello" { + panic(6) + } + + if varargs_overload.Vararg_over9(123) != "123" { + panic(7) + } + + if varargs_overload.Vararg_over9("Hello", 123) != "Hello" { + panic(8) + } } diff --git a/Examples/test-suite/ocaml/varargs_overload_runme.ml b/Examples/test-suite/ocaml/varargs_overload_runme.ml index 3085e6258..418f881e3 100644 --- a/Examples/test-suite/ocaml/varargs_overload_runme.ml +++ b/Examples/test-suite/ocaml/varargs_overload_runme.ml @@ -11,5 +11,19 @@ let _ = assert (_vararg_over3 '(2, 2.2, "hey") as string = "2 2.2 hey"); assert (_vararg_over4 '("Hello") as string = "Hello"); assert (_vararg_over4 '(123) as string = "123"); - assert (_vararg_over4 '("Hello", 123) as string = "Hello") + assert (_vararg_over4 '("Hello", 123) as string = "Hello"); + + + (* Same as above but non-vararg function declared first *) + + assert (_vararg_over6 '("Hello") as string = "Hello"); + assert (_vararg_over6 '(2) as string = "2"); + assert (_vararg_over7 '("Hello") as string = "Hello"); + assert (_vararg_over7 '(2, 2.2) as string = "2 2.2"); + + assert (_vararg_over8 '("Hello") as string = "Hello"); + assert (_vararg_over8 '(2, 2.2, "hey") as string = "2 2.2 hey"); + assert (_vararg_over9 '("Hello") as string = "Hello"); + assert (_vararg_over9 '(123) as string = "123"); + assert (_vararg_over9 '("Hello", 123) as string = "Hello"); ;; diff --git a/Examples/test-suite/python/varargs_overload_runme.py b/Examples/test-suite/python/varargs_overload_runme.py index 37958620c..6f5a70222 100644 --- a/Examples/test-suite/python/varargs_overload_runme.py +++ b/Examples/test-suite/python/varargs_overload_runme.py @@ -28,3 +28,35 @@ if varargs_overload.vararg_over4(123) != "123": if varargs_overload.vararg_over4("Hello", 123) != "Hello": raise RuntimeError, "Failed" + + +# Same as above but non-vararg function declared first + +if varargs_overload.vararg_over6("Hello") != "Hello": + raise RuntimeError, "Failed" + +if varargs_overload.vararg_over6(2) != "2": + raise RuntimeError, "Failed" + + +if varargs_overload.vararg_over7("Hello") != "Hello": + raise RuntimeError, "Failed" + +if varargs_overload.vararg_over7(2, 2.2) != "2 2.2": + raise RuntimeError, "Failed" + + +if varargs_overload.vararg_over8("Hello") != "Hello": + raise RuntimeError, "Failed" + +if varargs_overload.vararg_over8(2, 2.2, "hey") != "2 2.2 hey": + raise RuntimeError, "Failed" + +if varargs_overload.vararg_over9("Hello") != "Hello": + raise RuntimeError, "Failed" + +if varargs_overload.vararg_over9(123) != "123": + raise RuntimeError, "Failed" + +if varargs_overload.vararg_over9("Hello", 123) != "Hello": + raise RuntimeError, "Failed" diff --git a/Examples/test-suite/scilab/varargs_overload_runme.sci b/Examples/test-suite/scilab/varargs_overload_runme.sci index 7603b667c..7426e8165 100644 --- a/Examples/test-suite/scilab/varargs_overload_runme.sci +++ b/Examples/test-suite/scilab/varargs_overload_runme.sci @@ -4,7 +4,7 @@ checkequal(vararg_over1("Hello"), "Hello", "vararg_over1(""Hello"")"); checkequal(vararg_over1(2), "2", "vararg_over1(2)"); -checkequal(vararg_over2("Hello"), "Hello", "vararg_over1(""Hello"")"); +checkequal(vararg_over2("Hello"), "Hello", "vararg_over2(""Hello"")"); checkequal(vararg_over2(2, 2.2), "2 2.2", "vararg_over2(2, 2.2)") @@ -18,4 +18,24 @@ checkequal(vararg_over4(123), "123", "vararg_over4(123)"); checkequal(vararg_over4("Hello", 123), "Hello", "vararg_over4(""Hello"", 123)"); + +// Same as above but non-vararg function declared first + +checkequal(vararg_over6("Hello"), "Hello", "vararg_over6(""Hello"")"); + +checkequal(vararg_over6(2), "2", "vararg_over6(2)"); + +checkequal(vararg_over7("Hello"), "Hello", "vararg_over7(""Hello"")"); + +checkequal(vararg_over7(2, 2.2), "2 2.2", "vararg_over7(2, 2.2)") + +checkequal(vararg_over8("Hello"), "Hello", "vararg_over8(""Hello"")"); + +checkequal(vararg_over8(2, 2.2, "hey"), "2 2.2 hey", "vararg_over8(2, 2.2, ""hey"")"); + +checkequal(vararg_over9("Hello"), "Hello", "vararg_over9(""Hello"")"); + +checkequal(vararg_over9(123), "123", "vararg_over9(123)"); + +checkequal(vararg_over9("Hello", 123), "Hello", "vararg_over9(""Hello"", 123)"); exec("swigtest.quit", -1); diff --git a/Examples/test-suite/varargs_overload.i b/Examples/test-suite/varargs_overload.i index 9a24e15a8..eb9dcaab9 100644 --- a/Examples/test-suite/varargs_overload.i +++ b/Examples/test-suite/varargs_overload.i @@ -44,3 +44,47 @@ const char *vararg_over4(int i) { return buffer; } %} + + +// Same as above but non-vararg function declared first + +%inline %{ +const char *vararg_over6(int i) { + static char buffer[256]; + sprintf(buffer, "%d", i); + return buffer; +} +const char *vararg_over6(const char *fmt, ...) { + return fmt; +} + +const char *vararg_over7(int i, double j) { + static char buffer[256]; + sprintf(buffer, "%d %g", i, j); + return buffer; +} +const char *vararg_over7(const char *fmt, ...) { + return fmt; +} + +const char *vararg_over8(int i, double j, const char *s) { + static char buffer[256]; + sprintf(buffer, "%d %g %s", i, j, s); + return buffer; +} +const char *vararg_over8(const char *fmt, ...) { + return fmt; +} +%} + +%varargs(int mode = 0) vararg_over9; +%inline %{ +const char *vararg_over9(int i) { + static char buffer[256]; + sprintf(buffer, "%d", i); + return buffer; +} +const char *vararg_over9(const char *fmt, ...) { + return fmt; +} +%} diff --git a/Source/Modules/emit.cxx b/Source/Modules/emit.cxx index 43f87db6f..7a4c2dcfb 100644 --- a/Source/Modules/emit.cxx +++ b/Source/Modules/emit.cxx @@ -188,7 +188,9 @@ void emit_attach_parmmaps(ParmList *l, Wrapper *f) { p = lp; while (p) { if (SwigType_isvarargs(Getattr(p, "type"))) { + // Mark the head of the ParmList that it has varargs Setattr(l, "emit:varargs", lp); +//Printf(stdout, "setting emit:varargs %s ... %s +++ %s\n", Getattr(l, "emit:varargs"), Getattr(l, "type"), Getattr(p, "type")); break; } p = nextSibling(p); @@ -329,7 +331,8 @@ int emit_num_required(ParmList *parms) { /* ----------------------------------------------------------------------------- * emit_isvarargs() * - * Checks if a function is a varargs function + * Checks if a ParmList is a parameter list containing varargs. + * This function requires emit_attach_parmmaps to have been called beforehand. * ----------------------------------------------------------------------------- */ int emit_isvarargs(ParmList *p) { @@ -340,6 +343,28 @@ int emit_isvarargs(ParmList *p) { return 0; } +/* ----------------------------------------------------------------------------- + * emit_isvarargs_function() + * + * Checks for varargs in a function/constructor (can be overloaded) + * ----------------------------------------------------------------------------- */ + +bool emit_isvarargs_function(Node *n) { + bool has_varargs = false; + Node *over = Getattr(n, "sym:overloaded"); + if (over) { + for (Node *sibling = over; sibling; sibling = Getattr(sibling, "sym:nextSibling")) { + if (ParmList_has_varargs(Getattr(sibling, "parms"))) { + has_varargs = true; + break; + } + } + } else { + has_varargs = ParmList_has_varargs(Getattr(n, "parms")) ? true : false; + } + return has_varargs; +} + /* ----------------------------------------------------------------------------- * void emit_mark_vararg_parms() * diff --git a/Source/Modules/python.cxx b/Source/Modules/python.cxx index 3c1767d6f..9ffc00592 100755 --- a/Source/Modules/python.cxx +++ b/Source/Modules/python.cxx @@ -2187,7 +2187,7 @@ public: * is_real_overloaded() * * Check if the function is overloaded, but not just have some - * siblings generated due to the original function have + * siblings generated due to the original function having * default arguments. * ------------------------------------------------------------ */ bool is_real_overloaded(Node *n) { @@ -2689,7 +2689,6 @@ public: bool add_self = builtin_self && (!builtin_ctor || director_class); bool builtin_getter = (builtin && GetFlag(n, "memberget")); bool builtin_setter = (builtin && GetFlag(n, "memberset") && !builtin_getter); - bool over_varargs = false; char const *self_param = builtin ? "self" : "SWIGUNUSEDPARM(self)"; char const *wrap_return = builtin_ctor ? "int " : "PyObject *"; String *linkage = NewString("SWIGINTERN "); @@ -2765,22 +2764,7 @@ public: } } - if (overname) { - String *over_varargs_attr = Getattr(n, "python:overvarargs"); - if (!over_varargs_attr) { - for (Node *sibling = n; sibling; sibling = Getattr(sibling, "sym:nextSibling")) { - if (emit_isvarargs(Getattr(sibling, "parms"))) { - over_varargs = true; - break; - } - } - over_varargs_attr = NewString(over_varargs ? "1" : "0"); - for (Node *sibling = n; sibling; sibling = Getattr(sibling, "sym:nextSibling")) - Setattr(sibling, "python:overvarargs", over_varargs_attr); - } - if (Strcmp(over_varargs_attr, "0") != 0) - over_varargs = true; - } + bool over_varargs = emit_isvarargs_function(n); int funpack = fastunpack && !varargs && !over_varargs && !allow_kwargs; int noargs = funpack && (tuple_required == 0 && tuple_arguments == 0); diff --git a/Source/Modules/swigmod.h b/Source/Modules/swigmod.h index ef49c5684..583cb13fe 100644 --- a/Source/Modules/swigmod.h +++ b/Source/Modules/swigmod.h @@ -383,7 +383,8 @@ List *SWIG_output_files(); void SWIG_library_directory(const char *); int emit_num_arguments(ParmList *); int emit_num_required(ParmList *); -int emit_isvarargs(ParmList *); +int emit_isvarargs(ParmList *p); +bool emit_isvarargs_function(Node *n); void emit_attach_parmmaps(ParmList *, Wrapper *f); void emit_mark_varargs(ParmList *l); String *emit_action(Node *n); diff --git a/Source/Swig/parms.c b/Source/Swig/parms.c index bec1e63fa..3e832c361 100644 --- a/Source/Swig/parms.c +++ b/Source/Swig/parms.c @@ -254,3 +254,19 @@ int ParmList_has_defaultargs(ParmList *p) { } return 0; } + +/* --------------------------------------------------------------------- + * ParmList_has_varargs() + * + * Returns 1 if the parameter list passed in has varargs. + * Otherwise returns 0. + * ---------------------------------------------------------------------- */ + +int ParmList_has_varargs(ParmList *p) { + Parm *lp = 0; + while (p) { + lp = p; + p = nextSibling(p); + } + return lp ? SwigType_isvarargs(Getattr(lp, "type")) : 0; +} diff --git a/Source/Swig/swigparm.h b/Source/Swig/swigparm.h index 368b4d26b..7b27df5f6 100644 --- a/Source/Swig/swigparm.h +++ b/Source/Swig/swigparm.h @@ -24,6 +24,7 @@ extern ParmList *CopyParmListMax(ParmList *, int count); extern int ParmList_len(ParmList *); extern int ParmList_numrequired(ParmList *); extern int ParmList_has_defaultargs(ParmList *p); +extern int ParmList_has_varargs(ParmList *p); /* Output functions */ extern String *ParmList_str(ParmList *); From 9e29ae16d2bb51e47b255867551c794a6e45817a Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 1 Mar 2019 08:15:03 +0000 Subject: [PATCH 023/134] Update template_opaque testcase --- Examples/test-suite/template_opaque.i | 3 --- 1 file changed, 3 deletions(-) diff --git a/Examples/test-suite/template_opaque.i b/Examples/test-suite/template_opaque.i index b910e47e3..7aafd62e8 100644 --- a/Examples/test-suite/template_opaque.i +++ b/Examples/test-suite/template_opaque.i @@ -36,7 +36,4 @@ namespace A { } } -#ifndef SWIGCSHARP -// C# vector typemaps only ready for simple cases right now %template(OpaqueVectorType) std::vector; -#endif From be491506a4036f627778b71641dff1fdf66b9a67 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 1 Mar 2019 18:01:14 +0000 Subject: [PATCH 024/134] Java std::vector improvements for types that do not have a default constructor. The std::vector wrappers have been changed to work by default for elements that are not default insertable, i.e. have no default constructor. This has been achieved by not wrapping: vector(size_type n); Previously the above had to be ignored via %ignore. If the above constructor is still required it can be added back in again via %extend: %extend std::vector { vector(size_type count) { return new std::vector< T >(count); } } Alternatively, the following wrapped constructor could be used as it provides near-enough equivalent functionality: vector(jint count, const value_type& value); The equivalent change to std::list has also been made (std::list wrappers were not in the previous release [3.0.12] though). --- CHANGES.current | 24 +++++++++++++++++++ Examples/test-suite/common.mk | 1 + .../test-suite/java/li_std_list_runme.java | 2 +- .../test-suite/java/li_std_vector_runme.java | 2 +- .../test-suite/stl_no_default_constructor.i | 19 +++++++++++++++ Lib/java/std_list.i | 5 ---- Lib/java/std_vector.i | 5 ---- 7 files changed, 46 insertions(+), 12 deletions(-) create mode 100644 Examples/test-suite/stl_no_default_constructor.i diff --git a/CHANGES.current b/CHANGES.current index 23455b289..43df38b2c 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,30 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-02-28: wsfulton + [Java] std::vector improvements for types that do not have a default constructor. + + The std::vector wrappers have been changed to work by default for elements that are + not default insertable, i.e. have no default constructor. This has been achieved by + not wrapping: + + vector(size_type n); + + Previously the above had to be ignored via %ignore. + + If the above constructor is still required it can be added back in again via %extend: + + %extend std::vector { + vector(size_type count) { return new std::vector< T >(count); } + } + + Alternatively, the following wrapped constructor could be used as it provides near-enough + equivalent functionality: + + vector(jint count, const value_type& value); + + *** POTENTIAL INCOMPATIBILITY *** + 2019-02-25: wsfulton [Python] Fix compile errors wrapping overloaded functions/constructors where a vararg function is declared after a non-vararg function. diff --git a/Examples/test-suite/common.mk b/Examples/test-suite/common.mk index 3d4edd47b..60f6a9522 100644 --- a/Examples/test-suite/common.mk +++ b/Examples/test-suite/common.mk @@ -407,6 +407,7 @@ CPP_TEST_CASES += \ static_array_member \ static_const_member \ static_const_member_2 \ + stl_no_default_constructor \ string_constants \ struct_initialization_cpp \ struct_value \ diff --git a/Examples/test-suite/java/li_std_list_runme.java b/Examples/test-suite/java/li_std_list_runme.java index 94bcada02..96412fdaf 100644 --- a/Examples/test-suite/java/li_std_list_runme.java +++ b/Examples/test-suite/java/li_std_list_runme.java @@ -53,7 +53,7 @@ public class li_std_list_runme { if (v1.size() != 0) throw new RuntimeException("v1 test (16) failed"); if (v1.remove(Integer.valueOf(456))) throw new RuntimeException("v1 test (17) failed"); - if (new IntList(3).size() != 3) throw new RuntimeException("constructor initial size test failed"); + if (new IntList(3, 0).size() != 3) throw new RuntimeException("constructor initial size test failed"); for (int n : new IntList(10, 999)) if (n != 999) throw new RuntimeException("constructor initialization with value failed"); for (int n : new IntList(new IntList(10, 999))) diff --git a/Examples/test-suite/java/li_std_vector_runme.java b/Examples/test-suite/java/li_std_vector_runme.java index ba0648562..fc8ba0f6f 100644 --- a/Examples/test-suite/java/li_std_vector_runme.java +++ b/Examples/test-suite/java/li_std_vector_runme.java @@ -54,7 +54,7 @@ public class li_std_vector_runme { if (v1.size() != 0) throw new RuntimeException("v1 test (16) failed"); if (v1.remove(Integer.valueOf(456))) throw new RuntimeException("v1 test (17) failed"); - if (new IntVector(3).size() != 3) throw new RuntimeException("constructor initial size test failed"); + if (new IntVector(3, 0).size() != 3) throw new RuntimeException("constructor initial size test failed"); for (int n : new IntVector(10, 999)) if (n != 999) throw new RuntimeException("constructor initialization with value failed"); for (int n : new IntVector(new IntVector(10, 999))) diff --git a/Examples/test-suite/stl_no_default_constructor.i b/Examples/test-suite/stl_no_default_constructor.i new file mode 100644 index 000000000..164710bd5 --- /dev/null +++ b/Examples/test-suite/stl_no_default_constructor.i @@ -0,0 +1,19 @@ +%module stl_no_default_constructor + +%include + +%inline %{ +struct NoDefaultCtor { + int value; + NoDefaultCtor(int i) : value(i) {} +}; +%} + +#if defined(SWIGCSHARP) || defined(SWIGJAVA) || defined(SWIGD) +%template(VectorNoDefaultCtor) std::vector; +#endif + +#if defined(SWIGJAVA) +%include +%template(ListNoDefaultCtor) std::list; +#endif diff --git a/Lib/java/std_list.i b/Lib/java/std_list.i index 82ccde38b..1077bd0a0 100644 --- a/Lib/java/std_list.i +++ b/Lib/java/std_list.i @@ -198,11 +198,6 @@ namespace std { %extend { %fragment("SWIG_ListSize"); - list(jint count) throw (std::out_of_range) { - if (count < 0) - throw std::out_of_range("list count must be positive"); - return new std::list(static_cast::size_type>(count)); - } list(jint count, const T &value) throw (std::out_of_range) { if (count < 0) diff --git a/Lib/java/std_vector.i b/Lib/java/std_vector.i index f621e8992..88de46f46 100644 --- a/Lib/java/std_vector.i +++ b/Lib/java/std_vector.i @@ -94,11 +94,6 @@ SWIGINTERN jint SWIG_VectorSize(size_t size) { void clear(); %extend { %fragment("SWIG_VectorSize"); - vector(jint count) throw (std::out_of_range) { - if (count < 0) - throw std::out_of_range("vector count must be positive"); - return new std::vector< CTYPE >(static_cast::size_type>(count)); - } vector(jint count, const CTYPE &value) throw (std::out_of_range) { if (count < 0) From cfdf65eb3414e1c0ffb7156de72afb280dc8fe0d Mon Sep 17 00:00:00 2001 From: John Wason Date: Fri, 1 Mar 2019 19:13:35 -0500 Subject: [PATCH 025/134] Include all template parameters for std_unordered_map macro --- Lib/python/std_unordered_map.i | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/Lib/python/std_unordered_map.i b/Lib/python/std_unordered_map.i index 79882b292..76acbb1ec 100644 --- a/Lib/python/std_unordered_map.i +++ b/Lib/python/std_unordered_map.i @@ -56,26 +56,26 @@ %fragment("StdUnorderedMapTraits","header",fragment="StdMapCommonTraits",fragment="StdUnorderedMapForwardIteratorTraits") { namespace swig { - template + template inline void - assign(const SwigPySeq& swigpyseq, std::unordered_map *unordered_map) { - typedef typename std::unordered_map::value_type value_type; + assign(const SwigPySeq& swigpyseq, std::unordered_map *unordered_map) { + typedef typename std::unordered_map::value_type value_type; typename SwigPySeq::const_iterator it = swigpyseq.begin(); for (;it != swigpyseq.end(); ++it) { unordered_map->insert(value_type(it->first, it->second)); } } - template - struct traits_reserve > { - static void reserve(std::unordered_map &seq, typename std::unordered_map::size_type n) { + template + struct traits_reserve > { + static void reserve(std::unordered_map &seq, typename std::unordered_map::size_type n) { seq.reserve(n); } }; - template - struct traits_asptr > { - typedef std::unordered_map unordered_map_type; + template + struct traits_asptr > { + typedef std::unordered_map unordered_map_type; static int asptr(PyObject *obj, unordered_map_type **val) { int res = SWIG_ERROR; SWIG_PYTHON_THREAD_BEGIN_BLOCK; @@ -85,7 +85,7 @@ /* In Python 3.x the ".items()" method returns a dict_items object */ items = PySequence_Fast(items, ".items() didn't return a sequence!"); %#endif - res = traits_asptr_stdseq, std::pair >::asptr(items, val); + res = traits_asptr_stdseq, std::pair >::asptr(items, val); } else { unordered_map_type *p; swig_type_info *descriptor = swig::type_info(); @@ -97,9 +97,9 @@ } }; - template - struct traits_from > { - typedef std::unordered_map unordered_map_type; + template + struct traits_from > { + typedef std::unordered_map unordered_map_type; typedef typename unordered_map_type::const_iterator const_iterator; typedef typename unordered_map_type::size_type size_type; From b9c4a84780157ab1812a4ba6cdb72020430f8385 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 2 Mar 2019 19:02:35 +0000 Subject: [PATCH 026/134] Warning fix for final destructor in directors Fix suppression of final destructors used in director classes. Add testcase for final destructors in director classes. --- Examples/test-suite/cpp11_final_directors.i | 8 ++++++++ Examples/test-suite/errors/cpp_final_destructor.stderr | 1 + Source/Modules/lang.cxx | 2 ++ 3 files changed, 11 insertions(+) create mode 100644 Examples/test-suite/errors/cpp_final_destructor.stderr diff --git a/Examples/test-suite/cpp11_final_directors.i b/Examples/test-suite/cpp11_final_directors.i index 2b001bd7b..ccd5d1b20 100644 --- a/Examples/test-suite/cpp11_final_directors.i +++ b/Examples/test-suite/cpp11_final_directors.i @@ -1,6 +1,9 @@ %module(directors="1") cpp11_final_directors %director Derived; +%director BaseFinalDestructor; + +%warnfilter(SWIGWARN_LANG_DIRECTOR_FINAL) BaseFinalDestructor::~BaseFinalDestructor; %inline %{ struct Base { @@ -13,4 +16,9 @@ struct Derived : Base { virtual int meth() { return 2; } virtual ~Derived() {} }; + +struct BaseFinalDestructor { + virtual void basefinalmeth() final {} + virtual ~BaseFinalDestructor() final {} +}; %} diff --git a/Examples/test-suite/errors/cpp_final_destructor.stderr b/Examples/test-suite/errors/cpp_final_destructor.stderr new file mode 100644 index 000000000..924396341 --- /dev/null +++ b/Examples/test-suite/errors/cpp_final_destructor.stderr @@ -0,0 +1 @@ +cpp_final_destructor.i:7: Warning 525: Destructor of director base class BaseFinal is marked as final. diff --git a/Source/Modules/lang.cxx b/Source/Modules/lang.cxx index acb5e4348..d79e07f36 100644 --- a/Source/Modules/lang.cxx +++ b/Source/Modules/lang.cxx @@ -2200,7 +2200,9 @@ int Language::classDirector(Node *n) { Node *nodeType = Getattr(ni, "nodeType"); if (Cmp(nodeType, "destructor") == 0 && GetFlag(ni, "final")) { String *classtype = Getattr(n, "classtype"); + SWIG_WARN_NODE_BEGIN(ni); Swig_warning(WARN_LANG_DIRECTOR_FINAL, input_file, line_number, "Destructor of director base class %s is marked as final.\n", classtype); + SWIG_WARN_NODE_END(ni); Delete(vtable); Delete(using_protected_members_code); return SWIG_OK; From 3b07cba74066ef3a95b1e66a8c7d869a9510d1b9 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 2 Mar 2019 19:57:33 +0000 Subject: [PATCH 027/134] Fixes for final destructors in director classes A class marked as a director with a final destructor should not be a wrapped as a director class. Fix seg faults in this case. --- Examples/test-suite/cpp11_final_directors.i | 9 +++++++++ Source/Modules/lang.cxx | 3 +++ 2 files changed, 12 insertions(+) diff --git a/Examples/test-suite/cpp11_final_directors.i b/Examples/test-suite/cpp11_final_directors.i index ccd5d1b20..b58111adb 100644 --- a/Examples/test-suite/cpp11_final_directors.i +++ b/Examples/test-suite/cpp11_final_directors.i @@ -1,9 +1,13 @@ %module(directors="1") cpp11_final_directors %director Derived; + +// Check SWIG will not wrap these classes as directors where the destructors are final %director BaseFinalDestructor; +%director BaseFinalDestructor2; %warnfilter(SWIGWARN_LANG_DIRECTOR_FINAL) BaseFinalDestructor::~BaseFinalDestructor; +%warnfilter(SWIGWARN_LANG_DIRECTOR_FINAL) BaseFinalDestructor2::~BaseFinalDestructor2; %inline %{ struct Base { @@ -21,4 +25,9 @@ struct BaseFinalDestructor { virtual void basefinalmeth() final {} virtual ~BaseFinalDestructor() final {} }; + +struct BaseFinalDestructor2 { + virtual void basefinalmeth() {} + virtual ~BaseFinalDestructor2() final {} +}; %} diff --git a/Source/Modules/lang.cxx b/Source/Modules/lang.cxx index d79e07f36..272936e4e 100644 --- a/Source/Modules/lang.cxx +++ b/Source/Modules/lang.cxx @@ -1894,6 +1894,8 @@ int Language::unrollVirtualMethods(Node *n, Node *parent, List *vm, int default_ } if (!checkAttribute(nn, "storage", "virtual")) continue; + if (GetFlag(nn, "final")) + continue; /* we need to add methods(cdecl) and destructor (to check for throw decl) */ int is_destructor = (Cmp(nodeType, "destructor") == 0); if ((Cmp(nodeType, "cdecl") == 0) || is_destructor) { @@ -2203,6 +2205,7 @@ int Language::classDirector(Node *n) { SWIG_WARN_NODE_BEGIN(ni); Swig_warning(WARN_LANG_DIRECTOR_FINAL, input_file, line_number, "Destructor of director base class %s is marked as final.\n", classtype); SWIG_WARN_NODE_END(ni); + SetFlag(n, "feature:nodirector"); Delete(vtable); Delete(using_protected_members_code); return SWIG_OK; From 34108deec7e89d9f7c70b337702cfffb1e34c006 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sun, 3 Mar 2019 14:26:43 +0000 Subject: [PATCH 028/134] Documentation for directors and virtual final methods --- Doc/Manual/Go.html | 4 +++- Doc/Manual/Java.html | 7 ++++--- Doc/Manual/Perl5.html | 7 ++++--- Doc/Manual/Php.html | 7 ++++--- Doc/Manual/Python.html | 7 ++++--- 5 files changed, 19 insertions(+), 13 deletions(-) diff --git a/Doc/Manual/Go.html b/Doc/Manual/Go.html index 4a60e45e0..047b46edf 100644 --- a/Doc/Manual/Go.html +++ b/Doc/Manual/Go.html @@ -785,7 +785,9 @@ In order to override virtual methods on a C++ class with Go methods the NewDirectorClassName constructor functions receives a DirectorInterface argument. The methods in the DirectorInterface are a subset of the public and protected virtual methods -of the C++ class. If the DirectorInterface contains a method with a +of the C++ class. +Virtual methods that have a final specifier are unsurprisingly excluded. +If the DirectorInterface contains a method with a matching signature to a virtual method of the C++ class then the virtual C++ method will be overwritten with the Go method. As Go doesn't support protected methods all overridden protected virtual C++ methods will be public in Go. diff --git a/Doc/Manual/Java.html b/Doc/Manual/Java.html index bf77c1562..3a04b8a79 100644 --- a/Doc/Manual/Java.html +++ b/Doc/Manual/Java.html @@ -3629,7 +3629,7 @@ The %feature directive can be applied globally, to specific classes, and to spec // generate directors for all classes that have virtual methods %feature("director"); -// generate directors for all virtual methods in class Foo +// generate directors for the virtual methods in class Foo %feature("director") Foo; @@ -3647,7 +3647,7 @@ So for example,

    -will generate directors for all virtual methods of class Foo except bar(). +will generate directors for the virtual methods of class Foo except bar().

    @@ -3683,7 +3683,8 @@ The director classes store a pointer to their underlying Java proxy classes.

    For simplicity let's ignore the Swig::Director class and refer to the original C++ class as the director's base class. By default, a director class extends all virtual methods in the inheritance chain of its base class (see the preceding section for how to modify this behavior). -Thus all virtual method calls, whether they originate in C++ or in Java via proxy classes, eventually end up in at the implementation in the director class. +Virtual methods that have a final specifier are unsurprisingly excluded. +Thus the virtual method calls, whether they originate in C++ or in Java via proxy classes, eventually end up in at the implementation in the director class. The job of the director methods is to route these method calls to the appropriate place in the inheritance chain. By "appropriate place" we mean the method that would have been called if the C++ base class and its Java derived classes were seamlessly integrated. That seamless integration is exactly what the director classes provide, transparently skipping over all the messy JNI glue code that binds the two languages together. diff --git a/Doc/Manual/Perl5.html b/Doc/Manual/Perl5.html index 5ce765c26..766ccaede 100644 --- a/Doc/Manual/Perl5.html +++ b/Doc/Manual/Perl5.html @@ -3070,7 +3070,7 @@ globally, to specific classes, and to specific methods, like this: // generate directors for all classes that have virtual methods %feature("director"); -// generate directors for all virtual methods in class Foo +// generate directors for the virtual methods in class Foo %feature("director") Foo; @@ -3088,7 +3088,7 @@ directors for specific classes or methods. So for example,

    -will generate directors for all virtual methods of class Foo except +will generate directors for the virtual methods of class Foo except bar().

    @@ -3153,7 +3153,8 @@ For simplicity let's ignore the Swig::Director class and refer to the original C++ class as the director's base class. By default, a director class extends all virtual methods in the inheritance chain of its base class (see the preceding section for how to modify this behavior). -Thus all virtual method calls, whether they originate in C++ or in +Virtual methods that have a final specifier are unsurprisingly excluded. +Thus the virtual method calls, whether they originate in C++ or in Perl via proxy classes, eventually end up in at the implementation in the director class. The job of the director methods is to route these method calls to the appropriate place in the inheritance chain. By diff --git a/Doc/Manual/Php.html b/Doc/Manual/Php.html index 85732fd33..1b8b2d468 100644 --- a/Doc/Manual/Php.html +++ b/Doc/Manual/Php.html @@ -937,7 +937,7 @@ globally, to specific classes, and to specific methods, like this: // generate directors for all classes that have virtual methods %feature("director"); -// generate directors for all virtual methods in class Foo +// generate directors for the virtual methods in class Foo %feature("director") Foo; @@ -955,7 +955,7 @@ directors for specific classes or methods. So for example,

    -will generate directors for all virtual methods of class Foo except +will generate directors for the virtual methods of class Foo except bar().

    @@ -1020,7 +1020,8 @@ For simplicity let's ignore the Swig::Director class and refer to the original C++ class as the director's base class. By default, a director class extends all virtual methods in the inheritance chain of its base class (see the preceding section for how to modify this behavior). -Thus all virtual method calls, whether they originate in C++ or in +Virtual methods that have a final specifier are unsurprisingly excluded. +Thus the virtual method calls, whether they originate in C++ or in PHP via proxy classes, eventually end up in at the implementation in the director class. The job of the director methods is to route these method calls to the appropriate place in the inheritance chain. By "appropriate diff --git a/Doc/Manual/Python.html b/Doc/Manual/Python.html index 6a174fddf..2554e9da3 100644 --- a/Doc/Manual/Python.html +++ b/Doc/Manual/Python.html @@ -2934,7 +2934,7 @@ globally, to specific classes, and to specific methods, like this: // generate directors for all classes that have virtual methods %feature("director"); -// generate directors for all virtual methods in class Foo +// generate directors for the virtual methods in class Foo %feature("director") Foo; @@ -2952,7 +2952,7 @@ directors for specific classes or methods. So for example,

    -will generate directors for all virtual methods of class Foo except +will generate directors for the virtual methods of class Foo except bar().

    @@ -3018,7 +3018,8 @@ For simplicity let's ignore the Swig::Director class and refer to the original C++ class as the director's base class. By default, a director class extends all virtual methods in the inheritance chain of its base class (see the preceding section for how to modify this behavior). -Thus all virtual method calls, whether they originate in C++ or in +Virtual methods that have a final specifier are unsurprisingly excluded. +Thus the virtual method calls, whether they originate in C++ or in Python via proxy classes, eventually end up in at the implementation in the director class. The job of the director methods is to route these method calls to the appropriate place in the inheritance chain. By From 39b44a377a785ac45d7de5cdf725fb10caef48d1 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sun, 3 Mar 2019 15:12:29 +0000 Subject: [PATCH 029/134] Warning tweaks for destructors that are final in director classes --- Doc/Manual/Warnings.html | 2 +- Examples/test-suite/errors/cpp_final_destructor.stderr | 2 +- Source/Modules/lang.cxx | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Doc/Manual/Warnings.html b/Doc/Manual/Warnings.html index 8b2ab2b95..c63d7de0c 100644 --- a/Doc/Manual/Warnings.html +++ b/Doc/Manual/Warnings.html @@ -535,7 +535,7 @@ example.i(4) : Syntax error in input(1).
  • 522. Use of an illegal constructor name 'name' in %extend is deprecated, the constructor name should be 'name'.
  • 523. Use of an illegal destructor name 'name' in %extend is deprecated, the destructor name should be 'name'.
  • 524. Experimental target language. Target language language specified by lang is an experimental language. Please read about SWIG experimental languages, htmllink. -
  • 525. The director base class 'name' or the destructor of director base class 'name' is marked as final. +
  • 525. Destructor declaration is final, name cannot be a director class.

    18.9.6 Doxygen comments (560-599)

    diff --git a/Examples/test-suite/errors/cpp_final_destructor.stderr b/Examples/test-suite/errors/cpp_final_destructor.stderr index 924396341..d8c509d0c 100644 --- a/Examples/test-suite/errors/cpp_final_destructor.stderr +++ b/Examples/test-suite/errors/cpp_final_destructor.stderr @@ -1 +1 @@ -cpp_final_destructor.i:7: Warning 525: Destructor of director base class BaseFinal is marked as final. +cpp_final_destructor.i:7: Warning 525: Destructor BaseFinal::~BaseFinal() is final, BaseFinal cannot be a director class. diff --git a/Source/Modules/lang.cxx b/Source/Modules/lang.cxx index 272936e4e..f7979b611 100644 --- a/Source/Modules/lang.cxx +++ b/Source/Modules/lang.cxx @@ -2203,7 +2203,7 @@ int Language::classDirector(Node *n) { if (Cmp(nodeType, "destructor") == 0 && GetFlag(ni, "final")) { String *classtype = Getattr(n, "classtype"); SWIG_WARN_NODE_BEGIN(ni); - Swig_warning(WARN_LANG_DIRECTOR_FINAL, input_file, line_number, "Destructor of director base class %s is marked as final.\n", classtype); + Swig_warning(WARN_LANG_DIRECTOR_FINAL, input_file, line_number, "Destructor %s is final, %s cannot be a director class.\n", Swig_name_decl(ni), classtype); SWIG_WARN_NODE_END(ni); SetFlag(n, "feature:nodirector"); Delete(vtable); From 412b113c0b93b2c209ec53265b35ff4d91db257e Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sun, 3 Mar 2019 16:00:02 +0000 Subject: [PATCH 030/134] Run errors test cases in predictable order --- Examples/test-suite/errors/Makefile.in | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Examples/test-suite/errors/Makefile.in b/Examples/test-suite/errors/Makefile.in index c66840997..10e5bdd8f 100644 --- a/Examples/test-suite/errors/Makefile.in +++ b/Examples/test-suite/errors/Makefile.in @@ -24,11 +24,11 @@ SWIG_LIB_SET = @SWIG_LIB_SET@ SWIGINVOKE = $(SWIG_LIB_SET) $(SWIGTOOL) $(SWIGEXE) # All .i files with prefix 'cpp_' will be treated as C++ input and remaining .i files as C input -ALL_ERROR_TEST_CASES := $(patsubst %.i,%, $(notdir $(wildcard $(srcdir)/*.i))) -CPP_ERROR_TEST_CASES := $(filter cpp_%, $(ALL_ERROR_TEST_CASES)) -C_ERROR_TEST_CASES := $(filter-out $(CPP_ERROR_TEST_CASES), $(ALL_ERROR_TEST_CASES)) -DOXYGEN_ERROR_TEST_CASES := $(filter doxygen_%, $(C_ERROR_TEST_CASES)) -C_ERROR_TEST_CASES := $(filter-out $(DOXYGEN_ERROR_TEST_CASES), $(C_ERROR_TEST_CASES)) +ALL_ERROR_TEST_CASES := $(sort $(patsubst %.i,%, $(notdir $(wildcard $(srcdir)/*.i)))) +CPP_ERROR_TEST_CASES := $(sort $(filter cpp_%, $(ALL_ERROR_TEST_CASES))) +C_ERROR_TEST_CASES := $(sort $(filter-out $(CPP_ERROR_TEST_CASES), $(ALL_ERROR_TEST_CASES))) +DOXYGEN_ERROR_TEST_CASES := $(sort $(filter doxygen_%, $(C_ERROR_TEST_CASES))) +C_ERROR_TEST_CASES := $(sort $(filter-out $(DOXYGEN_ERROR_TEST_CASES), $(C_ERROR_TEST_CASES))) # Always use C++ for Doxygen tests, there doesn't seem to be any need to # distinguish between C and C++ Doxygen tests. From e5ae89403dd8b58737793aa3c32f0f90abcc213d Mon Sep 17 00:00:00 2001 From: Mizux Date: Tue, 5 Mar 2019 16:11:50 +0100 Subject: [PATCH 031/134] Fix "Default Marshaling for Arrays" Previous link is dead... --- Doc/Manual/CSharp.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Doc/Manual/CSharp.html b/Doc/Manual/CSharp.html index 7a9b7470b..d485a9714 100644 --- a/Doc/Manual/CSharp.html +++ b/Doc/Manual/CSharp.html @@ -643,7 +643,7 @@ passing a direct reference as described in the next section.

    For more information on the subject, see the -Default Marshaling for Arrays article +Default Marshaling for Arrays article on MSDN.

    From a0b84f51807dbfd35f334bb9c266841f8d2ae111 Mon Sep 17 00:00:00 2001 From: Zackery Spytz Date: Thu, 7 Mar 2019 09:44:01 -0700 Subject: [PATCH 032/134] Fix some MSVC compiler warnings in the test suite nested_in_template_wrap.cxx(247): warning C4244: 'initializing': conversion from 'double' to 'int', possible loss of data python_pybuffer_wrap.cxx(2788): warning C4267: 'return': conversion from 'size_t' to 'int', possible loss of data Modules\python.cxx(2227) : warning C4800: 'int' : forcing value to bool 'true' or 'false' (performance warning) --- Examples/test-suite/nested_in_template.i | 2 +- Examples/test-suite/python_pybuffer.i | 2 +- Source/Modules/python.cxx | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Examples/test-suite/nested_in_template.i b/Examples/test-suite/nested_in_template.i index 2e79fa574..81d5b6289 100644 --- a/Examples/test-suite/nested_in_template.i +++ b/Examples/test-suite/nested_in_template.i @@ -19,7 +19,7 @@ struct OuterTemplate<1> struct ConcreteDerived : AbstractBase { - ConcreteDerived() : m_value(0.) {} + ConcreteDerived() : m_value(0) {} explicit ConcreteDerived(int value) : m_value(value) {} virtual bool IsSameAs(const AbstractBase& other) const { diff --git a/Examples/test-suite/python_pybuffer.i b/Examples/test-suite/python_pybuffer.i index b46d8c36a..bff72bfa2 100644 --- a/Examples/test-suite/python_pybuffer.i +++ b/Examples/test-suite/python_pybuffer.i @@ -28,7 +28,7 @@ ++count; return count; } - int func4(const char *buf4) + size_t func4(const char *buf4) { return strlen(buf4); } diff --git a/Source/Modules/python.cxx b/Source/Modules/python.cxx index 9ffc00592..21392cc2e 100755 --- a/Source/Modules/python.cxx +++ b/Source/Modules/python.cxx @@ -2224,7 +2224,7 @@ public: n = nn; Parm *parms = Getattr(n, "parms"); - bool varargs = parms ? emit_isvarargs(parms) : 0; + int varargs = parms ? emit_isvarargs(parms) : 0; /* We prefer to explicitly list all parameters of the C function in the generated Python code as this makes the function more convenient to use, From e9b39797cc16842fff35e683623003b536cf96de Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Wed, 12 Sep 2018 17:30:04 +1000 Subject: [PATCH 033/134] Setting enum values with calls to the C code. --- Lib/r/srun.swg | 2 +- Source/Modules/r.cxx | 200 ++++++++++++++++++++++++++++++------------- 2 files changed, 142 insertions(+), 60 deletions(-) diff --git a/Lib/r/srun.swg b/Lib/r/srun.swg index d07218a77..2e8eda112 100644 --- a/Lib/r/srun.swg +++ b/Lib/r/srun.swg @@ -73,7 +73,7 @@ function(name, .values, where = topenv(parent.frame()), suffix = "Value") { # Mirror the class definitions via the E analogous to .__C__ defName = paste(".__E__", name, sep = "") - assign(defName, .values, envir = where) + delayedAssign(defName, .values, assign.env = where) if(nchar(suffix)) name = paste(name, suffix, sep = "") diff --git a/Source/Modules/r.cxx b/Source/Modules/r.cxx index 019d5dd66..099251d0d 100644 --- a/Source/Modules/r.cxx +++ b/Source/Modules/r.cxx @@ -288,7 +288,8 @@ public: int classDeclaration(Node *n); int enumDeclaration(Node *n); - + String *enumValue(Node *n); + virtual int enumvalueDeclaration(Node *n); int membervariableHandler(Node *n); int typedefHandler(Node *n); @@ -392,6 +393,8 @@ protected: // Strings into which we cumulate the generated code that is to be written //vto the files. + String *enum_values; + String *enum_def_calls; String *sfile; String *f_init; String *s_classes; @@ -456,6 +459,8 @@ R::R() : copyStruct(false), memoryProfile(false), aggressiveGc(false), + enum_values(0), + enum_def_calls(0), sfile(0), f_init(0), s_classes(0), @@ -756,6 +761,7 @@ void R::init() { s_classes = NewString(""); s_init = NewString(""); s_init_routine = NewString(""); + enum_def_calls = NewString(""); } @@ -878,6 +884,7 @@ int R::DumpCode(Node *n) { Printf(scode, "%s\n\n", s_init); Printf(scode, "%s\n\n", s_classes); Printf(scode, "%s\n", sfile); + Printf(scode, "%s\n", enum_def_calls); Delete(scode); String *outfile = Getattr(n,"outfile"); @@ -1198,75 +1205,103 @@ int R::OutputArrayMethod(String *className, List *el, File *out) { tdname is the typedef of the enumeration, i.e. giving its name. *************************************************************/ int R::enumDeclaration(Node *n) { - if (getCurrentClass() && (cplus_mode != PUBLIC)) - return SWIG_NOWRAP; + if (!ImportMode) { + if (getCurrentClass() && (cplus_mode != PUBLIC)) + return SWIG_NOWRAP; - String *name = Getattr(n, "name"); - String *tdname = Getattr(n, "tdname"); + String *symname = Getattr(n, "sym:name"); - /* Using name if tdname is empty. */ + // TODO - deal with anonymous enumerations + // Previous enum code for R didn't wrap them + if (!symname || Getattr(n, "unnamedinstance")) + return SWIG_NOWRAP; - if(Len(tdname) == 0) - tdname = name; + // create mangled name for the enum + // This will have content if the %nspace feature is set on + // the input file + String *nspace = Getattr(n, "sym:nspace"); // NSpace/getNSpace() only works during Language::enumDeclaration call + String * ename; - - if(!tdname || Strcmp(tdname, "") == 0) { + String *name = Getattr(n, "name"); + ename = getRClassName(name); + if (debugMode) { + Printf(stdout, "enumDeclaration: %s, %s, %s, %s\n", name, symname, nspace, ename); + } + Delete(name); + // set up a call to create the R enum structure. The list of + // individual elements will be built in enum_code + enum_values=0; + // Emit each enum item Language::enumDeclaration(n); - return SWIG_OK; + + Printf(enum_def_calls, "defineEnumeration(\"%s\",\n .values=c(%s))\n\n", + ename, enum_values); + Delete(enum_values); + Delete(ename); + //Delete(symname); + } + return SWIG_OK; +} +/************************************************************* +**************************************************************/ +int R::enumvalueDeclaration(Node *n) { + if (getCurrentClass() && (cplus_mode != PUBLIC)) { + Printf(stdout , "evd: Not public\n"); + return SWIG_NOWRAP; } - String *mangled_tdname = SwigType_manglestr(tdname); - String *scode = NewString(""); + Swig_require("enumvalueDeclaration", n, "*name", "?value", NIL); + String *symname = Getattr(n, "sym:name"); + String *value = Getattr(n, "value"); + String *name = Getattr(n, "name"); + Node *parent = parentNode(n); + String *parent_name = Getattr(parent, "name"); + String *newsymname = 0; + String *tmpValue; - Printv(scode, "defineEnumeration('", mangled_tdname, "'", - ",\n", tab8, tab8, tab4, ".values = c(\n", NIL); - - Node *c; - int value = -1; // First number is zero - for (c = firstChild(n); c; c = nextSibling(c)) { - // const char *tag = Char(nodeType(c)); - // if (Strcmp(tag,"cdecl") == 0) { - name = Getattr(c, "name"); - String *val = Getattr(c, "enumvalue"); - if(val && Char(val)) { - int inval; - if (!getNumber(val, &inval)) { - // Conversion failed - use the string value in val. - } else { - val = NULL; - value = inval; - } - } else { - val = NULL; - value++; - } - - if (val != NULL) { - // This won't work in general, but will at least handle cases like (3) - // and 3+7, and when it doesn't work, it'll fail noisly rather than - // quietly using the wrong enum value like we used to. - if (!Strcmp(val, "true")) { - Printf(scode, "%s%s%s'%s' = %s%s\n", tab8, tab8, tab8, name, "TRUE", - nextSibling(c) ? ", " : ""); - } else if (!Strcmp(val, "false")) { - Printf(scode, "%s%s%s'%s' = %s%s\n", tab8, tab8, tab8, name, "FALSE", - nextSibling(c) ? ", " : ""); - } else { - Printf(scode, "%s%s%s'%s' = %s%s\n", tab8, tab8, tab8, name, val, - nextSibling(c) ? ", " : ""); - } - } else { - Printf(scode, "%s%s%s'%s' = %d%s\n", tab8, tab8, tab8, name, value, - nextSibling(c) ? ", " : ""); - } - // } + // Strange hack from parent method + if (value) + tmpValue = NewString(value); + else + tmpValue = NewString(name); + // Note that this is used in enumValue() amongst other places + Setattr(n, "value", tmpValue); + + // Deal with enum values that are not int + int swigtype = SwigType_type(Getattr(n, "type")); + if (swigtype == T_BOOL) { + const char *val = Equal(Getattr(n, "enumvalue"), "true") ? "1" : "0"; + Setattr(n, "enumvalue", val); + } else if (swigtype == T_CHAR) { + String *val = NewStringf("'%s'", Getattr(n, "enumvalue")); + Setattr(n, "enumvalue", val); + Delete(val); } - Printv(scode, "))", NIL); - Printf(sfile, "%s\n", scode); + if (GetFlag(parent, "scopedenum")) { + newsymname = Swig_name_member(0, Getattr(parent, "sym:name"), symname); + symname = newsymname; + } - Delete(scode); - Delete(mangled_tdname); + { + // Wrap C/C++ enums with constant integers or use the typesafe enum pattern + SwigType *typemap_lookup_type = parent_name ? parent_name : NewString("enum "); + Setattr(n, "type", typemap_lookup_type); + + // Simple integer constants + // Note these are always generated for anonymous enums, no matter what enum_feature is specified + // Code generated is the same for SimpleEnum and TypeunsafeEnum -> the class it is generated into is determined later + + String *value = enumValue(n); + if (enum_values) { + Printf(enum_values, ",\n\"%s\" = %s", name, value); + } else { + enum_values=NewString(""); + Printf(enum_values, "\"%s\" = %s", name, value); + } + + Delete(value); + } return SWIG_OK; } @@ -2853,3 +2888,50 @@ String * R::processType(SwigType *t, Node *n, int *nargs) { } /*************************************************************************************/ + /* ----------------------------------------------------------------------- + * enumValue() + * This method will return a string with an enum value to use in from R when + * setting up an enum variable + * ------------------------------------------------------------------------ */ + +String *R::enumValue(Node *n) { + String *symname = Getattr(n, "sym:name"); + String *value = Getattr(n, "value"); + String *newsymname = 0; + + Node *parent = parentNode(n); + symname = Getattr(n, "sym:name"); + + String *etype = Getattr(parent, "enumtype"); + // we have to directly call the c wrapper function, as the + // R wrapper to the enum is designed to be used after the enum + // structures have been created on the R side. This means + // that we'll need to construct a .Call expression + + // change the type for variableWrapper + Setattr(n, "type", etype); + + if (!getCurrentClass()) { + newsymname = Swig_name_member(0, Getattr(parent, "sym:name"), symname); + + // Strange hack to change the name + Setattr(n, "name", Getattr(n, "value")); + Setattr(n, "sym:name", newsymname); + variableWrapper(n); + value = Swig_name_get(NSPACE_TODO, newsymname); + } else { + String *enumClassPrefix = getEnumClassPrefix(); + newsymname = Swig_name_member(0, enumClassPrefix, symname); + Setattr(n, "name", Getattr(n, "value")); + Setattr(n, "sym:name", newsymname); + variableWrapper(n); + value = Swig_name_get(NSPACE_TODO, newsymname); + } + value = Swig_name_wrapper(value); + Replace(value, "_wrap", "R_swig", DOH_REPLACE_FIRST); + + String *valuecall=NewString(""); + Printv(valuecall, ".Call('", value, "',FALSE, PACKAGE='", Rpackage, "')", NIL); + Delete(value); + return valuecall; +} From 06de7049382834f663ad963bbcd5bbdb2cc34695 Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Wed, 19 Sep 2018 07:46:07 +1000 Subject: [PATCH 034/134] ENH: R Module: Enumerations with values set by calls to C code, allowing arbitarily complex value expressions. R-side initialization of the enumeration structure employs delayedAssign, which allows the initialization code to be sourced before loading the shared library, which is the usual behaviour for code in an R package. --- Source/Modules/r.cxx | 68 +++++++++++++++++++++++++++++++++++--------- 1 file changed, 54 insertions(+), 14 deletions(-) diff --git a/Source/Modules/r.cxx b/Source/Modules/r.cxx index 099251d0d..da87cbcca 100644 --- a/Source/Modules/r.cxx +++ b/Source/Modules/r.cxx @@ -256,6 +256,7 @@ static void replaceRClass(String *tm, SwigType *type) { String *tmp = getRClassName(type); String *tmp_base = getRClassName(type, 0); String *tmp_ref = getRClassName(type, 1, 1); + Replaceall(tm, "$R_class", tmp); Replaceall(tm, "$*R_class", tmp_base); Replaceall(tm, "$&R_class", tmp_ref); @@ -579,7 +580,6 @@ String * R::createFunctionPointerHandler(SwigType *t, Node *n, int *numArgs) { for (i = 0; p; p = nextSibling(p), ++i) { String *arg = Getattr(p, "name"); String *lname; - if (!arg && Cmp(Getattr(p, "type"), "void")) { lname = NewStringf("arg%d", i+1); Setattr(p, "name", lname); @@ -640,6 +640,9 @@ String * R::createFunctionPointerHandler(SwigType *t, Node *n, int *numArgs) { } Replaceall(tm, "$1", name); Replaceall(tm, "$result", "r_tmp"); + if (debugMode) { + Printf(stdout, "Calling Replace A: %s\n", Getattr(p,"type")); + } replaceRClass(tm, Getattr(p,"type")); Replaceall(tm,"$owner", "0"); Delete(lstr); @@ -785,6 +788,11 @@ int R::cDeclaration(Node *n) { ***/ int R::top(Node *n) { String *module = Getattr(n, "name"); + + if (debugMode) { + Printf(stdout, " %s\n", module); + } + if(!Rpackage) Rpackage = Copy(module); if(!DllName) @@ -1225,7 +1233,12 @@ int R::enumDeclaration(Node *n) { String *name = Getattr(n, "name"); ename = getRClassName(name); if (debugMode) { - Printf(stdout, "enumDeclaration: %s, %s, %s, %s\n", name, symname, nspace, ename); + Node *N = getCurrentClass(); + String *cl = NewString(""); + if (N) { + cl=getEnumClassPrefix(); + } + Printf(stdout, "enumDeclaration: %s, %s, %s, %s, %s\n", name, symname, nspace, ename, cl); } Delete(name); // set up a call to create the R enum structure. The list of @@ -1286,6 +1299,9 @@ int R::enumvalueDeclaration(Node *n) { { // Wrap C/C++ enums with constant integers or use the typesafe enum pattern SwigType *typemap_lookup_type = parent_name ? parent_name : NewString("enum "); + if (debugMode) { + Printf(stdout, "Setting type: %s\n", Copy(typemap_lookup_type)); + } Setattr(n, "type", typemap_lookup_type); // Simple integer constants @@ -1311,19 +1327,27 @@ int R::enumvalueDeclaration(Node *n) { **************************************************************/ int R::variableWrapper(Node *n) { String *name = Getattr(n, "sym:name"); - + if (debugMode) { + Printf(stdout, "variableWrapper %s\n", n); + } processing_variable = 1; Language::variableWrapper(n); // Force the emission of the _set and _get function wrappers. processing_variable = 0; SwigType *ty = Getattr(n, "type"); + String *nodeType = nodeType(n); int addCopyParam = addCopyParameter(ty); //XXX processType(ty, n); - if(!SwigType_isconst(ty)) { + if (nodeType && !Strcmp(nodeType, "enumitem")) { + /* special wrapper for enums - don't want the R _set, _get functions*/ + if (debugMode) { + Printf(stdout, "variableWrapper enum branch\n"); + } + } else if(!SwigType_isconst(ty)) { Wrapper *f = NewWrapper(); Printf(f->def, "%s = \nfunction(value%s)\n{\n", name, addCopyParam ? ", .copy = FALSE" : ""); @@ -1341,6 +1365,8 @@ int R::variableWrapper(Node *n) { return SWIG_OK; } +/************************************************************* +**************************************************************/ void R::addAccessor(String *memberName, Wrapper *wrapper, String *name, int isSet) { @@ -1787,6 +1813,9 @@ int R::functionWrapper(Node *n) { SwigType *resolved = SwigType_typedef_resolve_all(resultType); if (expandTypedef(resolved)) { + if (debugMode) { + Printf(stdout, "Setting type: %s\n", resolved); + } Setattr(p, "type", Copy(resolved)); } } @@ -1799,6 +1828,9 @@ int R::functionWrapper(Node *n) { SwigType_istypedef(type)) { SwigType *resolved = SwigType_typedef_resolve_all(type); + if (debugMode) + Printf(stdout, " resolved %s\n", + Copy(unresolved_return_type)); if (expandTypedef(resolved)) { type = Copy(resolved); Setattr(n, "type", type); @@ -2102,14 +2134,12 @@ int R::functionWrapper(Node *n) { /* Deal with the explicit return value. */ if ((tm = Swig_typemap_lookup_out("out", n, Swig_cresult_name(), f, actioncode))) { SwigType *retType = Getattr(n, "type"); - //Printf(stdout, "Return Value for %s, array? %s\n", retType, SwigType_isarray(retType) ? "yes" : "no"); - /* if(SwigType_isarray(retType)) { - defineArrayAccessors(retType); - } */ - - + Replaceall(tm,"$1", Swig_cresult_name()); Replaceall(tm,"$result", "r_ans"); + if (debugMode){ + Printf(stdout, "Calling replace D: %s, %s, %s\n", retType, n, tm); + } replaceRClass(tm, retType); if (GetFlag(n,"feature:new")) { @@ -2196,6 +2226,9 @@ int R::functionWrapper(Node *n) { Delete(smartname); } } + if (debugMode) { + Printf(stdout, "Calling replace B: %s, %s, %s\n", Getattr(n, "type"), Getattr(n, "sym:name"), getNSpace()); + } replaceRClass(tm, Getattr(n, "type")); Chop(tm); } @@ -2231,6 +2264,9 @@ int R::functionWrapper(Node *n) { tm = Swig_typemap_lookup("rtype", n, "", 0); if(tm) { SwigType *retType = Getattr(n, "type"); + if (debugMode) { + Printf(stdout, "Calling replace C: %s\n", Copy(retType)); + } replaceRClass(tm, retType); } @@ -2469,8 +2505,8 @@ int R::classDeclaration(Node *n) { } if (Getattr(n, "has_destructor")) { Printf(sfile, "setMethod('delete', '_p%s', function(obj) {delete%s(obj)})\n", - getRClassName(Getattr(n, "name")), - getRClassName(Getattr(n, "name"))); + getRClassName(name), + getRClassName(name)); } if(!opaque && !Strcmp(kind, "struct") && copyStruct) { @@ -2842,7 +2878,7 @@ String * R::processType(SwigType *t, Node *n, int *nargs) { SwigType *tmp = Getattr(n, "tdname"); if (debugMode) - Printf(stdout, "processType %s (tdname = %s)\n", Getattr(n, "name"), tmp); + Printf(stdout, "processType %s (tdname = %s)(SwigType = %s)\n", Getattr(n, "name"), tmp, Copy(t)); SwigType *td = t; if (expandTypedef(t) && @@ -2902,6 +2938,7 @@ String *R::enumValue(Node *n) { Node *parent = parentNode(n); symname = Getattr(n, "sym:name"); + // parent enumtype has namespace mangled in String *etype = Getattr(parent, "enumtype"); // we have to directly call the c wrapper function, as the // R wrapper to the enum is designed to be used after the enum @@ -2909,11 +2946,14 @@ String *R::enumValue(Node *n) { // that we'll need to construct a .Call expression // change the type for variableWrapper + if (debugMode) { + Printf(stdout, " type set: %s\n", etype); + } + Setattr(n, "type", etype); if (!getCurrentClass()) { newsymname = Swig_name_member(0, Getattr(parent, "sym:name"), symname); - // Strange hack to change the name Setattr(n, "name", Getattr(n, "value")); Setattr(n, "sym:name", newsymname); From b5af07fd95f35f411c3f57b54ce001657cda83a8 Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Mon, 4 Feb 2019 15:58:03 +1100 Subject: [PATCH 035/134] Code style changes post review --- Source/Modules/r.cxx | 40 +++++++++++++++++++++------------------- 1 file changed, 21 insertions(+), 19 deletions(-) diff --git a/Source/Modules/r.cxx b/Source/Modules/r.cxx index da87cbcca..3260dfaf8 100644 --- a/Source/Modules/r.cxx +++ b/Source/Modules/r.cxx @@ -1228,38 +1228,38 @@ int R::enumDeclaration(Node *n) { // This will have content if the %nspace feature is set on // the input file String *nspace = Getattr(n, "sym:nspace"); // NSpace/getNSpace() only works during Language::enumDeclaration call - String * ename; + String *ename; String *name = Getattr(n, "name"); ename = getRClassName(name); if (debugMode) { - Node *N = getCurrentClass(); + Node *current_class = getCurrentClass(); String *cl = NewString(""); - if (N) { - cl=getEnumClassPrefix(); + if (current_class) { + cl = getEnumClassPrefix(); } Printf(stdout, "enumDeclaration: %s, %s, %s, %s, %s\n", name, symname, nspace, ename, cl); } Delete(name); // set up a call to create the R enum structure. The list of // individual elements will be built in enum_code - enum_values=0; + enum_values = 0; // Emit each enum item Language::enumDeclaration(n); - Printf(enum_def_calls, "defineEnumeration(\"%s\",\n .values=c(%s))\n\n", - ename, enum_values); + Printf(enum_def_calls, "defineEnumeration(\"%s\",\n .values=c(%s))\n\n", ename, enum_values); Delete(enum_values); Delete(ename); //Delete(symname); } return SWIG_OK; } + /************************************************************* **************************************************************/ int R::enumvalueDeclaration(Node *n) { if (getCurrentClass() && (cplus_mode != PUBLIC)) { - Printf(stdout , "evd: Not public\n"); + Printf(stdout, "evd: Not public\n"); return SWIG_NOWRAP; } @@ -1267,7 +1267,7 @@ int R::enumvalueDeclaration(Node *n) { String *symname = Getattr(n, "sym:name"); String *value = Getattr(n, "value"); String *name = Getattr(n, "name"); - Node *parent = parentNode(n); + Node *parent = parentNode(n); String *parent_name = Getattr(parent, "name"); String *newsymname = 0; String *tmpValue; @@ -1312,7 +1312,7 @@ int R::enumvalueDeclaration(Node *n) { if (enum_values) { Printf(enum_values, ",\n\"%s\" = %s", name, value); } else { - enum_values=NewString(""); + enum_values = NewString(""); Printf(enum_values, "\"%s\" = %s", name, value); } @@ -1324,6 +1324,9 @@ int R::enumvalueDeclaration(Node *n) { /************************************************************* +Create accessor functions for variables. +Does not create equivalent wrappers for enumerations, +which are handled differently **************************************************************/ int R::variableWrapper(Node *n) { String *name = Getattr(n, "sym:name"); @@ -1366,6 +1369,10 @@ int R::variableWrapper(Node *n) { } /************************************************************* +Creates accessor functions for class members. + +ToDo - this version depends on naming conventions and needs +to be replaced. **************************************************************/ void R::addAccessor(String *memberName, Wrapper *wrapper, String *name, @@ -1829,20 +1836,17 @@ int R::functionWrapper(Node *n) { SwigType *resolved = SwigType_typedef_resolve_all(type); if (debugMode) - Printf(stdout, " resolved %s\n", - Copy(unresolved_return_type)); + Printf(stdout, " resolved %s\n", Copy(unresolved_return_type)); if (expandTypedef(resolved)) { type = Copy(resolved); Setattr(n, "type", type); } } if (debugMode) - Printf(stdout, " unresolved_return_type %s\n", - unresolved_return_type); + Printf(stdout, " unresolved_return_type %s\n", unresolved_return_type); if(processing_member_access_function) { if (debugMode) - Printf(stdout, " '%s' '%s' '%s' '%s'\n", - fname, iname, member_name, class_name); + Printf(stdout, " '%s' '%s' '%s' '%s'\n", fname, iname, member_name, class_name); if(opaqueClassDeclaration) return SWIG_OK; @@ -2504,9 +2508,7 @@ int R::classDeclaration(Node *n) { class_member_set_functions = NULL; } if (Getattr(n, "has_destructor")) { - Printf(sfile, "setMethod('delete', '_p%s', function(obj) {delete%s(obj)})\n", - getRClassName(name), - getRClassName(name)); + Printf(sfile, "setMethod('delete', '_p%s', function(obj) {delete%s(obj)})\n", getRClassName(name), getRClassName(name)); } if(!opaque && !Strcmp(kind, "struct") && copyStruct) { From 62594c611aa0b5ebddc7224ded61e4cb1294647f Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Wed, 6 Feb 2019 15:26:08 +1100 Subject: [PATCH 036/134] ENH: Run test for enum_thorough in R This test exercises many complex cases for enumerations in R. References to enums currently fail and will be addressed in the next patch. Anonymous enums are not supported. There are some strange corner cases that could be seen as doing strange things in R. enums are allowed to have the same underlying integer representation on the C side. This means that the R structure ends up with two names for the same integer, which in turn means that the reverse lookup isn't unique. I don't think this matters. I'll add some of these cases to the documentation. --- Examples/test-suite/r/Makefile.in | 1 - Examples/test-suite/r/enum_thorough_runme.R | 453 ++++++++++++++++++++ 2 files changed, 453 insertions(+), 1 deletion(-) create mode 100644 Examples/test-suite/r/enum_thorough_runme.R diff --git a/Examples/test-suite/r/Makefile.in b/Examples/test-suite/r/Makefile.in index 13fd3654b..1616ffd3d 100644 --- a/Examples/test-suite/r/Makefile.in +++ b/Examples/test-suite/r/Makefile.in @@ -27,7 +27,6 @@ CPP_TEST_CASES += \ # arithmetic expressions FAILING_CPP_TESTS = \ - enum_thorough \ preproc_constants FAILING_C_TESTS = \ diff --git a/Examples/test-suite/r/enum_thorough_runme.R b/Examples/test-suite/r/enum_thorough_runme.R new file mode 100644 index 000000000..608abc71a --- /dev/null +++ b/Examples/test-suite/r/enum_thorough_runme.R @@ -0,0 +1,453 @@ +clargs <- commandArgs(trailing=TRUE) +source(file.path(clargs[1], "unittest.R")) + +dyn.load(paste("enum_thorough", .Platform$dynlib.ext, sep="")) +source("enum_thorough.R") +cacheMetaData(1) + +## Anonymous enums are not wrapped by the R module +## + +# Colours - string interface, various function signatures +unittest('red', colourTest1('red')) +unittest('blue', colourTest1('blue')) +unittest('green', colourTest1('green')) + + +unittest('red', colourTest2('red')) +unittest('blue', colourTest2('blue')) +unittest('green', colourTest2('green')) + +unittest('red', colourTest3('red')) +unittest('blue', colourTest3('blue')) +unittest('green', colourTest3('green')) + +unittest('red', colourTest4('red')) +unittest('blue', colourTest4('blue')) +unittest('green', colourTest4('green')) + +## Colours - underlying integers +unittest(-1, enumToInteger('red', '_colour')) +unittest(0, enumToInteger('blue', '_colour')) +unittest(10, enumToInteger('green', '_colour')) + +######## +## enum variable, wrapped as a function +## Is initialization to 0 a "standard" +myColour() + +## Test setting and retrieving +myColour('green') +unittest('green', myColour()) + +######## +## SpeedClass + +s <- SpeedClass() +v <- "medium" +unittest(v, s$speedTest1(v)) +unittest(v, s$speedTest2(v)) +unittest(v, s$speedTest3(v)) +unittest(v, s$speedTest4(v)) +unittest(v, s$speedTest5(v)) +unittest(v, s$speedTest6(v)) +# Not handling enum references - probably needs a typemap +# unittest(v, s$speedTest7(v)) +# unittest(v, s$speedTest8(v)) + +## speedTest methods not in the class + +unittest(v, speedTest1(v)) +unittest(v, speedTest2(v)) +unittest(v, speedTest3(v)) +unittest(v, speedTest4(v)) +# enum reference +# unittest(v, speedTest5(v)) + +## member access +s <- SpeedClass() +unittest("slow", s$mySpeedtd1) +# check integer value +unittest(10, enumToInteger(s$mySpeedtd1, "_SpeedClass__speed")) +# set and check +s$mySpeedtd1 <- "lightning" +unittest("lightning", s$mySpeedtd1) +unittest(31, enumToInteger(s$mySpeedtd1, "_SpeedClass__speed")) + +## Named anon - not wrapped nicely, but can be retrieved: + + +unittest("NamedAnon2", namedanon_NamedAnon2_get()) +unittest(0, enumToInteger(namedanon_NamedAnon1_get(), "_namedanon")) +unittest(1, enumToInteger(namedanon_NamedAnon2_get(), "_namedanon")) + +## Twonames +v <- "TwoNames1" +unittest(v, twonamesTest1(v)) +unittest(v, twonamesTest2(v)) +unittest(v, twonamesTest3(v)) +unittest(33, enumToInteger("TwoNames3", "_twonamestag")) + +tt <- TwoNamesStruct() +v <- "TwoNamesStruct1" +unittest(v, tt$twonamesTest1(v)) +unittest(v, tt$twonamesTest2(v)) +unittest(v, tt$twonamesTest3(v)) +## Try the wrong name +unittest(TRUE, is.na(tt$twonamesTest3("TwoNames1"))) + +## Namedanonspace +## can get the values + +v <- namedanonspace_NamedAnonSpace2_get() +unittest(v, namedanonspaceTest1(v)) +unittest(v, namedanonspaceTest2(v)) +unittest(v, namedanonspaceTest3(v)) +unittest(v, namedanonspaceTest4(v)) + +## scientists + +tt <- TemplateClassInt() + +g <- "galileo" +unittest(g, tt$scientistsTest1(g)) +unittest(g, tt$scientistsTest2(g)) +unittest(g, tt$scientistsTest3(g)) +unittest(g, tt$scientistsTest4(g)) +unittest(g, tt$scientistsTest5(g)) +unittest(g, tt$scientistsTest6(g)) +unittest(g, tt$scientistsTest7(g)) +unittest(g, tt$scientistsTest8(g)) +unittest(g, tt$scientistsTest9(g)) + +## This one is commented out in csharp too +## unittest(g, tt$scientistsTestA(g)) +unittest(g, tt$scientistsTestB(g)) +## This one is commented out in csharp too +## unittest(g, tt$scientistsTestC(g)) +unittest(g, tt$scientistsTestD(g)) +unittest(g, tt$scientistsTestE(g)) +unittest(g, tt$scientistsTestF(g)) +unittest(g, tt$scientistsTestG(g)) +unittest(g, tt$scientistsTestH(g)) +unittest(g, tt$scientistsTestI(g)) +# enum reference +#unittest(g, tt$scientistsTestJ(g)) + + +unittest(g, scientistsTest1(g)) +unittest(g, scientistsTest2(g)) +unittest(g, scientistsTest3(g)) +unittest(g, scientistsTest4(g)) +unittest(g, scientistsTest5(g)) +unittest(g, scientistsTest6(g)) +unittest(g, scientistsTest7(g)) +## enum reference +## unittest(g, scientistsTest8(g)) + +tt <- TClassInt() +b <- "bell" +unittest(b, tt$scientistsNameTest1(b)) +unittest(b, tt$scientistsNameTest2(b)) +unittest(b, tt$scientistsNameTest3(b)) +unittest(b, tt$scientistsNameTest4(b)) +unittest(b, tt$scientistsNameTest5(b)) +unittest(b, tt$scientistsNameTest6(b)) +unittest(b, tt$scientistsNameTest7(b)) +unittest(b, tt$scientistsNameTest8(b)) +unittest(b, tt$scientistsNameTest9(b)) + +## This one is commented out in csharp too +## unittest(b, tt$scientistsNameTestA(b)) +unittest(b, tt$scientistsNameTestB(b)) +## This one is commented out in csharp too +## unittest(b, tt$scientistsNameTestC(b)) +unittest(b, tt$scientistsNameTestD(b)) +unittest(b, tt$scientistsNameTestE(b)) +unittest(b, tt$scientistsNameTestF(b)) +unittest(b, tt$scientistsNameTestG(b)) +unittest(b, tt$scientistsNameTestH(b)) +unittest(b, tt$scientistsNameTestI(b)) + + +unittest(b, tt$scientistsNameSpaceTest1(b)) +unittest(b, tt$scientistsNameSpaceTest2(b)) +unittest(b, tt$scientistsNameSpaceTest3(b)) +unittest(b, tt$scientistsNameSpaceTest4(b)) +unittest(b, tt$scientistsNameSpaceTest5(b)) +unittest(b, tt$scientistsNameSpaceTest6(b)) +unittest(b, tt$scientistsNameSpaceTest7(b)) + +unittest(g, tt$scientistsOtherTest1(g)) +unittest(g, tt$scientistsOtherTest2(g)) +unittest(g, tt$scientistsOtherTest3(g)) +unittest(g, tt$scientistsOtherTest4(g)) +unittest(g, tt$scientistsOtherTest5(g)) +unittest(g, tt$scientistsOtherTest6(g)) +unittest(g, tt$scientistsOtherTest7(g)) + +## Global +unittest(b, scientistsNameTest1(b)) +unittest(b, scientistsNameTest2(b)) +unittest(b, scientistsNameTest3(b)) +unittest(b, scientistsNameTest4(b)) +unittest(b, scientistsNameTest5(b)) +unittest(b, scientistsNameTest6(b)) +unittest(b, scientistsNameTest7(b)) + +unittest(b, scientistsNameSpaceTest1(b)) +unittest(b, scientistsNameSpaceTest2(b)) +unittest(b, scientistsNameSpaceTest3(b)) +unittest(b, scientistsNameSpaceTest4(b)) +unittest(b, scientistsNameSpaceTest5(b)) +unittest(b, scientistsNameSpaceTest6(b)) +unittest(b, scientistsNameSpaceTest7(b)) + +unittest(b, scientistsNameSpaceTest8(b)) +unittest(b, scientistsNameSpaceTest9(b)) +unittest(b, scientistsNameSpaceTestA(b)) +unittest(b, scientistsNameSpaceTestB(b)) +unittest(b, scientistsNameSpaceTestC(b)) +unittest(b, scientistsNameSpaceTestD(b)) +unittest(b, scientistsNameSpaceTestE(b)) +unittest(b, scientistsNameSpaceTestF(b)) +unittest(b, scientistsNameSpaceTestG(b)) +unittest(b, scientistsNameSpaceTestH(b)) +unittest(b, scientistsNameSpaceTestI(b)) +unittest(b, scientistsNameSpaceTestJ(b)) +unittest(b, scientistsNameSpaceTestK(b)) +unittest(b, scientistsNameSpaceTestL(b)) + +## rename test +v <- "eek" +unittest(v, renameTest1(v)) +unittest(v, renameTest2(v)) + +## NewName +N <- NewNameStruct() +## Only half works: +unittest("kerboom", NewNameStruct_bang_get()) +## Can't put in "bang" in the call +## confirm with: +## get(".__E___OldNameStruct__enumeration") + +## TreeClass + +T <- TreesClass() +p <- "pine" + +unittest(p, T$treesTest1(p)) +unittest(p, T$treesTest2(p)) +unittest(p, T$treesTest3(p)) +unittest(p, T$treesTest4(p)) +unittest(p, T$treesTest5(p)) +unittest(p, T$treesTest6(p)) +unittest(p, T$treesTest7(p)) +unittest(p, T$treesTest8(p)) +unittest(p, T$treesTest9(p)) +unittest(p, T$treesTestA(p)) +unittest(p, T$treesTestB(p)) +unittest(p, T$treesTestC(p)) +unittest(p, T$treesTestD(p)) +unittest(p, T$treesTestE(p)) +unittest(p, T$treesTestF(p)) +unittest(p, T$treesTestG(p)) +unittest(p, T$treesTestH(p)) +unittest(p, T$treesTestI(p)) +unittest(p, T$treesTestJ(p)) +unittest(p, T$treesTestK(p)) +unittest(p, T$treesTestL(p)) +unittest(p, T$treesTestM(p)) +unittest(p, T$treesTestN(p)) +unittest(p, T$treesTestO(p)) + +unittest(p, treesTest1(p)) +unittest(p, treesTest2(p)) +unittest(p, treesTest3(p)) +unittest(p, treesTest4(p)) +unittest(p, treesTest5(p)) +unittest(p, treesTest6(p)) +unittest(p, treesTest7(p)) +unittest(p, treesTest8(p)) +unittest(p, treesTest9(p)) +unittest(p, treesTestA(p)) +unittest(p, treesTestB(p)) +unittest(p, treesTestC(p)) +unittest(p, treesTestD(p)) +unittest(p, treesTestE(p)) +unittest(p, treesTestF(p)) +unittest(p, treesTestG(p)) +unittest(p, treesTestH(p)) +unittest(p, treesTestI(p)) +unittest(p, treesTestJ(p)) +unittest(p, treesTestK(p)) +unittest(p, treesTestL(p)) +unittest(p, treesTestM(p)) +unittest(p, treesTestO(p)) +unittest(p, treesTestP(p)) +unittest(p, treesTestQ(p)) +unittest(p, treesTestR(p)) + +## Hair +h <- HairStruct() +g <- "ginger" +unittest(g, h$hairTest1(g)) +unittest(g, h$hairTest2(g)) +unittest(g, h$hairTest3(g)) +unittest(g, h$hairTest4(g)) +unittest(g, h$hairTest5(g)) +unittest(g, h$hairTest6(g)) +unittest(g, h$hairTest7(g)) +unittest(g, h$hairTest8(g)) +unittest(g, h$hairTest9(g)) +unittest(g, h$hairTestA(g)) +unittest(g, h$hairTestB(g)) + +r <- "red" +unittest(r, h$colourTest1(r)) +unittest(r, h$colourTest2(r)) + +nmA <- "NamedAnon1" +unittest(nmA, h$namedanonTest1(nmA)) +unittest("NamedAnonSpace2", h$namedanonspaceTest1("NamedAnonSpace2")) + +f <- "fir" + +unittest(f, h$treesGlobalTest1(f)) +unittest(f, h$treesGlobalTest2(f)) +unittest(f, h$treesGlobalTest3(f)) +unittest(f, h$treesGlobalTest4(f)) + +b <- "blonde" +unittest(b, hairTest1(b)) +unittest(b, hairTest2(b)) +unittest(b, hairTest3(b)) +unittest(b, hairTest4(b)) +unittest(b, hairTest5(b)) +unittest(b, hairTest6(b)) +unittest(b, hairTest7(b)) +unittest(b, hairTest8(b)) +unittest(b, hairTest9(b)) +unittest(b, hairTestA(b)) +unittest(b, hairTestB(b)) +## enum reference +##unittest(b, hairTestC(b)) +unittest(b, hairTestA1(b)) +unittest(b, hairTestA2(b)) +unittest(b, hairTestA3(b)) +unittest(b, hairTestA4(b)) +unittest(b, hairTestA5(b)) +unittest(b, hairTestA6(b)) +unittest(b, hairTestA7(b)) +unittest(b, hairTestA8(b)) +unittest(b, hairTestA9(b)) +unittest(b, hairTestAA(b)) +unittest(b, hairTestAB(b)) +## enum reference +## unittest(b, hairTestAC(b)) + +unittest(b, hairTestB1(b)) +unittest(b, hairTestB2(b)) +unittest(b, hairTestB3(b)) +unittest(b, hairTestB4(b)) +unittest(b, hairTestB5(b)) +unittest(b, hairTestB6(b)) +unittest(b, hairTestB7(b)) +unittest(b, hairTestB8(b)) +unittest(b, hairTestB9(b)) +unittest(b, hairTestBA(b)) +unittest(b, hairTestBB(b)) +## enum reference +## unittest(b, hairTestBC(b)) + +f <- FirStruct() +b <- "blonde" + +unittest(b, f$hairTestFir1(b)) +unittest(b, f$hairTestFir2(b)) +unittest(b, f$hairTestFir3(b)) +unittest(b, f$hairTestFir4(b)) +unittest(b, f$hairTestFir5(b)) +unittest(b, f$hairTestFir6(b)) +unittest(b, f$hairTestFir7(b)) +unittest(b, f$hairTestFir8(b)) +unittest(b, f$hairTestFir9(b)) +unittest(b, f$hairTestFirA(b)) + +## Unnamed enum instance doesn't work +## Wrapper set/get exists, but there's +## no mapping between strings and integers +GlobalInstance(1) +unittest(1, GlobalInstance()) + +ii <- Instances() +ii$MemberInstance <- 1 +unittest(1, ii$MemberInstance) + +ii <- IgnoreTest() + +## Testing integer values +unittest(0, enumToInteger(IgnoreTest_ignoreA_zero_get(), "_IgnoreTest__IgnoreA")) +unittest(3, enumToInteger(IgnoreTest_ignoreA_three_get(), "_IgnoreTest__IgnoreA")) +unittest(10, enumToInteger(IgnoreTest_ignoreA_ten_get(), "_IgnoreTest__IgnoreA")) + +unittest(11, enumToInteger(IgnoreTest_ignoreA_eleven_get(), "_IgnoreTest__IgnoreA")) +unittest(14, enumToInteger(IgnoreTest_ignoreA_fourteen_get(), "_IgnoreTest__IgnoreA")) +unittest(20, enumToInteger(IgnoreTest_ignoreA_twenty_get(), "_IgnoreTest__IgnoreA")) +unittest(30, enumToInteger(IgnoreTest_ignoreA_thirty_get(), "_IgnoreTest__IgnoreA")) +unittest(32, enumToInteger(IgnoreTest_ignoreA_thirty_two_get(), "_IgnoreTest__IgnoreA")) +unittest(33, enumToInteger(IgnoreTest_ignoreA_thirty_three_get(), "_IgnoreTest__IgnoreA")) + +unittest(11, enumToInteger(IgnoreTest_ignoreB_eleven_get(), "_IgnoreTest__IgnoreB")) +unittest(12, enumToInteger(IgnoreTest_ignoreB_twelve_get(), "_IgnoreTest__IgnoreB")) +unittest(31, enumToInteger(IgnoreTest_ignoreB_thirty_one_get(), "_IgnoreTest__IgnoreB")) +unittest(32, enumToInteger(IgnoreTest_ignoreB_thirty_two_get(), "_IgnoreTest__IgnoreB")) +unittest(41, enumToInteger(IgnoreTest_ignoreB_forty_one_get(), "_IgnoreTest__IgnoreB")) +unittest(42, enumToInteger(IgnoreTest_ignoreB_forty_two_get(), "_IgnoreTest__IgnoreB")) + +unittest(10, enumToInteger(IgnoreTest_ignoreC_ten_get(), "_IgnoreTest__IgnoreC")) +unittest(12, enumToInteger(IgnoreTest_ignoreC_twelve_get(), "_IgnoreTest__IgnoreC")) +unittest(30, enumToInteger(IgnoreTest_ignoreC_thirty_get(), "_IgnoreTest__IgnoreC")) +unittest(32, enumToInteger(IgnoreTest_ignoreC_thirty_two_get(), "_IgnoreTest__IgnoreC")) +unittest(40, enumToInteger(IgnoreTest_ignoreC_forty_get(), "_IgnoreTest__IgnoreC")) +unittest(42, enumToInteger(IgnoreTest_ignoreC_forty_two_get(), "_IgnoreTest__IgnoreC")) + +unittest(21, enumToInteger(IgnoreTest_ignoreD_twenty_one_get(), "_IgnoreTest__IgnoreD")) +unittest(22, enumToInteger(IgnoreTest_ignoreD_twenty_two_get(), "_IgnoreTest__IgnoreD")) + +unittest(0, enumToInteger(IgnoreTest_ignoreE_zero_get(), "_IgnoreTest__IgnoreE")) +unittest(21, enumToInteger(IgnoreTest_ignoreE_twenty_one_get(), "_IgnoreTest__IgnoreE")) +unittest(22, enumToInteger(IgnoreTest_ignoreE_twenty_two_get(), "_IgnoreTest__IgnoreE")) + +## confirm that an ignore directive is followed: +unittest(TRUE, is.na(ignoreCTest("ignoreC_eleven"))) + + +## repeat test +unittest(1, enumToInteger(repeatTest("one"), "_RepeatSpace__repeat")) +unittest(1, enumToInteger(repeatTest("initial"), "_RepeatSpace__repeat")) +unittest(2, enumToInteger(repeatTest("two"), "_RepeatSpace__repeat")) +unittest(3, enumToInteger(repeatTest("three"), "_RepeatSpace__repeat")) +unittest(3, enumToInteger(repeatTest("llast"), "_RepeatSpace__repeat")) +unittest(3, enumToInteger(repeatTest("end"), "_RepeatSpace__repeat")) + +## Macro test - nothing in csharp +## Note - this enum is set up with both entries the same +## This means that mapping back from the integer value to the +## string value isn't unique, so asking for "ABCD2" will return +## a string of "ABCD" +unittest("ABCD", enumWithMacroTest("ABCD")) + +## Different types +unittest(10, enumToInteger(differentTypesTest("typeint"), "_DifferentSpace__DifferentTypes")) +unittest(0, enumToInteger(differentTypesTest("typeboolfalse"), "_DifferentSpace__DifferentTypes")) +unittest(1, enumToInteger(differentTypesTest("typebooltrue"), "_DifferentSpace__DifferentTypes")) +unittest(2, enumToInteger(differentTypesTest("typebooltwo"), "_DifferentSpace__DifferentTypes")) +unittest(utf8ToInt('C'), enumToInteger(differentTypesTest("typechar"), "_DifferentSpace__DifferentTypes")) +unittest(utf8ToInt('D'), enumToInteger(differentTypesTest("typedefaultint"), "_DifferentSpace__DifferentTypes")) +unittest(utf8ToInt('A') + 1, enumToInteger(differentTypesTest("typecharcompound"), "_DifferentSpace__DifferentTypes")) + + +## Global different types +## Test uses an anonymous type so the string mapping +## framework doesn't exist. From 80cd2f5cd7de65706dc563a1720d5687b9603081 Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Tue, 19 Feb 2019 10:09:06 +1100 Subject: [PATCH 037/134] Reformat comments in R module --- Source/Modules/r.cxx | 321 +++++++++++++++++++++++-------------------- 1 file changed, 170 insertions(+), 151 deletions(-) diff --git a/Source/Modules/r.cxx b/Source/Modules/r.cxx index 3260dfaf8..5ae138f93 100644 --- a/Source/Modules/r.cxx +++ b/Source/Modules/r.cxx @@ -65,11 +65,11 @@ static String * getRTypeName(SwigType *t, int *outCount = NULL) { */ } -/********************* - Tries to get the name of the R class corresponding to the given type - e.g. struct A * is ARef, struct A** is ARefRef. - Now handles arrays, i.e. struct A[2] -****************/ +/* -------------------------------------------------------------- + * Tries to get the name of the R class corresponding to the given type + * e.g. struct A * is ARef, struct A** is ARefRef. + * Now handles arrays, i.e. struct A[2] + * --------------------------------------------------------------*/ static String *getRClassName(String *retType, int /*addRef*/ = 1, int upRef=0) { String *tmp = NewString(""); @@ -131,11 +131,12 @@ static String *getRClassName(String *retType, int /*addRef*/ = 1, int upRef=0) { */ } -/********************* - Tries to get the name of the R class corresponding to the given type - e.g. struct A * is ARef, struct A** is ARefRef. - Now handles arrays, i.e. struct A[2] -****************/ +/* -------------------------------------------------------------- + * Tries to get the name of the R class corresponding to the given type + * e.g. struct A * is ARef, struct A** is ARefRef. + * Now handles arrays, i.e. struct A[2] + * --------------------------------------------------------------*/ + static String * getRClassNameCopyStruct(String *retType, int addRef) { String *tmp = NewString(""); @@ -188,12 +189,13 @@ static String * getRClassNameCopyStruct(String *retType, int addRef) { } -/********************************* - Write the elements of a list to the File*, one element per line. - If quote is true, surround the element with "element". - This takes care of inserting a tab in front of each line and also - a comma after each element, except the last one. -**********************************/ +/* ------------------------------------------------------------- + * Write the elements of a list to the File*, one element per line. + * If quote is true, surround the element with "element". + * This takes care of inserting a tab in front of each line and also + * a comma after each element, except the last one. + * --------------------------------------------------------------*/ + static void writeListByLine(List *l, File *out, bool quote = 0) { int i, n = Len(l); @@ -222,9 +224,10 @@ R Options (available with -r)\n\ -/************ - Display the help for this module on the screen/console. -*************/ +/* ------------------------------------------------------------- + * Display the help for this module on the screen/console. + * --------------------------------------------------------------*/ + static void showUsage() { fputs(usage, stdout); } @@ -238,10 +241,11 @@ static bool expandTypedef(SwigType *t) { } -/***** - Determine whether we should add a .copy argument to the S function - that wraps/interfaces to the routine that returns the given type. -*****/ +/* ------------------------------------------------------------- + * Determine whether we should add a .copy argument to the S function + * that wraps/interfaces to the routine that returns the given type. + * --------------------------------------------------------------*/ + static int addCopyParameter(SwigType *type) { int ok = 0; ok = Strncmp(type, "struct ", 7) == 0 || Strncmp(type, "p.struct ", 9) == 0; @@ -541,9 +545,10 @@ void R::addSMethodInfo(String *name, String *argType, int nargs) { } } -/* - Returns the name of the new routine. -*/ +/* ---------------------------------------- + * Returns the name of the new routine. + * ------------------------------------------ */ + String * R::createFunctionPointerHandler(SwigType *t, Node *n, int *numArgs) { String *funName = SwigType_manglestr(t); @@ -780,12 +785,12 @@ int R::cDeclaration(Node *n) { #endif -/** - Method from Language that is called to start the entire - processing off, i.e. the generation of the code. - It is called after the input has been read and parsed. - Here we open the output streams and generate the code. -***/ +/* ------------------------------------------------------------- + * Method from Language that is called to start the entire + * processing off, i.e. the generation of the code. + * It is called after the input has been read and parsed. + * Here we open the output streams and generate the code. + * ------------------------------------------------------------- */ int R::top(Node *n) { String *module = Getattr(n, "name"); @@ -867,9 +872,9 @@ int R::top(Node *n) { } -/***************************************************** - Write the generated code to the .S and the .c files. -****************************************************/ +/* ------------------------------------------------------------- + * Write the generated code to the .S and the .c files. + * ------------------------------------------------------------- */ int R::DumpCode(Node *n) { String *output_filename = NewString(""); @@ -937,22 +942,23 @@ int R::DumpCode(Node *n) { -/* - We may need to do more.... so this is left as a - stub for the moment. -*/ +/* ------------------------------------------------------------- + * We may need to do more.... so this is left as a + * stub for the moment. + * -------------------------------------------------------------*/ int R::OutputClassAccessInfo(Hash *tb, File *out) { int n = OutputClassMemberTable(tb, out); OutputClassMethodsTable(out); return n; } -/************************************************************************ - Currently this just writes the information collected about the - different methods of the C++ classes that have been processed - to the console. - This will be used later to define S4 generics and methods. -**************************************************************************/ +/* ------------------------------------------------------------- + * Currently this just writes the information collected about the + * different methods of the C++ classes that have been processed + * to the console. + * This will be used later to define S4 generics and methods. + * --------------------------------------------------------------*/ + int R::OutputClassMethodsTable(File *) { Hash *tb = ClassMethodsTable; @@ -981,20 +987,21 @@ int R::OutputClassMethodsTable(File *) { } -/* - Iterate over the _set and <>_get - elements and generate the $ and $<- functions - that provide constrained access to the member - fields in these elements. +/* -------------------------------------------------------------- + * Iterate over the _set and <>_get + * elements and generate the $ and $<- functions + * that provide constrained access to the member + * fields in these elements. - tb - a hash table that is built up in functionWrapper - as we process each membervalueHandler. - The entries are indexed by _set and - _get. Each entry is a List *. + * tb - a hash table that is built up in functionWrapper + * as we process each membervalueHandler. + * The entries are indexed by _set and + * _get. Each entry is a List *. + + * out - the stram where the code is to be written. This is the S + * code stream as we generate only S code here. + * --------------------------------------------------------------*/ - out - the stram where the code is to be written. This is the S - code stream as we generate only S code here.. -*/ int R::OutputClassMemberTable(Hash *tb, File *out) { List *keys = Keys(tb), *el; @@ -1034,17 +1041,18 @@ int R::OutputClassMemberTable(Hash *tb, File *out) { return n; } -/******************************************************************* - Write the methods for $ or $<- for accessing a member field in an - struct or union (or class). - className - the name of the struct or union (e.g. Bar for struct Bar) - isSet - a logical value indicating whether the method is for - modifying ($<-) or accessing ($) the member field. - el - a list of length 2 * # accessible member elements + 1. - The first element is the name of the class. - The other pairs are member name and the name of the R function to access it. - out - the stream where we write the code. -********************************************************************/ +/* -------------------------------------------------------------- + * Write the methods for $ or $<- for accessing a member field in an + * struct or union (or class). + * className - the name of the struct or union (e.g. Bar for struct Bar) + * isSet - a logical value indicating whether the method is for + * modifying ($<-) or accessing ($) the member field. + * el - a list of length 2 * # accessible member elements + 1. + * The first element is the name of the class. + * The other pairs are member name and the name of the R function to access it. + * out - the stream where we write the code. + * --------------------------------------------------------------*/ + int R::OutputMemberReferenceMethod(String *className, int isSet, List *el, File *out) { int numMems = Len(el), j; @@ -1168,15 +1176,16 @@ int R::OutputMemberReferenceMethod(String *className, int isSet, return SWIG_OK; } -/******************************************************************* - Write the methods for [ or [<- for accessing a member field in an - struct or union (or class). - className - the name of the struct or union (e.g. Bar for struct Bar) - el - a list of length 2 * # accessible member elements + 1. - The first element is the name of the class. - The other pairs are member name and the name of the R function to access it. - out - the stream where we write the code. -********************************************************************/ +/* ------------------------------------------------------------- + * Write the methods for [ or [<- for accessing a member field in an + * struct or union (or class). + * className - the name of the struct or union (e.g. Bar for struct Bar) + * el - a list of length 2 * # accessible member elements + 1. + * The first element is the name of the class. + * The other pairs are member name and the name of the R function to access it. + * out - the stream where we write the code. + * --------------------------------------------------------------*/ + int R::OutputArrayMethod(String *className, List *el, File *out) { int numMems = Len(el), j; @@ -1207,11 +1216,12 @@ int R::OutputArrayMethod(String *className, List *el, File *out) { } -/************************************************************ - Called when a enumeration is to be processed. - We want to call the R function defineEnumeration(). - tdname is the typedef of the enumeration, i.e. giving its name. -*************************************************************/ +/* ------------------------------------------------------------- + * Called when a enumeration is to be processed. + * We want to call the R function defineEnumeration(). + * tdname is the typedef of the enumeration, i.e. giving its name. + * --------------------------------------------------------------*/ + int R::enumDeclaration(Node *n) { if (!ImportMode) { if (getCurrentClass() && (cplus_mode != PUBLIC)) @@ -1255,8 +1265,9 @@ int R::enumDeclaration(Node *n) { return SWIG_OK; } -/************************************************************* -**************************************************************/ +/* ------------------------------------------------------------- +* --------------------------------------------------------------*/ + int R::enumvalueDeclaration(Node *n) { if (getCurrentClass() && (cplus_mode != PUBLIC)) { Printf(stdout, "evd: Not public\n"); @@ -1323,11 +1334,12 @@ int R::enumvalueDeclaration(Node *n) { } -/************************************************************* -Create accessor functions for variables. -Does not create equivalent wrappers for enumerations, -which are handled differently -**************************************************************/ +/* ------------------------------------------------------------- + * Create accessor functions for variables. + * Does not create equivalent wrappers for enumerations, + * which are handled differently + * --------------------------------------------------------------*/ + int R::variableWrapper(Node *n) { String *name = Getattr(n, "sym:name"); if (debugMode) { @@ -1368,12 +1380,12 @@ int R::variableWrapper(Node *n) { return SWIG_OK; } -/************************************************************* -Creates accessor functions for class members. +/* ------------------------------------------------------------- + * Creates accessor functions for class members. -ToDo - this version depends on naming conventions and needs -to be replaced. -**************************************************************/ + * ToDo - this version depends on naming conventions and needs + * to be replaced. + * --------------------------------------------------------------*/ void R::addAccessor(String *memberName, Wrapper *wrapper, String *name, int isSet) { @@ -1776,9 +1788,10 @@ void R::dispatchFunction(Node *n) { DelWrapper(f); } -/****************************************************************** +/*-------------------------------------------------------------- + +* --------------------------------------------------------------*/ -*******************************************************************/ int R::functionWrapper(Node *n) { String *fname = Getattr(n, "name"); String *iname = Getattr(n, "sym:name"); @@ -2329,15 +2342,16 @@ int R::constantWrapper(Node *n) { return SWIG_OK; } -/***************************************************** - Add the specified routine name to the collection of - generated routines that are called from R functions. - This is used to register the routines with R for - resolving symbols. +/*-------------------------------------------------------------- + * Add the specified routine name to the collection of + * generated routines that are called from R functions. + * This is used to register the routines with R for + * resolving symbols. + + * rname - the name of the routine + * nargs - the number of arguments it expects. + * --------------------------------------------------------------*/ - rname - the name of the routine - nargs - the number of arguments it expects. -******************************************************/ int R::addRegistrationRoutine(String *rname, int nargs) { if(!registrationTable) registrationTable = NewHash(); @@ -2350,11 +2364,12 @@ int R::addRegistrationRoutine(String *rname, int nargs) { return SWIG_OK; } -/***************************************************** - Write the registration information to an array and - create the initialization routine for registering - these. -******************************************************/ +/* ------------------------------------------------------------- + * Write the registration information to an array and + * create the initialization routine for registering + * these. + * --------------------------------------------------------------*/ + int R::outputRegistrationRoutines(File *out) { int i, n; if(!registrationTable) @@ -2397,11 +2412,11 @@ int R::outputRegistrationRoutines(File *out) { -/**************************************************************************** - Process a struct, union or class declaration in the source code, - or an anonymous typedef struct +/* ------------------------------------------------------------- + * Process a struct, union or class declaration in the source code, + * or an anonymous typedef struct + * --------------------------------------------------------------*/ -*****************************************************************************/ //XXX What do we need to do here - // Define an S4 class to refer to this. @@ -2582,12 +2597,13 @@ int R::classDeclaration(Node *n) { -/*************************************************************** - Create the C routines that copy an S object of the class given - by the given struct definition in Node *n to the C value - and also the routine that goes from the C routine to an object - of this S class. -****************************************************************/ +/* ------------------------------------------------------------- + * Create the C routines that copy an S object of the class given + * by the given struct definition in Node *n to the C value + * and also the routine that goes from the C routine to an object + * of this S class. + * --------------------------------------------------------------*/ + /*XXX Clean up the toCRef - make certain the names are correct for the types, etc. in all cases. @@ -2682,13 +2698,14 @@ int R::generateCopyRoutines(Node *n) { -/***** - Called when there is a typedef to be invoked. +/* ------------------------------------------------------------- + * Called when there is a typedef to be invoked. + * + * XXX Needs to be enhanced or split to handle the case where we have a + * typedef within a classDeclaration emission because the struct/union/etc. + * is anonymous. + * --------------------------------------------------------------*/ - XXX Needs to be enhanced or split to handle the case where we have a - typedef within a classDeclaration emission because the struct/union/etc. - is anonymous. -******/ int R::typedefHandler(Node *n) { SwigType *tp = Getattr(n, "type"); String *type = Getattr(n, "type"); @@ -2712,12 +2729,13 @@ int R::typedefHandler(Node *n) { -/********************* - Called when processing a field in a "class", i.e. struct, union or - actual class. We set a state variable so that we can correctly - interpret the resulting functionWrapper() call and understand that - it is for a field element. -**********************/ +/* -------------------------------------------------------------- + * Called when processing a field in a "class", i.e. struct, union or + * actual class. We set a state variable so that we can correctly + * interpret the resulting functionWrapper() call and understand that + * it is for a field element. + * --------------------------------------------------------------*/ + int R::membervariableHandler(Node *n) { SwigType *t = Getattr(n, "type"); processType(t, n, NULL); @@ -2752,12 +2770,14 @@ String * R::runtimeCode() { } -/** - Called when SWIG wants to initialize this - We initialize anythin we want here. - Most importantly, tell SWIG where to find the files (e.g. r.swg) for this module. - Use Swig_mark_arg() to tell SWIG that it is understood and not to throw an error. -**/ +/* ----------------------------------------------------------------------- + * Called when SWIG wants to initialize this + * We initialize anythin we want here. + * Most importantly, tell SWIG where to find the files (e.g. r.swg) for this module. + * Use Swig_mark_arg() to tell SWIG that it is understood and not to + * throw an error. + * --------------------------------------------------------------*/ + void R::main(int argc, char *argv[]) { init(); Preprocessor_define("SWIGR 1", 0); @@ -2840,10 +2860,10 @@ void R::main(int argc, char *argv[]) { } } -/* - Could make this work for String or File and then just store the resulting string - rather than the collection of arguments and argc. -*/ +/* ----------------------------------------------------------------------- + * Could make this work for String or File and then just store the resulting string + * rather than the collection of arguments and argc. + * ----------------------------------------------------------------------- */ int R::outputCommandLineArguments(File *out) { if(Argc < 1 || !Argv || !Argv[0]) @@ -2869,11 +2889,10 @@ Language *swig_r(void) { -/*************************************************************************************/ -/* - Needs to be reworked. -*/ +/* ----------------------------------------------------------------------- + * Needs to be reworked. + *----------------------------------------------------------------------- */ String * R::processType(SwigType *t, Node *n, int *nargs) { //XXX Need to handle typedefs, e.g. // a type which is a typedef to a function pointer. @@ -2925,12 +2944,12 @@ String * R::processType(SwigType *t, Node *n, int *nargs) { return NULL; } -/*************************************************************************************/ - /* ----------------------------------------------------------------------- - * enumValue() - * This method will return a string with an enum value to use in from R when - * setting up an enum variable - * ------------------------------------------------------------------------ */ + +/* ----------------------------------------------------------------------- + * enumValue() + * This method will return a string with an enum value to use in from R when + * setting up an enum variable + * ------------------------------------------------------------------------ */ String *R::enumValue(Node *n) { String *symname = Getattr(n, "sym:name"); From 4490d0ec2ca318d63aa40ac3ed07e751d539359a Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Thu, 21 Feb 2019 21:23:25 +1100 Subject: [PATCH 038/134] FIX: Corrected path to output from R tests Makefile was attempting to cat output files from the script source directory instead of the build directory. --- Examples/test-suite/r/Makefile.in | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Examples/test-suite/r/Makefile.in b/Examples/test-suite/r/Makefile.in index 1616ffd3d..33e9d90da 100644 --- a/Examples/test-suite/r/Makefile.in +++ b/Examples/test-suite/r/Makefile.in @@ -63,7 +63,7 @@ include $(srcdir)/../common.mk # check for syntactic correctness run_testcase = \ if [ -f $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) ]; then \ - env LD_LIBRARY_PATH=.:$$LD_LIBRARY_PATH PATH=.:"$$PATH" $(RUNTOOL) $(RUNR) $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) || (cat $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX)out ; false); \ + env LD_LIBRARY_PATH=.:$$LD_LIBRARY_PATH PATH=.:"$$PATH" $(RUNTOOL) $(RUNR) $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) || (cat ./$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX)out ; false); \ else \ $(RUNTOOL) $(RUNR) ./$(SCRIPTPREFIX)$*$(WRAPSUFFIX) || (cat ./$(SCRIPTPREFIX)$*$(WRAPSUFFIX)out ; false); \ fi @@ -71,7 +71,7 @@ run_testcase = \ run_multitestcase = \ for f in `cat $(top_srcdir)/$(EXAMPLES)/$(TEST_SUITE)/$*.list` ; do \ if [ -f $(SCRIPTDIR)/$(SCRIPTPREFIX)$${f}$(SCRIPTSUFFIX) ]; then \ - env LD_LIBRARY_PATH=.:$$LD_LIBRARY_PATH PATH=.:"$$PATH" $(RUNTOOL) $(RUNR) $(SCRIPTDIR)/$(SCRIPTPREFIX)$${f}$(SCRIPTSUFFIX) || (cat $(SCRIPTDIR)/$(SCRIPTPREFIX)$${f}$(SCRIPTSUFFIX)out ; false); \ + env LD_LIBRARY_PATH=.:$$LD_LIBRARY_PATH PATH=.:"$$PATH" $(RUNTOOL) $(RUNR) $(SCRIPTDIR)/$(SCRIPTPREFIX)$${f}$(SCRIPTSUFFIX) || (cat ./$(SCRIPTPREFIX)$${f}$(SCRIPTSUFFIX)out ; false); \ else \ $(RUNTOOL) $(RUNR) ./$(SCRIPTPREFIX)$${f}$(WRAPSUFFIX) || (cat ./$(SCRIPTPREFIX)$${f}$(WRAPSUFFIX)out ; false); \ fi; \ From 4081521210deb5509a679ac0b59f7bd17a446f8d Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Thu, 21 Feb 2019 21:48:51 +1100 Subject: [PATCH 039/134] DOC: Extended documentation on enumeration support in R Touched on delayedAssign, use of character strings, function attributes, hidden environments and the lack of support for anonymous enumerations. --- Doc/Manual/R.html | 43 ++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 40 insertions(+), 3 deletions(-) diff --git a/Doc/Manual/R.html b/Doc/Manual/R.html index b9dba4f9c..9fa27274b 100644 --- a/Doc/Manual/R.html +++ b/Doc/Manual/R.html @@ -189,9 +189,46 @@ of the proxy class baggage you see in other languages.

    -enumerations are characters which are then converted back and forth to -ints before calling the C routines. All of the enumeration code is -done in R. +R doesn't have a native enumeration type. Enumerations are represented +as character strings in R, with calls to R functions that convert back +and forth between integers. + +The details of enumeration names and contents are stored in hidden R +environments, which are named according the the enumeration name - for +example, an enumeration colour: +

    +enum colour { red=-1, blue, green = 10 };
    +
    + +will be initialized by the following call in R: +
    +defineEnumeration("_colour",
    + .values=c("red" = .Call('R_swig_colour_red_get',FALSE, PACKAGE='enum_thorough'),
    +"blue" = .Call('R_swig_colour_blue_get',FALSE, PACKAGE='enum_thorough'),
    +"green" = .Call('R_swig_colour_green_get',FALSE, PACKAGE='enum_thorough')))
    +
    +
    + +which will create an environment named .__E___colour. The enumeration +values are initialised via calls to C/C++ code, allowing complex +values for enumerations to be used. Calls to the C/C++ code require +the compiled library to be loaded, so a delayedAssign is employed +within defineEnumeration in order to allow the code to be easily used in R +packages. + +The user typically does not need to access the enumeration lookup +functions or know the name of the enumeration type used by +R. Attributes containing the type information are attached by swig to +functions requiring enumeration arguments or returning enumeration +values, and those attributes are used to identify and access the +appropriate environments and thus translate between characters +and integers. + +The relevant functions, for debugging purposes, are enumToInteger and +enumFromInteger. + +Anonymous enumerations are not supported. +

    From 43af20ab3bf7aa0a935bef8e74da5b44ad3bedca Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Wed, 6 Mar 2019 20:57:04 +1100 Subject: [PATCH 040/134] FIX: references to enums now functioning There is some consolidation work to be done. The core of the change is getRClassName2, which will probably eventually replace getRClassName. getRClassName seems to be in a funny state, with a middle argument that is commented out and never used. My next step is to verify whether the new version can replace it. --- Examples/test-suite/r/enum_thorough_runme.R | 17 ++-- Lib/r/r.swg | 5 ++ Lib/r/rtype.swg | 7 +- Source/Modules/r.cxx | 87 ++++++++------------- 4 files changed, 47 insertions(+), 69 deletions(-) diff --git a/Examples/test-suite/r/enum_thorough_runme.R b/Examples/test-suite/r/enum_thorough_runme.R index 608abc71a..a0f1270b7 100644 --- a/Examples/test-suite/r/enum_thorough_runme.R +++ b/Examples/test-suite/r/enum_thorough_runme.R @@ -51,9 +51,8 @@ unittest(v, s$speedTest3(v)) unittest(v, s$speedTest4(v)) unittest(v, s$speedTest5(v)) unittest(v, s$speedTest6(v)) -# Not handling enum references - probably needs a typemap -# unittest(v, s$speedTest7(v)) -# unittest(v, s$speedTest8(v)) +unittest(v, s$speedTest7(v)) +unittest(v, s$speedTest8(v)) ## speedTest methods not in the class @@ -62,7 +61,7 @@ unittest(v, speedTest2(v)) unittest(v, speedTest3(v)) unittest(v, speedTest4(v)) # enum reference -# unittest(v, speedTest5(v)) +unittest(v, speedTest5(v)) ## member access s <- SpeedClass() @@ -132,7 +131,7 @@ unittest(g, tt$scientistsTestG(g)) unittest(g, tt$scientistsTestH(g)) unittest(g, tt$scientistsTestI(g)) # enum reference -#unittest(g, tt$scientistsTestJ(g)) +unittest(g, tt$scientistsTestJ(g)) unittest(g, scientistsTest1(g)) @@ -143,7 +142,7 @@ unittest(g, scientistsTest5(g)) unittest(g, scientistsTest6(g)) unittest(g, scientistsTest7(g)) ## enum reference -## unittest(g, scientistsTest8(g)) +unittest(g, scientistsTest8(g)) tt <- TClassInt() b <- "bell" @@ -331,7 +330,7 @@ unittest(b, hairTest9(b)) unittest(b, hairTestA(b)) unittest(b, hairTestB(b)) ## enum reference -##unittest(b, hairTestC(b)) +unittest(b, hairTestC(b)) unittest(b, hairTestA1(b)) unittest(b, hairTestA2(b)) unittest(b, hairTestA3(b)) @@ -344,7 +343,7 @@ unittest(b, hairTestA9(b)) unittest(b, hairTestAA(b)) unittest(b, hairTestAB(b)) ## enum reference -## unittest(b, hairTestAC(b)) +unittest(b, hairTestAC(b)) unittest(b, hairTestB1(b)) unittest(b, hairTestB2(b)) @@ -358,7 +357,7 @@ unittest(b, hairTestB9(b)) unittest(b, hairTestBA(b)) unittest(b, hairTestBB(b)) ## enum reference -## unittest(b, hairTestBC(b)) +unittest(b, hairTestBC(b)) f <- FirStruct() b <- "blonde" diff --git a/Lib/r/r.swg b/Lib/r/r.swg index a9035331b..e6153892e 100644 --- a/Lib/r/r.swg +++ b/Lib/r/r.swg @@ -192,6 +192,11 @@ unsigned char *OUTPUT free($1); } +%typemap(in) const enum SWIGTYPE & ($*1_ltype temp) +%{ temp = ($*1_ltype)INTEGER($input)[0]; + $1 = &temp; %} + +%typemap(out) const enum SWIGTYPE & %{ $result = Rf_ScalarInteger(*$1); %} %typemap(memberin) char[] %{ if ($input) strcpy($1, $input); diff --git a/Lib/r/rtype.swg b/Lib/r/rtype.swg index c55c70377..bdc48c24e 100644 --- a/Lib/r/rtype.swg +++ b/Lib/r/rtype.swg @@ -16,6 +16,7 @@ %typemap("rtype") enum SWIGTYPE * "character"; %typemap("rtype") enum SWIGTYPE *const "character"; %typemap("rtype") enum SWIGTYPE & "character"; +%typemap("rtype") const enum SWIGTYPE & "character"; %typemap("rtype") enum SWIGTYPE && "character"; %typemap("rtype") SWIGTYPE * "$R_class"; %typemap("rtype") SWIGTYPE *const "$R_class"; @@ -86,9 +87,7 @@ %typemap(scoercein) enum SWIGTYPE %{ $input = enumToInteger($input, "$R_class"); %} %typemap(scoercein) enum SWIGTYPE & - %{ $input = enumToInteger($input, "$R_class"); %} -%typemap(scoercein) enum SWIGTYPE && - %{ $input = enumToInteger($input, "$R_class"); %} + %{ $input = enumToInteger($input, "$*R_class"); %} %typemap(scoercein) enum SWIGTYPE * %{ $input = enumToInteger($input, "$R_class"); %} %typemap(scoercein) enum SWIGTYPE *const @@ -138,7 +137,7 @@ string &, std::string & %{ $result = enumFromInteger($result, "$R_class"); %} %typemap(scoerceout) enum SWIGTYPE & - %{ $result = enumFromInteger($result, "$R_class"); %} + %{ $result = enumFromInteger($result, "$*R_class"); %} %typemap(scoerceout) enum SWIGTYPE && %{ $result = enumFromInteger($result, "$R_class"); %} diff --git a/Source/Modules/r.cxx b/Source/Modules/r.cxx index 5ae138f93..ff68b8cf4 100644 --- a/Source/Modules/r.cxx +++ b/Source/Modules/r.cxx @@ -74,61 +74,37 @@ static String * getRTypeName(SwigType *t, int *outCount = NULL) { static String *getRClassName(String *retType, int /*addRef*/ = 1, int upRef=0) { String *tmp = NewString(""); SwigType *resolved = SwigType_typedef_resolve_all(retType); - char *retName = Char(SwigType_manglestr(resolved)); if (upRef) { - Printf(tmp, "_p%s", retName); - } else{ - Insert(tmp, 0, retName); - } - - return tmp; -/* -#if 1 - List *l = SwigType_split(retType); - int n = Len(l); - if(!l || n == 0) { -#ifdef R_SWIG_VERBOSE - if (debugMode) - Printf(stdout, "SwigType_split return an empty list for %s\n", - retType); -#endif - return(tmp); - } - - - String *el = Getitem(l, n-1); - char *ptr = Char(el); - if(strncmp(ptr, "struct ", 7) == 0) - ptr += 7; - - Printf(tmp, "%s", ptr); - - if(addRef) { - for(int i = 0; i < n; i++) { - if(Strcmp(Getitem(l, i), "p.") == 0 || - Strncmp(Getitem(l, i), "a(", 2) == 0) - Printf(tmp, "Ref"); - } - } - -#else - char *retName = Char(SwigType_manglestr(retType)); - if(!retName) - return(tmp); - - if(addRef) { - while(retName && strlen(retName) > 1 && strncmp(retName, "_p", 2) == 0) { - retName += 2; - Printf(tmp, "Ref"); - } - } - if(retName[0] == '_') - retName ++; + SwigType_add_pointer(resolved); + } + char *retName = Char(SwigType_manglestr(resolved)); Insert(tmp, 0, retName); -#endif - return tmp; -*/ +} +/* -------------------------------------------------------------- + * Tries to get the resolved name, with options of adding + * or removing a layer of references. Take care not + * to request both + * --------------------------------------------------------------*/ + +static String *getRClassName2(String *retType, int deRef=0, int upRef=0) { + SwigType *resolved = SwigType_typedef_resolve_all(retType); + int ispointer = SwigType_ispointer(resolved); + int isreference = SwigType_isreference(resolved); + if (upRef) { + SwigType_add_pointer(resolved); + } + if (deRef) { + if (ispointer) { + SwigType_del_pointer(resolved); + } + if (isreference) { + SwigType_del_reference(resolved); + } + } + String *tmp = NewString(""); + Insert(tmp, 0, Char(SwigType_manglestr(resolved))); + return(tmp); } /* -------------------------------------------------------------- @@ -257,10 +233,9 @@ static int addCopyParameter(SwigType *type) { } static void replaceRClass(String *tm, SwigType *type) { - String *tmp = getRClassName(type); - String *tmp_base = getRClassName(type, 0); - String *tmp_ref = getRClassName(type, 1, 1); - + String *tmp = getRClassName2(type, 0, 0); + String *tmp_base = getRClassName2(type, 1, 0); + String *tmp_ref = getRClassName2(type, 0, 1); Replaceall(tm, "$R_class", tmp); Replaceall(tm, "$*R_class", tmp_base); Replaceall(tm, "$&R_class", tmp_ref); From c38b7de6a120e6392abff50afd9bb919cc858cfc Mon Sep 17 00:00:00 2001 From: Orion Poplawski Date: Sun, 10 Mar 2019 11:47:27 -0600 Subject: [PATCH 041/134] Fix format-security error with octave 5.1 --- Lib/octave/octrun.swg | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Lib/octave/octrun.swg b/Lib/octave/octrun.swg index 301233103..ff614e681 100644 --- a/Lib/octave/octrun.swg +++ b/Lib/octave/octrun.swg @@ -51,7 +51,7 @@ SWIGRUNTIME octave_value SWIG_Error(int code, const char *msg) { octave_value type(SWIG_ErrorType(code)); std::string r = msg; r += " (" + type.string_value() + ")"; - error(r.c_str()); + error("%s", r.c_str()); return octave_value(r); } @@ -840,7 +840,7 @@ SWIGRUNTIME void swig_acquire_ownership_obj(void *vptr, int own); const std::string opname = std::string("__") + octave_base_value::get_umap_name(umap) + std::string("__"); octave_value ret; if (!dispatch_unary_op(opname, ret)) { - error((opname + std::string(" method not found")).c_str()); + error("%s", (opname + std::string(" method not found")).c_str()); return octave_value(); } return ret; From 6e3518c9b4b8cfd08c7e6d828053c7e3212adeb8 Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Mon, 11 Mar 2019 21:17:03 +1100 Subject: [PATCH 042/134] ENH: Replaced the old getRClassName with the new one that uses the swig functions for detecting, adding and removing pointers andreferences. --- Source/Modules/r.cxx | 24 ++++-------------------- 1 file changed, 4 insertions(+), 20 deletions(-) diff --git a/Source/Modules/r.cxx b/Source/Modules/r.cxx index ff68b8cf4..fde583ed6 100644 --- a/Source/Modules/r.cxx +++ b/Source/Modules/r.cxx @@ -65,29 +65,13 @@ static String * getRTypeName(SwigType *t, int *outCount = NULL) { */ } -/* -------------------------------------------------------------- - * Tries to get the name of the R class corresponding to the given type - * e.g. struct A * is ARef, struct A** is ARefRef. - * Now handles arrays, i.e. struct A[2] - * --------------------------------------------------------------*/ - -static String *getRClassName(String *retType, int /*addRef*/ = 1, int upRef=0) { - String *tmp = NewString(""); - SwigType *resolved = SwigType_typedef_resolve_all(retType); - if (upRef) { - SwigType_add_pointer(resolved); - } - char *retName = Char(SwigType_manglestr(resolved)); - Insert(tmp, 0, retName); - return tmp; -} /* -------------------------------------------------------------- * Tries to get the resolved name, with options of adding * or removing a layer of references. Take care not * to request both * --------------------------------------------------------------*/ -static String *getRClassName2(String *retType, int deRef=0, int upRef=0) { +static String *getRClassName(String *retType, int deRef=0, int upRef=0) { SwigType *resolved = SwigType_typedef_resolve_all(retType); int ispointer = SwigType_ispointer(resolved); int isreference = SwigType_isreference(resolved); @@ -233,9 +217,9 @@ static int addCopyParameter(SwigType *type) { } static void replaceRClass(String *tm, SwigType *type) { - String *tmp = getRClassName2(type, 0, 0); - String *tmp_base = getRClassName2(type, 1, 0); - String *tmp_ref = getRClassName2(type, 0, 1); + String *tmp = getRClassName(type, 0, 0); + String *tmp_base = getRClassName(type, 1, 0); + String *tmp_ref = getRClassName(type, 0, 1); Replaceall(tm, "$R_class", tmp); Replaceall(tm, "$*R_class", tmp_base); Replaceall(tm, "$&R_class", tmp_ref); From 38572f925136e6263d648eafb9fbec9211e03bc7 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 11 Mar 2019 18:53:48 +0000 Subject: [PATCH 043/134] Add changes entry for Octave 5.1 format-security fix --- CHANGES.current | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 2b77e63f3..80230e964 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,11 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-03-11: dirteat,opoplawski + [Octave] Fix compilation errors in Octave 5.1. + + error: format not a string literal and no format arguments [-Werror=format-security] + 2019-02-28: wsfulton [Java] std::vector improvements for types that do not have a default constructor. From f0067b6bbfd1e43f01016a78428bc3d55434bc39 Mon Sep 17 00:00:00 2001 From: Vadim Zeitlin Date: Thu, 7 Mar 2019 02:25:49 +0100 Subject: [PATCH 044/134] Add std::set<> typemaps for C# Create new Lib/csharp/std_set.i based on the existing std_map.i and run li_std_set unit test for C# as well. Notice that the set operations defined by the base ISet<> interface are not implemented yet. --- CHANGES.current | 6 + .../test-suite/csharp/li_std_set_runme.cs | 55 ++++ Examples/test-suite/li_std_set.i | 6 +- Lib/csharp/std_set.i | 239 ++++++++++++++++++ 4 files changed, 303 insertions(+), 3 deletions(-) create mode 100644 Examples/test-suite/csharp/li_std_set_runme.cs create mode 100644 Lib/csharp/std_set.i diff --git a/CHANGES.current b/CHANGES.current index 80230e964..3e3da1099 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,12 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-03-12: vadz + [C#] Add std::set<> typemaps. + + Not all methods of System.Collections.Generic.ISet are implemented yet, but all the + basic methods, including elements access and iteration, are. + 2019-03-11: dirteat,opoplawski [Octave] Fix compilation errors in Octave 5.1. diff --git a/Examples/test-suite/csharp/li_std_set_runme.cs b/Examples/test-suite/csharp/li_std_set_runme.cs new file mode 100644 index 000000000..c186c2f7a --- /dev/null +++ b/Examples/test-suite/csharp/li_std_set_runme.cs @@ -0,0 +1,55 @@ +using System; +using System.Collections.Generic; +using li_std_setNamespace; + +public class runme +{ + static void checkThat(bool mustBeTrue, string message) + { + if (!mustBeTrue) + throw new Exception("Test that the set " + message + " failed"); + } + + static void Main() + { + StringSet ss = new StringSet(); + + // Check the interface methods first. + ISet s = ss; + + checkThat(s.Count == 0, "is initially empty"); + checkThat(!s.Contains("key"), "doesn't contain inexistent element"); + checkThat(!s.Remove("key"), "returns false when removing inexistent element"); + + checkThat(s.Add("key"), "returns true when adding a new element"); + checkThat(!s.Add("key"), "returns false when adding an existing element"); + checkThat(s.Contains("key"), "contains the just added element"); + checkThat(s.Remove("key"), "returns true when removing an existing element"); + checkThat(s.Count == 0, "is empty again"); + + checkThat(s.Add("key1"), "Add(key1) returns true"); + checkThat(s.Add("key2"), "Add(key2) returns true"); + checkThat(s.Add("key3"), "Add(key3) returns true"); + + // Also check a different interface, providing a different Add() (sic!). + ICollection coll = ss; + coll.Add("key"); + checkThat(ss.Count == 4, "contains 4 elements"); + + // Now use object-specific methods, mimicking HashSet<>. + string val; + checkThat(ss.TryGetValue("key1", out val), "could retrieve existing item"); + checkThat(val.Equals("key1"), "value was returned correctly by TryGetValue()"); + checkThat(!ss.TryGetValue("no-such-key", out val), "couldn't retrieve inexistent item"); + checkThat(val == null, "value was reset after failed TryGetValue()"); + + IList list = new List(); + foreach (string str in ss) { + list.Add(str); + } + checkThat(list.Count == 4, "copy contains 4 elements"); + + ss.Clear(); + checkThat(ss.Count == 0, "is empty after Clear()"); + } +} diff --git a/Examples/test-suite/li_std_set.i b/Examples/test-suite/li_std_set.i index fc9db42a9..bb952cd85 100644 --- a/Examples/test-suite/li_std_set.i +++ b/Examples/test-suite/li_std_set.i @@ -15,15 +15,15 @@ %include %include -// Use language macros since Java doesn't have multiset support (yet) +// Use language macros since Java and C# don't have multiset support (yet) // and uses different naming conventions. #if defined(SWIGRUBY) || defined(SWIGPYTHON) %include %template(set_int) std::multiset; %template(v_int) std::vector; %template(set_string) std::set; -#elif defined(SWIGJAVA) - %template(StringSet) std::set; +#elif defined(SWIGJAVA) || defined(SWIGCSHARP) + %template(StringSet) std::set; #endif #if defined(SWIGRUBY) diff --git a/Lib/csharp/std_set.i b/Lib/csharp/std_set.i new file mode 100644 index 000000000..b988d8d91 --- /dev/null +++ b/Lib/csharp/std_set.i @@ -0,0 +1,239 @@ +/* ----------------------------------------------------------------------------- + * std_map.i + * + * SWIG typemaps for std::set + * + * The C# wrapper is made to look and feel like a C# System.Collections.Generic.HashSet<>. + * ----------------------------------------------------------------------------- */ + +%{ +#include +#include +#include +%} + +%csmethodmodifiers std::set::size "private" +%csmethodmodifiers std::set::getitem "private" +%csmethodmodifiers std::set::create_iterator_begin "private" +%csmethodmodifiers std::set::get_next "private" +%csmethodmodifiers std::set::destroy_iterator "private" + +namespace std { + +// TODO: Add support for comparator and allocator template parameters. +template +class set { + +%typemap(csinterfaces) std::set "global::System.IDisposable, global::System.Collections.Generic.ISet<$typemap(cstype, T)>\n"; +%proxycode %{ + void global::System.Collections.Generic.ICollection<$typemap(cstype, T)>.Add(string item) { + ((global::System.Collections.Generic.ISet<$typemap(cstype, T)>)this).Add(item); + } + + public bool TryGetValue($typemap(cstype, T) equalValue, out $typemap(cstype, T) actualValue) { + try { + actualValue = getitem(equalValue); + return true; + } catch { + actualValue = default($typemap(cstype, T)); + return false; + } + } + + public int Count { + get { + return (int)size(); + } + } + + public bool IsReadOnly { + get { + return false; + } + } + + public void CopyTo($typemap(cstype, T)[] array) { + CopyTo(array, 0); + } + + public void CopyTo($typemap(cstype, T)[] array, int arrayIndex) { + if (array == null) + throw new global::System.ArgumentNullException("array"); + if (arrayIndex < 0) + throw new global::System.ArgumentOutOfRangeException("arrayIndex", "Value is less than zero"); + if (array.Rank > 1) + throw new global::System.ArgumentException("Multi dimensional array.", "array"); + if (arrayIndex+this.Count > array.Length) + throw new global::System.ArgumentException("Number of elements to copy is too large."); + + foreach ($typemap(cstype, T) item in this) { + array.SetValue(item, arrayIndex++); + } + } + + public void ExceptWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public void IntersectWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public bool IsProperSubsetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public bool IsProperSupersetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public bool IsSubsetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public bool IsSupersetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public bool Overlaps(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public bool SetEquals(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public void SymmetricExceptWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public void UnionWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + + private global::System.Collections.Generic.ICollection<$typemap(cstype, T)> Items { + get { + global::System.Collections.Generic.ICollection<$typemap(cstype, T)> items = new global::System.Collections.Generic.List<$typemap(cstype, T)>(); + int size = this.Count; + if (size > 0) { + global::System.IntPtr iter = create_iterator_begin(); + for (int i = 0; i < size; i++) { + items.Add(get_next(iter)); + } + destroy_iterator(iter); + } + return items; + } + } + + global::System.Collections.Generic.IEnumerator<$typemap(cstype, T)> global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)>.GetEnumerator() { + return new $csclassnameEnumerator(this); + } + + global::System.Collections.IEnumerator global::System.Collections.IEnumerable.GetEnumerator() { + return new $csclassnameEnumerator(this); + } + + public $csclassnameEnumerator GetEnumerator() { + return new $csclassnameEnumerator(this); + } + + // Type-safe enumerator + /// Note that the IEnumerator documentation requires an InvalidOperationException to be thrown + /// whenever the collection is modified. This has been done for changes in the size of the + /// collection but not when one of the elements of the collection is modified as it is a bit + /// tricky to detect unmanaged code that modifies the collection under our feet. + public sealed class $csclassnameEnumerator : global::System.Collections.IEnumerator, + global::System.Collections.Generic.IEnumerator<$typemap(cstype, T)> + { + private $csclassname collectionRef; + private global::System.Collections.Generic.IList<$typemap(cstype, T)> ItemsCollection; + private int currentIndex; + private $typemap(cstype, T) currentObject; + private int currentSize; + + public $csclassnameEnumerator($csclassname collection) { + collectionRef = collection; + ItemsCollection = new global::System.Collections.Generic.List<$typemap(cstype, T)>(collection.Items); + currentIndex = -1; + currentObject = null; + currentSize = collectionRef.Count; + } + + // Type-safe iterator Current + public $typemap(cstype, T) Current { + get { + if (currentIndex == -1) + throw new global::System.InvalidOperationException("Enumeration not started."); + if (currentIndex > currentSize - 1) + throw new global::System.InvalidOperationException("Enumeration finished."); + if (currentObject == null) + throw new global::System.InvalidOperationException("Collection modified."); + return currentObject; + } + } + + // Type-unsafe IEnumerator.Current + object global::System.Collections.IEnumerator.Current { + get { + return Current; + } + } + + public bool MoveNext() { + int size = collectionRef.Count; + bool moveOkay = (currentIndex+1 < size) && (size == currentSize); + if (moveOkay) { + currentIndex++; + currentObject = ItemsCollection[currentIndex]; + } else { + currentObject = null; + } + return moveOkay; + } + + public void Reset() { + currentIndex = -1; + currentObject = null; + if (collectionRef.Count != currentSize) { + throw new global::System.InvalidOperationException("Collection modified."); + } + } + + public void Dispose() { + currentIndex = -1; + currentObject = null; + } + } + +%} + + public: + typedef size_t size_type; + typedef ptrdiff_t difference_type; + typedef T key_type; + typedef T value_type; + typedef value_type* pointer; + typedef const value_type* const_pointer; + typedef value_type& reference; + typedef const value_type& const_reference; + + set(); + set(const set& other); + size_type size() const; + bool empty() const; + %rename(Clear) clear; + void clear(); + %extend { + bool Add(const value_type& item) { + return $self->insert(item).second; + } + + bool Contains(const value_type& item) { + return $self->count(item) != 0; + } + + bool Remove(const value_type& item) { + return $self->erase(item) != 0; + } + + const value_type& getitem(const value_type& item) throw (std::out_of_range) { + std::set::iterator iter = $self->find(item); + if (iter == $self->end()) + throw std::out_of_range("item not found"); + + return *iter; + } + + // create_iterator_begin(), get_next() and destroy_iterator work together to provide a collection of items to C# + %apply void *VOID_INT_PTR { std::set::iterator *create_iterator_begin } + %apply void *VOID_INT_PTR { std::set::iterator *swigiterator } + + std::set::iterator *create_iterator_begin() { + return new std::set::iterator($self->begin()); + } + + const key_type& get_next(std::set::iterator *swigiterator) { + std::set::iterator iter = *swigiterator; + (*swigiterator)++; + return *iter; + } + + void destroy_iterator(std::set::iterator *swigiterator) { + delete swigiterator; + } + } +}; + +} From aaa12450c06d994900ae86fc7a1a9f8f2e25038d Mon Sep 17 00:00:00 2001 From: Vadim Zeitlin Date: Mon, 11 Mar 2019 23:05:10 +0100 Subject: [PATCH 045/134] Implement set-theoretic methods in std::set C# typemaps These implementations are not optimized, i.e. are done in a naive way in C#, rather than using C++ functions more efficiently, but are better than nothing. --- CHANGES.current | 3 - .../test-suite/csharp/li_std_set_runme.cs | 34 +++++++ Lib/csharp/std_set.i | 88 ++++++++++++++++--- 3 files changed, 112 insertions(+), 13 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 3e3da1099..3765a8273 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -10,9 +10,6 @@ Version 4.0.0 (in progress) 2019-03-12: vadz [C#] Add std::set<> typemaps. - Not all methods of System.Collections.Generic.ISet are implemented yet, but all the - basic methods, including elements access and iteration, are. - 2019-03-11: dirteat,opoplawski [Octave] Fix compilation errors in Octave 5.1. diff --git a/Examples/test-suite/csharp/li_std_set_runme.cs b/Examples/test-suite/csharp/li_std_set_runme.cs index c186c2f7a..6519e8c8d 100644 --- a/Examples/test-suite/csharp/li_std_set_runme.cs +++ b/Examples/test-suite/csharp/li_std_set_runme.cs @@ -51,5 +51,39 @@ public class runme ss.Clear(); checkThat(ss.Count == 0, "is empty after Clear()"); + + // Check set-theoretic methods. + checkThat(new StringSet().SetEquals(new StringSet()), "SetEquals() works for empty sets"); + checkThat(new StringSet{"foo"}.SetEquals(new StringSet{"foo"}), "SetEquals() works for non-empty sets"); + checkThat(!new StringSet{"foo"}.SetEquals(new[] {"bar"}), "SetEquals() doesn't always return true"); + + ss = new StringSet{"foo", "bar", "baz"}; + ss.ExceptWith(new[] {"baz", "quux"}); + checkThat(ss.SetEquals(new[] {"foo", "bar"}), "ExceptWith works"); + + ss = new StringSet{"foo", "bar", "baz"}; + ss.IntersectWith(new[] {"baz", "quux"}); + checkThat(ss.SetEquals(new[] {"baz"}), "IntersectWith works"); + + checkThat(ss.IsProperSubsetOf(new[] {"bar", "baz"}), "IsProperSubsetOf works"); + checkThat(!ss.IsProperSubsetOf(new[] {"baz"}), "!IsProperSubsetOf works"); + checkThat(ss.IsSubsetOf(new[] {"bar", "baz"}), "IsSubsetOf works"); + checkThat(!ss.IsSubsetOf(new[] {"bar"}), "!IsSubsetOf works"); + + ss = new StringSet{"foo", "bar", "baz"}; + checkThat(ss.IsProperSupersetOf(new[] {"bar"}), "IsProperSupersetOf works"); + checkThat(!ss.IsProperSupersetOf(new[] {"quux"}), "IsProperSupersetOf works"); + checkThat(ss.IsSupersetOf(new[] {"foo", "bar", "baz"}), "IsProperSupersetOf works"); + checkThat(!ss.IsSupersetOf(new[] {"foo", "bar", "baz", "quux"}), "IsProperSupersetOf works"); + + checkThat(ss.Overlaps(new[] {"foo"}), "Overlaps works"); + checkThat(!ss.Overlaps(new[] {"moo"}), "!Overlaps works"); + + ss.SymmetricExceptWith(new[] {"baz", "quux"}); + checkThat(ss.SetEquals(new[] {"foo", "bar", "quux"}), "SymmetricExceptWith works"); + + ss = new StringSet{"foo", "bar", "baz"}; + ss.UnionWith(new[] {"baz", "quux"}); + checkThat(ss.SetEquals(new[] {"foo", "bar", "baz", "quux"}), "UnionWith works"); } } diff --git a/Lib/csharp/std_set.i b/Lib/csharp/std_set.i index b988d8d91..c5dd09473 100644 --- a/Lib/csharp/std_set.i +++ b/Lib/csharp/std_set.i @@ -71,16 +71,84 @@ class set { } } - public void ExceptWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public void IntersectWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public bool IsProperSubsetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public bool IsProperSupersetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public bool IsSubsetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public bool IsSupersetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public bool Overlaps(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public bool SetEquals(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public void SymmetricExceptWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } - public void UnionWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { throw new global::System.Exception("TODO"); } + public void ExceptWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + foreach ($typemap(cstype, T) item in other) { + Remove(item); + } + } + + public void IntersectWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + $csclassname old = new $csclassname(this); + + Clear(); + foreach ($typemap(cstype, T) item in other) { + if (old.Contains(item)) + Add(item); + } + } + + private static int count_enum(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + int count = 0; + foreach ($typemap(cstype, T) item in other) { + count++; + } + + return count; + } + + public bool IsProperSubsetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + return IsSubsetOf(other) && Count < count_enum(other); + } + + public bool IsProperSupersetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + return IsSupersetOf(other) && Count > count_enum(other); + } + + public bool IsSubsetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + int countContained = 0; + + foreach ($typemap(cstype, T) item in other) { + if (Contains(item)) + countContained++; + } + + return countContained == Count; + } + + public bool IsSupersetOf(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + foreach ($typemap(cstype, T) item in other) { + if (!Contains(item)) + return false; + } + + return true; + } + + public bool Overlaps(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + foreach ($typemap(cstype, T) item in other) { + if (Contains(item)) + return true; + } + + return false; + } + + public bool SetEquals(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + return IsSupersetOf(other) && Count == count_enum(other); + } + + public void SymmetricExceptWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + foreach ($typemap(cstype, T) item in other) { + if (!Remove(item)) + Add(item); + } + } + + public void UnionWith(global::System.Collections.Generic.IEnumerable<$typemap(cstype, T)> other) { + foreach ($typemap(cstype, T) item in other) { + Add(item); + } + } private global::System.Collections.Generic.ICollection<$typemap(cstype, T)> Items { get { From 04c9a977873928ca341a06a931f197670562fe97 Mon Sep 17 00:00:00 2001 From: Vadim Zeitlin Date: Mon, 11 Mar 2019 23:08:19 +0100 Subject: [PATCH 046/134] Fix header comment in C# std_set typemaps Mention that these typemaps require .NET 4 or greater. --- Lib/csharp/std_set.i | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/Lib/csharp/std_set.i b/Lib/csharp/std_set.i index c5dd09473..3b2492e0e 100644 --- a/Lib/csharp/std_set.i +++ b/Lib/csharp/std_set.i @@ -1,9 +1,13 @@ /* ----------------------------------------------------------------------------- - * std_map.i + * std_set.i * - * SWIG typemaps for std::set + * SWIG typemaps for std::set. * - * The C# wrapper is made to look and feel like a C# System.Collections.Generic.HashSet<>. + * Note that ISet<> used here requires .NET 4 or later. + * + * The C# wrapper implements ISet<> interface and shares performance + * characteristics of C# System.Collections.Generic.SortedSet<> class, but + * doesn't provide quite all of its methods. * ----------------------------------------------------------------------------- */ %{ From 30f59ffe2286283fb01ae2418bf6464f78f18e05 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 12 Mar 2019 20:03:14 +0000 Subject: [PATCH 047/134] Include all template parameters for std_unordered_multimap and std_unordered_map --- Examples/test-suite/cpp11_std_unordered_map.i | 4 +++ Lib/python/std_unordered_map.i | 6 ++-- Lib/python/std_unordered_multimap.i | 28 +++++++++---------- Lib/ruby/std_unordered_map.i | 20 ++++++------- Lib/ruby/std_unordered_multimap.i | 22 +++++++-------- 5 files changed, 42 insertions(+), 38 deletions(-) diff --git a/Examples/test-suite/cpp11_std_unordered_map.i b/Examples/test-suite/cpp11_std_unordered_map.i index b11d8f275..4bdec9c7c 100644 --- a/Examples/test-suite/cpp11_std_unordered_map.i +++ b/Examples/test-suite/cpp11_std_unordered_map.i @@ -5,3 +5,7 @@ %template(UnorderedMapIntInt) std::unordered_map; %template(UnorderedMapStringInt) std::unordered_map; + +%inline %{ +std::unordered_map,std::equal_to< std::string >,std::allocator< std::pair< std::string const,int > > > inout(std::unordered_map m) { return m; } +%} diff --git a/Lib/python/std_unordered_map.i b/Lib/python/std_unordered_map.i index 76acbb1ec..042d5b671 100644 --- a/Lib/python/std_unordered_map.i +++ b/Lib/python/std_unordered_map.i @@ -56,9 +56,9 @@ %fragment("StdUnorderedMapTraits","header",fragment="StdMapCommonTraits",fragment="StdUnorderedMapForwardIteratorTraits") { namespace swig { - template + template inline void - assign(const SwigPySeq& swigpyseq, std::unordered_map *unordered_map) { + assign(const SwigPySeq& swigpyseq, std::unordered_map *unordered_map) { typedef typename std::unordered_map::value_type value_type; typename SwigPySeq::const_iterator it = swigpyseq.begin(); for (;it != swigpyseq.end(); ++it) { @@ -97,7 +97,7 @@ } }; - template + template struct traits_from > { typedef std::unordered_map unordered_map_type; typedef typename unordered_map_type::const_iterator const_iterator; diff --git a/Lib/python/std_unordered_multimap.i b/Lib/python/std_unordered_multimap.i index aa29a7cff..281140445 100644 --- a/Lib/python/std_unordered_multimap.i +++ b/Lib/python/std_unordered_multimap.i @@ -6,27 +6,27 @@ %fragment("StdUnorderedMultimapTraits","header",fragment="StdMapCommonTraits",fragment="StdUnorderedMapForwardIteratorTraits") { namespace swig { - template + template inline void - assign(const SwigPySeq& swigpyseq, std::unordered_multimap *unordered_multimap) { - typedef typename std::unordered_multimap::value_type value_type; + assign(const SwigPySeq& swigpyseq, std::unordered_multimap *unordered_multimap) { + typedef typename std::unordered_multimap::value_type value_type; typename SwigPySeq::const_iterator it = swigpyseq.begin(); for (;it != swigpyseq.end(); ++it) { unordered_multimap->insert(value_type(it->first, it->second)); } } - template - struct traits_reserve > { - static void reserve(std::unordered_multimap &seq, typename std::unordered_multimap::size_type n) { + template + struct traits_reserve > { + static void reserve(std::unordered_multimap &seq, typename std::unordered_multimap::size_type n) { seq.reserve(n); } }; - template - struct traits_asptr > { - typedef std::unordered_multimap unordered_multimap_type; - static int asptr(PyObject *obj, std::unordered_multimap **val) { + template + struct traits_asptr > { + typedef std::unordered_multimap unordered_multimap_type; + static int asptr(PyObject *obj, std::unordered_multimap **val) { int res = SWIG_ERROR; if (PyDict_Check(obj)) { SwigVar_PyObject items = PyObject_CallMethod(obj,(char *)"items",NULL); @@ -34,7 +34,7 @@ /* In Python 3.x the ".items()" method returns a dict_items object */ items = PySequence_Fast(items, ".items() didn't return a sequence!"); %#endif - res = traits_asptr_stdseq, std::pair >::asptr(items, val); + res = traits_asptr_stdseq, std::pair >::asptr(items, val); } else { unordered_multimap_type *p; swig_type_info *descriptor = swig::type_info(); @@ -45,9 +45,9 @@ } }; - template - struct traits_from > { - typedef std::unordered_multimap unordered_multimap_type; + template + struct traits_from > { + typedef std::unordered_multimap unordered_multimap_type; typedef typename unordered_multimap_type::const_iterator const_iterator; typedef typename unordered_multimap_type::size_type size_type; diff --git a/Lib/ruby/std_unordered_map.i b/Lib/ruby/std_unordered_map.i index c3f60bbba..48c875214 100644 --- a/Lib/ruby/std_unordered_map.i +++ b/Lib/ruby/std_unordered_map.i @@ -6,25 +6,25 @@ %fragment("StdUnorderedMapTraits","header",fragment="StdMapCommonTraits") { namespace swig { - template + template inline void - assign(const RubySeq& rubyseq, std::unordered_map *map) { - typedef typename std::unordered_map::value_type value_type; + assign(const RubySeq& rubyseq, std::unordered_map *map) { + typedef typename std::unordered_map::value_type value_type; typename RubySeq::const_iterator it = rubyseq.begin(); for (;it != rubyseq.end(); ++it) { map->insert(value_type(it->first, it->second)); } } - template - struct traits_asptr > { - typedef std::unordered_map map_type; + template + struct traits_asptr > { + typedef std::unordered_map map_type; static int asptr(VALUE obj, map_type **val) { int res = SWIG_ERROR; if (TYPE(obj) == T_HASH) { static ID id_to_a = rb_intern("to_a"); VALUE items = rb_funcall(obj, id_to_a, 0); - res = traits_asptr_stdseq, std::pair >::asptr(items, val); + res = traits_asptr_stdseq, std::pair >::asptr(items, val); } else { map_type *p; swig_type_info *descriptor = swig::type_info(); @@ -35,9 +35,9 @@ } }; - template - struct traits_from > { - typedef std::unordered_map map_type; + template + struct traits_from > { + typedef std::unordered_map map_type; typedef typename map_type::const_iterator const_iterator; typedef typename map_type::size_type size_type; diff --git a/Lib/ruby/std_unordered_multimap.i b/Lib/ruby/std_unordered_multimap.i index b663c1298..ebc53b597 100644 --- a/Lib/ruby/std_unordered_multimap.i +++ b/Lib/ruby/std_unordered_multimap.i @@ -6,25 +6,25 @@ %fragment("StdUnorderedMultimapTraits","header",fragment="StdMapCommonTraits") { namespace swig { - template + template inline void - assign(const RubySeq& rubyseq, std::unordered_multimap *multimap) { - typedef typename std::unordered_multimap::value_type value_type; + assign(const RubySeq& rubyseq, std::unordered_multimap *multimap) { + typedef typename std::unordered_multimap::value_type value_type; typename RubySeq::const_iterator it = rubyseq.begin(); for (;it != rubyseq.end(); ++it) { multimap->insert(value_type(it->first, it->second)); } } - template - struct traits_asptr > { - typedef std::unordered_multimap multimap_type; - static int asptr(VALUE obj, std::unordered_multimap **val) { + template + struct traits_asptr > { + typedef std::unordered_multimap multimap_type; + static int asptr(VALUE obj, std::unordered_multimap **val) { int res = SWIG_ERROR; if ( TYPE(obj) == T_HASH ) { static ID id_to_a = rb_intern("to_a"); VALUE items = rb_funcall(obj, id_to_a, 0); - return traits_asptr_stdseq, std::pair >::asptr(items, val); + return traits_asptr_stdseq, std::pair >::asptr(items, val); } else { multimap_type *p; res = SWIG_ConvertPtr(obj,(void**)&p,swig::type_info(),0); @@ -34,9 +34,9 @@ } }; - template - struct traits_from > { - typedef std::unordered_multimap multimap_type; + template + struct traits_from > { + typedef std::unordered_multimap multimap_type; typedef typename multimap_type::const_iterator const_iterator; typedef typename multimap_type::size_type size_type; From 4a25ddbb97c5c1c793ae5552c40932e6684bb5ae Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 12 Mar 2019 20:21:19 +0000 Subject: [PATCH 048/134] Correct unordered_set/unordered_multiset template Key parameter name --- Lib/java/std_unordered_set.i | 40 ++++++++++++++--------------- Lib/python/std_unordered_multiset.i | 26 +++++++++---------- Lib/python/std_unordered_set.i | 26 +++++++++---------- Lib/ruby/std_unordered_multiset.i | 20 +++++++-------- Lib/ruby/std_unordered_set.i | 20 +++++++-------- Lib/std/std_unordered_multiset.i | 14 +++++----- Lib/std/std_unordered_set.i | 14 +++++----- 7 files changed, 80 insertions(+), 80 deletions(-) diff --git a/Lib/java/std_unordered_set.i b/Lib/java/std_unordered_set.i index 1a7b03688..59726e94d 100644 --- a/Lib/java/std_unordered_set.i +++ b/Lib/java/std_unordered_set.i @@ -43,12 +43,12 @@ namespace std { -template +template class unordered_set { -%typemap(javabase) std::unordered_set "java.util.AbstractSet<$typemap(jboxtype, T)>" +%typemap(javabase) std::unordered_set "java.util.AbstractSet<$typemap(jboxtype, Key)>" %proxycode %{ - public $javaclassname(java.util.Collection collection) { + public $javaclassname(java.util.Collection collection) { this(); addAll(collection); } @@ -57,34 +57,34 @@ class unordered_set { return sizeImpl(); } - public boolean addAll(java.util.Collection collection) { + public boolean addAll(java.util.Collection collection) { boolean didAddElement = false; for (java.lang.Object object : collection) { - didAddElement |= add(($typemap(jboxtype, T))object); + didAddElement |= add(($typemap(jboxtype, Key))object); } return didAddElement; } - public java.util.Iterator<$typemap(jboxtype, T)> iterator() { - return new java.util.Iterator<$typemap(jboxtype, T)>() { + public java.util.Iterator<$typemap(jboxtype, Key)> iterator() { + return new java.util.Iterator<$typemap(jboxtype, Key)>() { private Iterator curr; private Iterator end; - private java.util.Iterator<$typemap(jboxtype, T)> init() { + private java.util.Iterator<$typemap(jboxtype, Key)> init() { curr = $javaclassname.this.begin(); end = $javaclassname.this.end(); return this; } - public $typemap(jboxtype, T) next() { + public $typemap(jboxtype, Key) next() { if (!hasNext()) { throw new java.util.NoSuchElementException(); } // Save the current position, increment it, // then return the value at the position before the increment. - final $typemap(jboxtype, T) currValue = curr.derefUnchecked(); + final $typemap(jboxtype, Key) currValue = curr.derefUnchecked(); curr.incrementUnchecked(); return currValue; } @@ -106,11 +106,11 @@ class unordered_set { } public boolean contains(java.lang.Object object) { - if (!(object instanceof $typemap(jboxtype, T))) { + if (!(object instanceof $typemap(jboxtype, Key))) { return false; } - return containsImpl(($typemap(jboxtype, T))object); + return containsImpl(($typemap(jboxtype, Key))object); } public boolean removeAll(java.util.Collection collection) { @@ -123,11 +123,11 @@ class unordered_set { } public boolean remove(java.lang.Object object) { - if (!(object instanceof $typemap(jboxtype, T))) { + if (!(object instanceof $typemap(jboxtype, Key))) { return false; } - return removeImpl(($typemap(jboxtype, T))object); + return removeImpl(($typemap(jboxtype, Key))object); } %} @@ -140,7 +140,7 @@ class unordered_set { ++(*$self); } - T derefUnchecked() const { + Key derefUnchecked() const { return **$self; } @@ -152,8 +152,8 @@ class unordered_set { typedef size_t size_type; typedef ptrdiff_t difference_type; - typedef T value_type; - typedef T key_type; + typedef Key value_type; + typedef Key key_type; typedef value_type* pointer; typedef const value_type* const_pointer; typedef value_type& reference; @@ -172,17 +172,17 @@ class unordered_set { %fragment("SWIG_UnorderedSetSize"); // Returns whether item was inserted. - bool add(const T& key) { + bool add(const Key& key) { return self->insert(key).second; } // Returns whether set contains key. - bool containsImpl(const T& key) { + bool containsImpl(const Key& key) { return (self->count(key) > 0); } // Returns whether the item was erased. - bool removeImpl(const T& key) { + bool removeImpl(const Key& key) { return (self->erase(key) > 0); } diff --git a/Lib/python/std_unordered_multiset.i b/Lib/python/std_unordered_multiset.i index d90a97bdc..4b67c7305 100644 --- a/Lib/python/std_unordered_multiset.i +++ b/Lib/python/std_unordered_multiset.i @@ -7,9 +7,9 @@ %fragment("StdUnorderedMultisetTraits","header",fragment="StdSequenceTraits") %{ namespace swig { - template + template inline void - assign(const SwigPySeq& swigpyseq, std::unordered_multiset* seq) { + assign(const SwigPySeq& swigpyseq, std::unordered_multiset* seq) { // seq->insert(swigpyseq.begin(), swigpyseq.end()); // not used as not always implemented typedef typename SwigPySeq::value_type value_type; typename SwigPySeq::const_iterator it = swigpyseq.begin(); @@ -18,24 +18,24 @@ } } - template - struct traits_reserve > { - static void reserve(std::unordered_multiset &seq, typename std::unordered_multiset::size_type n) { + template + struct traits_reserve > { + static void reserve(std::unordered_multiset &seq, typename std::unordered_multiset::size_type n) { seq.reserve(n); } }; - template - struct traits_asptr > { - static int asptr(PyObject *obj, std::unordered_multiset **m) { - return traits_asptr_stdseq >::asptr(obj, m); + template + struct traits_asptr > { + static int asptr(PyObject *obj, std::unordered_multiset **m) { + return traits_asptr_stdseq >::asptr(obj, m); } }; - template - struct traits_from > { - static PyObject *from(const std::unordered_multiset& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static PyObject *from(const std::unordered_multiset& vec) { + return traits_from_stdseq >::from(vec); } }; } diff --git a/Lib/python/std_unordered_set.i b/Lib/python/std_unordered_set.i index 8736cb1b5..9eab62226 100644 --- a/Lib/python/std_unordered_set.i +++ b/Lib/python/std_unordered_set.i @@ -5,9 +5,9 @@ %fragment("StdUnorderedSetTraits","header",fragment="StdSequenceTraits") %{ namespace swig { - template + template inline void - assign(const SwigPySeq& swigpyseq, std::unordered_set* seq) { + assign(const SwigPySeq& swigpyseq, std::unordered_set* seq) { // seq->insert(swigpyseq.begin(), swigpyseq.end()); // not used as not always implemented typedef typename SwigPySeq::value_type value_type; typename SwigPySeq::const_iterator it = swigpyseq.begin(); @@ -16,24 +16,24 @@ } } - template - struct traits_reserve > { - static void reserve(std::unordered_set &seq, typename std::unordered_set::size_type n) { + template + struct traits_reserve > { + static void reserve(std::unordered_set &seq, typename std::unordered_set::size_type n) { seq.reserve(n); } }; - template - struct traits_asptr > { - static int asptr(PyObject *obj, std::unordered_set **s) { - return traits_asptr_stdseq >::asptr(obj, s); + template + struct traits_asptr > { + static int asptr(PyObject *obj, std::unordered_set **s) { + return traits_asptr_stdseq >::asptr(obj, s); } }; - template - struct traits_from > { - static PyObject *from(const std::unordered_set& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static PyObject *from(const std::unordered_set& vec) { + return traits_from_stdseq >::from(vec); } }; } diff --git a/Lib/ruby/std_unordered_multiset.i b/Lib/ruby/std_unordered_multiset.i index 181aa212d..4bc13790a 100644 --- a/Lib/ruby/std_unordered_multiset.i +++ b/Lib/ruby/std_unordered_multiset.i @@ -7,9 +7,9 @@ %fragment("StdUnorderedMultisetTraits","header",fragment="StdUnorderedSetTraits") %{ namespace swig { - template + template inline void - assign(const RubySeq& rubyseq, std::unordered_multiset* seq) { + assign(const RubySeq& rubyseq, std::unordered_multiset* seq) { // seq->insert(rubyseq.begin(), rubyseq.end()); // not used as not always implemented typedef typename RubySeq::value_type value_type; typename RubySeq::const_iterator it = rubyseq.begin(); @@ -18,17 +18,17 @@ } } - template - struct traits_asptr > { - static int asptr(VALUE obj, std::unordered_multiset **m) { - return traits_asptr_stdseq >::asptr(obj, m); + template + struct traits_asptr > { + static int asptr(VALUE obj, std::unordered_multiset **m) { + return traits_asptr_stdseq >::asptr(obj, m); } }; - template - struct traits_from > { - static VALUE from(const std::unordered_multiset& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static VALUE from(const std::unordered_multiset& vec) { + return traits_from_stdseq >::from(vec); } }; } diff --git a/Lib/ruby/std_unordered_set.i b/Lib/ruby/std_unordered_set.i index 3d4494351..84d3b4b09 100644 --- a/Lib/ruby/std_unordered_set.i +++ b/Lib/ruby/std_unordered_set.i @@ -7,9 +7,9 @@ %fragment("StdUnorderedSetTraits","header",fragment="",fragment="StdSetTraits") %{ namespace swig { - template + template inline void - assign(const RubySeq& rubyseq, std::unordered_set* seq) { + assign(const RubySeq& rubyseq, std::unordered_set* seq) { // seq->insert(rubyseq.begin(), rubyseq.end()); // not used as not always implemented typedef typename RubySeq::value_type value_type; typename RubySeq::const_iterator it = rubyseq.begin(); @@ -18,17 +18,17 @@ } } - template - struct traits_asptr > { - static int asptr(VALUE obj, std::unordered_set **s) { - return traits_asptr_stdseq >::asptr(obj, s); + template + struct traits_asptr > { + static int asptr(VALUE obj, std::unordered_set **s) { + return traits_asptr_stdseq >::asptr(obj, s); } }; - template - struct traits_from > { - static VALUE from(const std::unordered_set& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static VALUE from(const std::unordered_set& vec) { + return traits_from_stdseq >::from(vec); } }; } diff --git a/Lib/std/std_unordered_multiset.i b/Lib/std/std_unordered_multiset.i index 1817fc24a..8effa586e 100644 --- a/Lib/std/std_unordered_multiset.i +++ b/Lib/std/std_unordered_multiset.i @@ -17,19 +17,19 @@ // const declarations are used to guess the intent of the function being // exported; therefore, the following rationale is applied: // -// -- f(std::unordered_multiset), f(const std::unordered_multiset&): +// -- f(std::unordered_multiset), f(const std::unordered_multiset&): // the parameter being read-only, either a sequence or a -// previously wrapped std::unordered_multiset can be passed. -// -- f(std::unordered_multiset&), f(std::unordered_multiset*): +// previously wrapped std::unordered_multiset can be passed. +// -- f(std::unordered_multiset&), f(std::unordered_multiset*): // the parameter may be modified; therefore, only a wrapped std::unordered_multiset // can be passed. -// -- std::unordered_multiset f(), const std::unordered_multiset& f(): -// the set is returned by copy; therefore, a sequence of T:s +// -- std::unordered_multiset f(), const std::unordered_multiset& f(): +// the set is returned by copy; therefore, a sequence of Key:s // is returned which is most easily used in other functions -// -- std::unordered_multiset& f(), std::unordered_multiset* f(): +// -- std::unordered_multiset& f(), std::unordered_multiset* f(): // the set is returned by reference; therefore, a wrapped std::unordered_multiset // is returned -// -- const std::unordered_multiset* f(), f(const std::unordered_multiset*): +// -- const std::unordered_multiset* f(), f(const std::unordered_multiset*): // for consistency, they expect and return a plain set pointer. // ------------------------------------------------------------------------ diff --git a/Lib/std/std_unordered_set.i b/Lib/std/std_unordered_set.i index 133246da8..d7fc24a22 100644 --- a/Lib/std/std_unordered_set.i +++ b/Lib/std/std_unordered_set.i @@ -50,19 +50,19 @@ // const declarations are used to guess the intent of the function being // exported; therefore, the following rationale is applied: // -// -- f(std::unordered_set), f(const std::unordered_set&): +// -- f(std::unordered_set), f(const std::unordered_set&): // the parameter being read-only, either a sequence or a -// previously wrapped std::unordered_set can be passed. -// -- f(std::unordered_set&), f(std::unordered_set*): +// previously wrapped std::unordered_set can be passed. +// -- f(std::unordered_set&), f(std::unordered_set*): // the parameter may be modified; therefore, only a wrapped std::unordered_set // can be passed. -// -- std::unordered_set f(), const std::unordered_set& f(): -// the unordered_set is returned by copy; therefore, a sequence of T:s +// -- std::unordered_set f(), const std::unordered_set& f(): +// the unordered_set is returned by copy; therefore, a sequence of Key:s // is returned which is most easily used in other functions -// -- std::unordered_set& f(), std::unordered_set* f(): +// -- std::unordered_set& f(), std::unordered_set* f(): // the unordered_set is returned by reference; therefore, a wrapped std::unordered_set // is returned -// -- const std::unordered_set* f(), f(const std::unordered_set*): +// -- const std::unordered_set* f(), f(const std::unordered_set*): // for consistency, they expect and return a plain unordered_set pointer. // ------------------------------------------------------------------------ From f3e2ab91950f6b8e4ef387a9a3ea34f44bd3907b Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 12 Mar 2019 21:47:45 +0000 Subject: [PATCH 049/134] Include all template parameters for std_unordered_multiset and std_unordered_set --- Lib/python/std_unordered_multiset.i | 26 +++++++++++++------------- Lib/python/std_unordered_set.i | 26 +++++++++++++------------- Lib/ruby/std_unordered_multiset.i | 20 ++++++++++---------- Lib/ruby/std_unordered_set.i | 20 ++++++++++---------- 4 files changed, 46 insertions(+), 46 deletions(-) diff --git a/Lib/python/std_unordered_multiset.i b/Lib/python/std_unordered_multiset.i index 4b67c7305..b0f3f096b 100644 --- a/Lib/python/std_unordered_multiset.i +++ b/Lib/python/std_unordered_multiset.i @@ -7,9 +7,9 @@ %fragment("StdUnorderedMultisetTraits","header",fragment="StdSequenceTraits") %{ namespace swig { - template + template inline void - assign(const SwigPySeq& swigpyseq, std::unordered_multiset* seq) { + assign(const SwigPySeq& swigpyseq, std::unordered_multiset* seq) { // seq->insert(swigpyseq.begin(), swigpyseq.end()); // not used as not always implemented typedef typename SwigPySeq::value_type value_type; typename SwigPySeq::const_iterator it = swigpyseq.begin(); @@ -18,24 +18,24 @@ } } - template - struct traits_reserve > { - static void reserve(std::unordered_multiset &seq, typename std::unordered_multiset::size_type n) { + template + struct traits_reserve > { + static void reserve(std::unordered_multiset &seq, typename std::unordered_multiset::size_type n) { seq.reserve(n); } }; - template - struct traits_asptr > { - static int asptr(PyObject *obj, std::unordered_multiset **m) { - return traits_asptr_stdseq >::asptr(obj, m); + template + struct traits_asptr > { + static int asptr(PyObject *obj, std::unordered_multiset **m) { + return traits_asptr_stdseq >::asptr(obj, m); } }; - template - struct traits_from > { - static PyObject *from(const std::unordered_multiset& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static PyObject *from(const std::unordered_multiset& vec) { + return traits_from_stdseq >::from(vec); } }; } diff --git a/Lib/python/std_unordered_set.i b/Lib/python/std_unordered_set.i index 9eab62226..79fca6c2f 100644 --- a/Lib/python/std_unordered_set.i +++ b/Lib/python/std_unordered_set.i @@ -5,9 +5,9 @@ %fragment("StdUnorderedSetTraits","header",fragment="StdSequenceTraits") %{ namespace swig { - template + template inline void - assign(const SwigPySeq& swigpyseq, std::unordered_set* seq) { + assign(const SwigPySeq& swigpyseq, std::unordered_set* seq) { // seq->insert(swigpyseq.begin(), swigpyseq.end()); // not used as not always implemented typedef typename SwigPySeq::value_type value_type; typename SwigPySeq::const_iterator it = swigpyseq.begin(); @@ -16,24 +16,24 @@ } } - template - struct traits_reserve > { - static void reserve(std::unordered_set &seq, typename std::unordered_set::size_type n) { + template + struct traits_reserve > { + static void reserve(std::unordered_set &seq, typename std::unordered_set::size_type n) { seq.reserve(n); } }; - template - struct traits_asptr > { - static int asptr(PyObject *obj, std::unordered_set **s) { - return traits_asptr_stdseq >::asptr(obj, s); + template + struct traits_asptr > { + static int asptr(PyObject *obj, std::unordered_set **s) { + return traits_asptr_stdseq >::asptr(obj, s); } }; - template - struct traits_from > { - static PyObject *from(const std::unordered_set& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static PyObject *from(const std::unordered_set& vec) { + return traits_from_stdseq >::from(vec); } }; } diff --git a/Lib/ruby/std_unordered_multiset.i b/Lib/ruby/std_unordered_multiset.i index 4bc13790a..dae13eef3 100644 --- a/Lib/ruby/std_unordered_multiset.i +++ b/Lib/ruby/std_unordered_multiset.i @@ -7,9 +7,9 @@ %fragment("StdUnorderedMultisetTraits","header",fragment="StdUnorderedSetTraits") %{ namespace swig { - template + template inline void - assign(const RubySeq& rubyseq, std::unordered_multiset* seq) { + assign(const RubySeq& rubyseq, std::unordered_multiset* seq) { // seq->insert(rubyseq.begin(), rubyseq.end()); // not used as not always implemented typedef typename RubySeq::value_type value_type; typename RubySeq::const_iterator it = rubyseq.begin(); @@ -18,17 +18,17 @@ } } - template - struct traits_asptr > { - static int asptr(VALUE obj, std::unordered_multiset **m) { - return traits_asptr_stdseq >::asptr(obj, m); + template + struct traits_asptr > { + static int asptr(VALUE obj, std::unordered_multiset **m) { + return traits_asptr_stdseq >::asptr(obj, m); } }; - template - struct traits_from > { - static VALUE from(const std::unordered_multiset& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static VALUE from(const std::unordered_multiset& vec) { + return traits_from_stdseq >::from(vec); } }; } diff --git a/Lib/ruby/std_unordered_set.i b/Lib/ruby/std_unordered_set.i index 84d3b4b09..e8e1b0872 100644 --- a/Lib/ruby/std_unordered_set.i +++ b/Lib/ruby/std_unordered_set.i @@ -7,9 +7,9 @@ %fragment("StdUnorderedSetTraits","header",fragment="",fragment="StdSetTraits") %{ namespace swig { - template + template inline void - assign(const RubySeq& rubyseq, std::unordered_set* seq) { + assign(const RubySeq& rubyseq, std::unordered_set* seq) { // seq->insert(rubyseq.begin(), rubyseq.end()); // not used as not always implemented typedef typename RubySeq::value_type value_type; typename RubySeq::const_iterator it = rubyseq.begin(); @@ -18,17 +18,17 @@ } } - template - struct traits_asptr > { - static int asptr(VALUE obj, std::unordered_set **s) { - return traits_asptr_stdseq >::asptr(obj, s); + template + struct traits_asptr > { + static int asptr(VALUE obj, std::unordered_set **s) { + return traits_asptr_stdseq >::asptr(obj, s); } }; - template - struct traits_from > { - static VALUE from(const std::unordered_set& vec) { - return traits_from_stdseq >::from(vec); + template + struct traits_from > { + static VALUE from(const std::unordered_set& vec) { + return traits_from_stdseq >::from(vec); } }; } From f58a6dade3b0c13626af271d3d054dc6076d8e0d Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 12 Mar 2019 21:59:03 +0000 Subject: [PATCH 050/134] Add missing hasher and key_type typedefs to C++11 STL containers --- Lib/std/std_unordered_map.i | 2 ++ Lib/std/std_unordered_multimap.i | 2 ++ Lib/std/std_unordered_multiset.i | 7 +++++-- Lib/std/std_unordered_set.i | 8 +++++--- 4 files changed, 14 insertions(+), 5 deletions(-) diff --git a/Lib/std/std_unordered_map.i b/Lib/std/std_unordered_map.i index 723c0232d..1fd1eb980 100644 --- a/Lib/std/std_unordered_map.i +++ b/Lib/std/std_unordered_map.i @@ -75,6 +75,8 @@ namespace std { typedef const value_type* const_pointer; typedef value_type& reference; typedef const value_type& const_reference; + typedef _Hash hasher; + typedef _Compare key_equal; typedef _Alloc allocator_type; %traits_swigtype(_Key); diff --git a/Lib/std/std_unordered_multimap.i b/Lib/std/std_unordered_multimap.i index f2855343d..4be6aa492 100644 --- a/Lib/std/std_unordered_multimap.i +++ b/Lib/std/std_unordered_multimap.i @@ -53,6 +53,8 @@ namespace std { typedef const value_type* const_pointer; typedef value_type& reference; typedef const value_type& const_reference; + typedef _Hash hasher; + typedef _Compare key_equal; typedef _Alloc allocator_type; %traits_swigtype(_Key); diff --git a/Lib/std/std_unordered_multiset.i b/Lib/std/std_unordered_multiset.i index 8effa586e..2910fb6ff 100644 --- a/Lib/std/std_unordered_multiset.i +++ b/Lib/std/std_unordered_multiset.i @@ -40,9 +40,10 @@ namespace std { //unordered_multiset - template , + template , class _Compare = std::equal_to< _Key >, - class _Alloc = allocator< _Key > > + class _Alloc = allocator< _Key > > class unordered_multiset { public: typedef size_t size_type; @@ -53,6 +54,8 @@ namespace std { typedef const value_type* const_pointer; typedef value_type& reference; typedef const value_type& const_reference; + typedef _Hash hasher; + typedef _Compare key_equal; typedef _Alloc allocator_type; %traits_swigtype(_Key); diff --git a/Lib/std/std_unordered_set.i b/Lib/std/std_unordered_set.i index d7fc24a22..91e807423 100644 --- a/Lib/std/std_unordered_set.i +++ b/Lib/std/std_unordered_set.i @@ -74,20 +74,22 @@ namespace std { - template , + template , class _Compare = std::equal_to< _Key >, - class _Alloc = allocator< _Key > > + class _Alloc = allocator< _Key > > class unordered_set { public: typedef size_t size_type; typedef ptrdiff_t difference_type; - typedef _Hash hasher; typedef _Key value_type; typedef _Key key_type; typedef value_type* pointer; typedef const value_type* const_pointer; typedef value_type& reference; typedef const value_type& const_reference; + typedef _Hash hasher; + typedef _Compare key_equal; typedef _Alloc allocator_type; %traits_swigtype(_Key); From d3ae85ee734ec701cea0f67f0ccf3d187199819c Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 12 Mar 2019 22:47:11 +0000 Subject: [PATCH 051/134] Cosmetic tweaks for C# std::set support --- CHANGES.current | 2 +- Lib/java/std_set.i | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 3765a8273..9e74e767e 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -8,7 +8,7 @@ Version 4.0.0 (in progress) =========================== 2019-03-12: vadz - [C#] Add std::set<> typemaps. + [C#] #1495 Add std_set.i for std::set support. 2019-03-11: dirteat,opoplawski [Octave] Fix compilation errors in Octave 5.1. diff --git a/Lib/java/std_set.i b/Lib/java/std_set.i index 086d10c8a..04658f765 100644 --- a/Lib/java/std_set.i +++ b/Lib/java/std_set.i @@ -152,8 +152,8 @@ class set { typedef size_t size_type; typedef ptrdiff_t difference_type; - typedef T value_type; typedef T key_type; + typedef T value_type; typedef value_type* pointer; typedef const value_type* const_pointer; typedef value_type& reference; From 1e981dfc238cd255a5dc4ccdabf0803671607d2f Mon Sep 17 00:00:00 2001 From: mochizk Date: Wed, 13 Mar 2019 21:43:21 +0900 Subject: [PATCH 052/134] Fix node.js deprecated warnings >= v10.12.0 --- .travis.yml | 6 ---- Lib/javascript/v8/javascripthelpers.swg | 2 +- Lib/javascript/v8/javascriptprimtypes.swg | 14 ++++----- Lib/javascript/v8/javascriptrun.swg | 36 +++++++++++++++++++---- Lib/javascript/v8/javascriptruntime.swg | 2 ++ Lib/javascript/v8/javascriptstrings.swg | 8 ++--- 6 files changed, 45 insertions(+), 23 deletions(-) diff --git a/.travis.yml b/.travis.yml index b443ae07a..78d8883b5 100644 --- a/.travis.yml +++ b/.travis.yml @@ -377,12 +377,6 @@ matrix: env: SWIGLANG=tcl allow_failures: - # Deprecated functions causing build failure since upgrade from Node v10.11.0 to v10.12.0 - - compiler: gcc - os: linux - env: SWIGLANG=javascript ENGINE=node VER=10 CPP11=1 - sudo: required - dist: trusty # Sometimes hits the Travis 50 minute time limit - compiler: gcc os: linux diff --git a/Lib/javascript/v8/javascripthelpers.swg b/Lib/javascript/v8/javascripthelpers.swg index 7b8a5ec23..80fbd7aa1 100644 --- a/Lib/javascript/v8/javascripthelpers.swg +++ b/Lib/javascript/v8/javascripthelpers.swg @@ -93,7 +93,7 @@ SWIGRUNTIME void JS_veto_set_variable(v8::Local property, v8::Local sproperty; if (property->ToString(SWIGV8_CURRENT_CONTEXT()).ToLocal(&sproperty)) { - sproperty->WriteUtf8(buffer, 256); + SWIGV8_WRITE_UTF8(sproperty, buffer, 256); res = sprintf(msg, "Tried to write read-only variable: %s.", buffer); } else { diff --git a/Lib/javascript/v8/javascriptprimtypes.swg b/Lib/javascript/v8/javascriptprimtypes.swg index c0055c48e..f76be983b 100644 --- a/Lib/javascript/v8/javascriptprimtypes.swg +++ b/Lib/javascript/v8/javascriptprimtypes.swg @@ -22,7 +22,7 @@ int SWIG_AsVal_dec(bool)(v8::Handle obj, bool *val) return SWIG_ERROR; } - if (val) *val = obj->BooleanValue(); + if (val) *val = SWIGV8_BOOLEAN_VALUE(obj); return SWIG_OK; } } @@ -44,7 +44,7 @@ int SWIG_AsVal_dec(int)(v8::Handle valRef, int* val) if (!valRef->IsNumber()) { return SWIG_TypeError; } - if(val) *val = valRef->IntegerValue(); + if(val) *val = SWIGV8_INTEGER_VALUE(valRef); return SWIG_OK; } @@ -68,7 +68,7 @@ int SWIG_AsVal_dec(long)(v8::Handle obj, long* val) if (!obj->IsNumber()) { return SWIG_TypeError; } - if(val) *val = (long) obj->IntegerValue(); + if(val) *val = (long) SWIGV8_INTEGER_VALUE(obj); return SWIG_OK; } @@ -95,7 +95,7 @@ int SWIG_AsVal_dec(unsigned long)(v8::Handle obj, unsigned long *val) return SWIG_TypeError; } - long longVal = (long) obj->NumberValue(); + long longVal = (long) SWIGV8_NUMBER_VALUE(obj); if(longVal < 0) { return SWIG_OverflowError; @@ -133,7 +133,7 @@ int SWIG_AsVal_dec(long long)(v8::Handle obj, long long* val) if (!obj->IsNumber()) { return SWIG_TypeError; } - if(val) *val = (long long) obj->IntegerValue(); + if(val) *val = (long long) SWIGV8_INTEGER_VALUE(obj); return SWIG_OK; } @@ -168,7 +168,7 @@ int SWIG_AsVal_dec(unsigned long long)(v8::Handle obj, unsigned long return SWIG_TypeError; } - long long longVal = (long long) obj->NumberValue(); + long long longVal = (long long) SWIGV8_NUMBER_VALUE(obj); if(longVal < 0) { return SWIG_OverflowError; @@ -198,7 +198,7 @@ int SWIG_AsVal_dec(double)(v8::Handle obj, double *val) if(!obj->IsNumber()) { return SWIG_TypeError; } - if(val) *val = obj->NumberValue(); + if(val) *val = SWIGV8_NUMBER_VALUE(obj); return SWIG_OK; } diff --git a/Lib/javascript/v8/javascriptrun.swg b/Lib/javascript/v8/javascriptrun.swg index 84bd4cc67..2452f4040 100644 --- a/Lib/javascript/v8/javascriptrun.swg +++ b/Lib/javascript/v8/javascriptrun.swg @@ -91,6 +91,32 @@ typedef v8::PropertyCallbackInfo SwigV8PropertyCallbackInfo; #define SWIGV8_SET_CLASS_TEMPL(class_templ, class) class_templ.Reset(v8::Isolate::GetCurrent(), class); #endif +#ifdef NODE_VERSION +#if NODE_VERSION_AT_LEAST(10, 12, 0) +#define SWIG_NODE_AT_LEAST_1012 +#endif +#endif + +//Necessary to check Node.js version because V8 API changes are backported in Node.js +#if (defined(NODE_VERSION) && !defined(SWIG_NODE_AT_LEAST_1012)) || \ + (!defined(NODE_VERSION) && (V8_MAJOR_VERSION-0) < 7) +#define SWIGV8_TO_OBJECT(handle) (handle)->ToObject() +#define SWIGV8_TO_STRING(handle) (handle)->ToString() +#define SWIGV8_NUMBER_VALUE(handle) (handle)->NumberValue() +#define SWIGV8_INTEGER_VALUE(handle) (handle)->IntegerValue() +#define SWIGV8_BOOLEAN_VALUE(handle) (handle)->BooleanValue() +#define SWIGV8_WRITE_UTF8(handle, buffer, len) (handle)->WriteUtf8(buffer, len) +#define SWIGV8_UTF8_LENGTH(handle) (handle)->Utf8Length() +#else +#define SWIGV8_TO_OBJECT(handle) (handle)->ToObject(SWIGV8_CURRENT_CONTEXT()).ToLocalChecked() +#define SWIGV8_TO_STRING(handle) (handle)->ToString(SWIGV8_CURRENT_CONTEXT()).ToLocalChecked() +#define SWIGV8_NUMBER_VALUE(handle) (handle)->NumberValue(SWIGV8_CURRENT_CONTEXT()).ToChecked() +#define SWIGV8_INTEGER_VALUE(handle) (handle)->IntegerValue(SWIGV8_CURRENT_CONTEXT()).ToChecked() +#define SWIGV8_BOOLEAN_VALUE(handle) (handle)->BooleanValue(SWIGV8_CURRENT_CONTEXT()).ToChecked() +#define SWIGV8_WRITE_UTF8(handle, buffer, len) (handle)->WriteUtf8(v8::Isolate::GetCurrent(), buffer, len) +#define SWIGV8_UTF8_LENGTH(handle) (handle)->Utf8Length(v8::Isolate::GetCurrent()) +#endif + /* --------------------------------------------------------------------------- * Error handling * @@ -258,7 +284,7 @@ SWIGRUNTIME int SWIG_V8_GetInstancePtr(v8::Handle valRef, void **ptr) if(!valRef->IsObject()) { return SWIG_TypeError; } - v8::Handle objRef = valRef->ToObject(); + v8::Handle objRef = SWIGV8_TO_OBJECT(valRef); if(objRef->InternalFieldCount() < 1) return SWIG_ERROR; @@ -352,7 +378,7 @@ SWIGRUNTIME int SWIG_V8_ConvertPtr(v8::Handle valRef, void **ptr, swi if(!valRef->IsObject()) { return SWIG_TypeError; } - v8::Handle objRef = valRef->ToObject(); + v8::Handle objRef = SWIGV8_TO_OBJECT(valRef); return SWIG_V8_ConvertInstancePtr(objRef, ptr, info, flags); } @@ -479,7 +505,7 @@ SWIGRUNTIMEINLINE int SwigV8Packed_Check(v8::Handle valRef) { SWIGV8_HANDLESCOPE(); - v8::Handle objRef = valRef->ToObject(); + v8::Handle objRef = SWIGV8_TO_OBJECT(valRef); if(objRef->InternalFieldCount() < 1) return false; #if (V8_MAJOR_VERSION-0) < 5 v8::Handle flag = objRef->GetHiddenValue(SWIGV8_STRING_NEW("__swig__packed_data__")); @@ -489,7 +515,7 @@ int SwigV8Packed_Check(v8::Handle valRef) { if (!objRef->GetPrivate(SWIGV8_CURRENT_CONTEXT(), privateKey).ToLocal(&flag)) return false; #endif - return (flag->IsBoolean() && flag->BooleanValue()); + return (flag->IsBoolean() && SWIGV8_BOOLEAN_VALUE(flag)); } SWIGRUNTIME @@ -499,7 +525,7 @@ swig_type_info *SwigV8Packed_UnpackData(v8::Handle valRef, void *ptr, SwigV8PackedData *sobj; - v8::Handle objRef = valRef->ToObject(); + v8::Handle objRef = SWIGV8_TO_OBJECT(valRef); #if (V8_MAJOR_VERSION-0) < 4 && (SWIG_V8_VERSION < 0x031511) v8::Handle cdataRef = objRef->GetInternalField(0); diff --git a/Lib/javascript/v8/javascriptruntime.swg b/Lib/javascript/v8/javascriptruntime.swg index 0e4059326..c78e04efb 100644 --- a/Lib/javascript/v8/javascriptruntime.swg +++ b/Lib/javascript/v8/javascriptruntime.swg @@ -44,6 +44,8 @@ #ifdef BUILDING_NODE_EXTENSION %insert("runtime") %{ #include +//Older version of node.h does not include this +#include %} #endif diff --git a/Lib/javascript/v8/javascriptstrings.swg b/Lib/javascript/v8/javascriptstrings.swg index 65ba20e5a..e767a6d66 100644 --- a/Lib/javascript/v8/javascriptstrings.swg +++ b/Lib/javascript/v8/javascriptstrings.swg @@ -7,11 +7,11 @@ SWIGINTERN int SWIG_AsCharPtrAndSize(v8::Handle valRef, char** cptr, size_t* psize, int *alloc) { if(valRef->IsString()) { - v8::Handle js_str = valRef->ToString(); + v8::Handle js_str = SWIGV8_TO_STRING(valRef); - size_t len = js_str->Utf8Length() + 1; + size_t len = SWIGV8_UTF8_LENGTH(js_str) + 1; char* cstr = new char[len]; - js_str->WriteUtf8(cstr, len); + SWIGV8_WRITE_UTF8(js_str, cstr, len); if(alloc) *alloc = SWIG_NEWOBJ; if(psize) *psize = len; @@ -20,7 +20,7 @@ SWIG_AsCharPtrAndSize(v8::Handle valRef, char** cptr, size_t* psize, return SWIG_OK; } else { if(valRef->IsObject()) { - v8::Handle obj = valRef->ToObject(); + v8::Handle obj = SWIGV8_TO_OBJECT(valRef); // try if the object is a wrapped char[] swig_type_info* pchar_descriptor = SWIG_pchar_descriptor(); if (pchar_descriptor) { From 39d67aea8ea07bcd2744ff74e9fc82218561cd15 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 14 Mar 2019 20:32:42 +0000 Subject: [PATCH 053/134] Add changes entry for Node V8 api changes --- CHANGES.current | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 9e74e767e..3983829de 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,10 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-03-14: mochizk + [Javascript] #1500 Fix compilation errors due to deprecating V8 API in Node.js. + New V8 API is used if node.js >= v10.12, or if V8 >= v7.0. + 2019-03-12: vadz [C#] #1495 Add std_set.i for std::set support. From e60670ec45d64e2aac922c5e52b826204064e6f7 Mon Sep 17 00:00:00 2001 From: Richard Beare Date: Mon, 18 Mar 2019 21:33:25 +1100 Subject: [PATCH 054/134] extra doc on anonymous enums --- Doc/Manual/R.html | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/Doc/Manual/R.html b/Doc/Manual/R.html index 9fa27274b..9ca39c99f 100644 --- a/Doc/Manual/R.html +++ b/Doc/Manual/R.html @@ -227,7 +227,9 @@ and integers. The relevant functions, for debugging purposes, are enumToInteger and enumFromInteger. -Anonymous enumerations are not supported. +Anonymous enumerations are ignored by the binding generation process, +leaving no way of accessing the value of anonymous enumerations from R +code.

    From f5b53683f09aba885af2a48afdda073b3024219a Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 15 Mar 2019 07:51:45 +0000 Subject: [PATCH 055/134] Remove unused code in r.cxx --- Source/Modules/r.cxx | 12 ------------ 1 file changed, 12 deletions(-) diff --git a/Source/Modules/r.cxx b/Source/Modules/r.cxx index fde583ed6..bb43dad48 100644 --- a/Source/Modules/r.cxx +++ b/Source/Modules/r.cxx @@ -226,18 +226,6 @@ static void replaceRClass(String *tm, SwigType *type) { Delete(tmp); Delete(tmp_base); Delete(tmp_ref); } -static bool getNumber(String *value, int* result) { - if(Char(value)) { - // Check the conversion processed the whole of value by having %c at - // the end of the format, and checking that only the first value is - // converted. We don't want to convert "3+7" -> 3. - char dummy; - if (sscanf(Char(value), "%i%c", result, &dummy) == 1) - return true; - } - return false; -} - class R : public Language { public: R(); From 39e3c3b9d774a483fbec8f0fcf6c136833a79bf8 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 18 Mar 2019 17:49:24 +0000 Subject: [PATCH 056/134] Fix R return by C++11 const ref enum classes --- Lib/r/r.swg | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Lib/r/r.swg b/Lib/r/r.swg index e6153892e..8cf8cdf53 100644 --- a/Lib/r/r.swg +++ b/Lib/r/r.swg @@ -196,7 +196,7 @@ unsigned char *OUTPUT %{ temp = ($*1_ltype)INTEGER($input)[0]; $1 = &temp; %} -%typemap(out) const enum SWIGTYPE & %{ $result = Rf_ScalarInteger(*$1); %} +%typemap(out) const enum SWIGTYPE & %{ $result = Rf_ScalarInteger((int)*$1); %} %typemap(memberin) char[] %{ if ($input) strcpy($1, $input); From b2365f119e91eae698c29f3b8212510a40b9bb68 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 18 Mar 2019 18:10:20 +0000 Subject: [PATCH 057/134] Add changes entry for R enum fixes --- CHANGES.current | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 3983829de..5022e3097 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,10 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-03-18: richardbeare + [R] #1328 Non-trivial enums are working now. The enum values are now obtained from + the C/C++ layer. const reference enums and C++11 enum classes are also now working. + 2019-03-14: mochizk [Javascript] #1500 Fix compilation errors due to deprecating V8 API in Node.js. New V8 API is used if node.js >= v10.12, or if V8 >= v7.0. From 1fa2d85dc0a02dbe88241f35923fe0ff998772f3 Mon Sep 17 00:00:00 2001 From: Zackery Spytz Date: Tue, 19 Mar 2019 16:23:56 -0600 Subject: [PATCH 058/134] [OCaml] Fix race conds when running the examples with parallel make Race conditions could occur when running the examples with parallel make. --- Examples/ocaml/shapes/Makefile | 2 +- Examples/ocaml/string_from_ptr/Makefile | 2 +- Examples/ocaml/strings_test/Makefile | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Examples/ocaml/shapes/Makefile b/Examples/ocaml/shapes/Makefile index bc269d6d0..a9932793b 100644 --- a/Examples/ocaml/shapes/Makefile +++ b/Examples/ocaml/shapes/Makefile @@ -20,7 +20,7 @@ static: PROGFILE='$(PROGFILE)' OBJS='$(OBJS)' \ ocaml_static_cpp -toplevel: +toplevel: static $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ SWIGOPT='$(SWIGOPT)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/string_from_ptr/Makefile b/Examples/ocaml/string_from_ptr/Makefile index 0d3163e36..6917e4638 100644 --- a/Examples/ocaml/string_from_ptr/Makefile +++ b/Examples/ocaml/string_from_ptr/Makefile @@ -19,7 +19,7 @@ static: PROGFILE='$(PROGFILE)' OBJS='$(OBJS)' \ ocaml_static -toplevel: +toplevel: static $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/strings_test/Makefile b/Examples/ocaml/strings_test/Makefile index bed86841b..9474f5364 100644 --- a/Examples/ocaml/strings_test/Makefile +++ b/Examples/ocaml/strings_test/Makefile @@ -23,7 +23,7 @@ dynamic: PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ ocaml_static_cpp -toplevel: +toplevel: static $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ From 2bb5eeef91c5d08ba5b631648015ab776620561e Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Wed, 20 Mar 2019 21:10:28 +0000 Subject: [PATCH 059/134] Improve Python static member variable testing Double check the values are being set in the C++ layer via a function call to C++ layer. --- Examples/test-suite/cpp_static.i | 3 +++ Examples/test-suite/python/cpp_static_runme.py | 12 ++++++++++++ 2 files changed, 15 insertions(+) diff --git a/Examples/test-suite/cpp_static.i b/Examples/test-suite/cpp_static.i index 1f8ca1282..9ffe55837 100644 --- a/Examples/test-suite/cpp_static.i +++ b/Examples/test-suite/cpp_static.i @@ -10,6 +10,7 @@ Tests Sourceforge bug #444748. class StaticMemberTest { public: static int static_int; + static int grab_int() { return static_int; } }; class StaticFunctionTest { @@ -28,10 +29,12 @@ int StaticMemberTest::static_int = 99; %inline %{ struct StaticBase { static int statty; + static int grab_statty_base() { return statty; } virtual ~StaticBase() {} }; struct StaticDerived : StaticBase { static int statty; + static int grab_statty_derived() { return statty; } }; %} diff --git a/Examples/test-suite/python/cpp_static_runme.py b/Examples/test-suite/python/cpp_static_runme.py index e8c8cf615..760fb6791 100644 --- a/Examples/test-suite/python/cpp_static_runme.py +++ b/Examples/test-suite/python/cpp_static_runme.py @@ -8,15 +8,21 @@ StaticFunctionTest.static_func_3(1, 2) if is_python_builtin(): if not StaticMemberTest.static_int == 99: raise RuntimeError("static_int not 99") + if not StaticMemberTest.grab_int() == 99: raise RuntimeError("static_int not 99") StaticMemberTest.static_int = 10 if not StaticMemberTest.static_int == 10: raise RuntimeError("static_int not 10") + if not StaticMemberTest.grab_int() == 10: raise RuntimeError("static_int not 10") if not StaticBase.statty == 11: raise RuntimeError("statty not 11") + if not StaticBase.grab_statty_base() == 11: raise RuntimeError("statty not 11") if not StaticDerived.statty == 111: raise RuntimeError("statty not 111") + if not StaticDerived.grab_statty_derived() == 111: raise RuntimeError("statty not 111") StaticBase.statty = 22 StaticDerived.statty = 222 if not StaticBase.statty == 22: raise RuntimeError("statty not 22") + if not StaticBase.grab_statty_base() == 22: raise RuntimeError("statty not 22") if not StaticDerived.statty == 222: raise RuntimeError("statty not 222") + if not StaticDerived.grab_statty_derived() == 222: raise RuntimeError("statty not 222") # Restore StaticMemberTest.static_int = 99 @@ -24,12 +30,18 @@ if is_python_builtin(): StaticDerived.statty = 111 if not cvar.StaticMemberTest_static_int == 99: raise RuntimeError("cvar static_int not 99") +if not StaticMemberTest.grab_int() == 99: raise RuntimeError("cvar static_int not 99") cvar.StaticMemberTest_static_int = 10 if not cvar.StaticMemberTest_static_int == 10: raise RuntimeError("cvar static_int not 10") +if not StaticMemberTest.grab_int() == 10: raise RuntimeError("cvar static_int not 10") if not cvar.StaticBase_statty == 11: raise RuntimeError("cvar statty not 11") +if not StaticBase.grab_statty_base() == 11: raise RuntimeError("cvar statty not 11") if not cvar.StaticDerived_statty == 111: raise RuntimeError("cvar statty not 111") +if not StaticDerived.grab_statty_derived() == 111: raise RuntimeError("cvar statty not 111") cvar.StaticBase_statty = 22 cvar.StaticDerived_statty = 222 if not cvar.StaticBase_statty == 22: raise RuntimeError("cvar statty not 22") +if not StaticBase.grab_statty_base() == 22: raise RuntimeError("cvar statty not 22") if not cvar.StaticDerived_statty == 222: raise RuntimeError("cvar statty not 222") +if not StaticDerived.grab_statty_derived() == 222: raise RuntimeError("cvar statty not 222") From 826f1448b838bc3efadf2f1cc93e614426e104dd Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Wed, 20 Mar 2019 21:44:34 +0000 Subject: [PATCH 060/134] Fix Python low-level static member setters. The low-level API for setting static member variables stopped working when the fastunpack option was turned on by default. The PyMethodDef setup requires METH_O, not METH_VARARGS with fastunpack. --- .../test-suite/python/cpp_static_runme.py | 25 +++++++++++++++++++ Source/Modules/python.cxx | 2 +- 2 files changed, 26 insertions(+), 1 deletion(-) diff --git a/Examples/test-suite/python/cpp_static_runme.py b/Examples/test-suite/python/cpp_static_runme.py index 760fb6791..cd7398fbb 100644 --- a/Examples/test-suite/python/cpp_static_runme.py +++ b/Examples/test-suite/python/cpp_static_runme.py @@ -45,3 +45,28 @@ if not cvar.StaticBase_statty == 22: raise RuntimeError("cvar statty not 22") if not StaticBase.grab_statty_base() == 22: raise RuntimeError("cvar statty not 22") if not cvar.StaticDerived_statty == 222: raise RuntimeError("cvar statty not 222") if not StaticDerived.grab_statty_derived() == 222: raise RuntimeError("cvar statty not 222") + +# Restore +cvar.StaticMemberTest_static_int = 99 +cvar.StaticBase_statty = 11 +cvar.StaticDerived_statty = 111 + +# Low-level layer testing +if not is_python_builtin(): + from cpp_static import _cpp_static + if not _cpp_static.StaticMemberTest_static_int_get() == 99: raise RuntimeError("low-level static_int not 99") + if not StaticMemberTest.grab_int() == 99: raise RuntimeError("low-level static_int not 99") + _cpp_static.StaticMemberTest_static_int_set(10) + if not _cpp_static.StaticMemberTest_static_int_get() == 10: raise RuntimeError("low-level static_int not 10") + if not StaticMemberTest.grab_int() == 10: raise RuntimeError("low-level static_int not 10") + + if not _cpp_static.StaticBase_statty_get() == 11: raise RuntimeError("low-level statty not 11") + if not StaticBase.grab_statty_base() == 11: raise RuntimeError("low-level statty not 11") + if not _cpp_static.StaticDerived_statty_get() == 111: raise RuntimeError("low-level statty not 111") + if not StaticDerived.grab_statty_derived() == 111: raise RuntimeError("low-level statty not 111") + _cpp_static.StaticBase_statty_set(22) + _cpp_static.StaticDerived_statty_set(222) + if not _cpp_static.StaticBase_statty_get() == 22: raise RuntimeError("low-level statty not 22") + if not StaticBase.grab_statty_base() == 22: raise RuntimeError("low-level statty not 22") + if not _cpp_static.StaticDerived_statty_get() == 222: raise RuntimeError("low-level statty not 222") + if not StaticDerived.grab_statty_derived() == 222: raise RuntimeError("low-level statty not 222") diff --git a/Source/Modules/python.cxx b/Source/Modules/python.cxx index 21392cc2e..7c9603a3d 100755 --- a/Source/Modules/python.cxx +++ b/Source/Modules/python.cxx @@ -2426,7 +2426,7 @@ public: void add_method(String *name, String *function, int kw, Node *n = 0, int funpack = 0, int num_required = -1, int num_arguments = -1) { String * meth_str = NewString(""); if (!kw) { - if (n && funpack) { + if (funpack) { if (num_required == 0 && num_arguments == 0) { Printf(meth_str, "\t { \"%s\", %s, METH_NOARGS, ", name, function); } else if (num_required == 1 && num_arguments == 1) { From 9f0b9da024696c19573f0566adceea277e36f0cd Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 21 Mar 2019 20:59:54 +0000 Subject: [PATCH 061/134] Always use fastunpack for Python swigregister function --- Source/Modules/python.cxx | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/Source/Modules/python.cxx b/Source/Modules/python.cxx index 7c9603a3d..9eb233e9e 100755 --- a/Source/Modules/python.cxx +++ b/Source/Modules/python.cxx @@ -4510,16 +4510,12 @@ public: } else { Printv(f_wrappers, "SWIGINTERN PyObject *", class_name, "_swigregister(PyObject *SWIGUNUSEDPARM(self), PyObject *args) {\n", NIL); Printv(f_wrappers, " PyObject *obj;\n", NIL); - if (fastunpack) { - Printv(f_wrappers, " if (!SWIG_Python_UnpackTuple(args, \"swigregister\", 1, 1, &obj)) return NULL;\n", NIL); - } else { - Printv(f_wrappers, " if (!PyArg_UnpackTuple(args, \"swigregister\", 1, 1, &obj)) return NULL;\n", NIL); - } + Printv(f_wrappers, " if (!SWIG_Python_UnpackTuple(args, \"swigregister\", 1, 1, &obj)) return NULL;\n", NIL); Printv(f_wrappers, " SWIG_TypeNewClientData(SWIGTYPE", SwigType_manglestr(ct), ", SWIG_NewClientData(obj));\n", " return SWIG_Py_Void();\n", "}\n\n", NIL); String *cname = NewStringf("%s_swigregister", class_name); - add_method(cname, cname, 0); + add_method(cname, cname, 0, 0, 1, 1, 1); Delete(cname); } Delete(smart); From 39599f2112004dc1aff1df8d1ff15ededbecdb4c Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 21 Mar 2019 21:17:21 +0000 Subject: [PATCH 062/134] Always use fastunpack for Python swigconstant wrappers --- Source/Modules/python.cxx | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/Source/Modules/python.cxx b/Source/Modules/python.cxx index 9eb233e9e..b8493352c 100755 --- a/Source/Modules/python.cxx +++ b/Source/Modules/python.cxx @@ -3592,11 +3592,7 @@ public: Printf(f_wrappers, "SWIGINTERN PyObject *%s_swigconstant(PyObject *SWIGUNUSEDPARM(self), PyObject *args) {\n", iname); Printf(f_wrappers, tab2 "PyObject *module;\n", tm); Printf(f_wrappers, tab2 "PyObject *d;\n"); - if (fastunpack) { - Printf(f_wrappers, tab2 "if (!SWIG_Python_UnpackTuple(args, \"swigconstant\", 1, 1, &module)) return NULL;\n"); - } else { - Printf(f_wrappers, tab2 "if (!PyArg_UnpackTuple(args, \"swigconstant\", 1, 1, &module)) return NULL;\n"); - } + Printf(f_wrappers, tab2 "if (!SWIG_Python_UnpackTuple(args, \"swigconstant\", 1, 1, &module)) return NULL;\n"); Printf(f_wrappers, tab2 "d = PyModule_GetDict(module);\n"); Printf(f_wrappers, tab2 "if (!d) return NULL;\n"); Printf(f_wrappers, tab2 "%s\n", tm); @@ -3605,7 +3601,7 @@ public: // Register the method in SwigMethods array String *cname = NewStringf("%s_swigconstant", iname); - add_method(cname, cname, 0); + add_method(cname, cname, 0, 0, 1, 1, 1); Delete(cname); } else { Printf(f_init, "%s\n", tm); From e7f9316e6037c97d005abd97cf7d12bb2582ccc4 Mon Sep 17 00:00:00 2001 From: Adrien JUND Date: Sat, 4 Nov 2017 16:09:33 +0100 Subject: [PATCH 063/134] C# - add std::list --- Examples/test-suite/csharp/Makefile.in | 3 +- .../test-suite/csharp/li_std_list_runme.cs | 402 +++++++++++++++ Examples/test-suite/li_std_list.i | 21 +- Lib/csharp/std_list.i | 483 ++++++++++++++++++ 4 files changed, 904 insertions(+), 5 deletions(-) create mode 100644 Examples/test-suite/csharp/li_std_list_runme.cs create mode 100644 Lib/csharp/std_list.i diff --git a/Examples/test-suite/csharp/Makefile.in b/Examples/test-suite/csharp/Makefile.in index a4ae7131d..c9e48f804 100644 --- a/Examples/test-suite/csharp/Makefile.in +++ b/Examples/test-suite/csharp/Makefile.in @@ -26,7 +26,8 @@ CPP_TEST_CASES = \ enum_thorough_typesafe \ exception_partial_info \ intermediary_classname \ - li_boost_intrusive_ptr + li_boost_intrusive_ptr \ + li_std_list \ CPP11_TEST_CASES = \ cpp11_shared_ptr_const \ diff --git a/Examples/test-suite/csharp/li_std_list_runme.cs b/Examples/test-suite/csharp/li_std_list_runme.cs new file mode 100644 index 000000000..fdcd0d9ac --- /dev/null +++ b/Examples/test-suite/csharp/li_std_list_runme.cs @@ -0,0 +1,402 @@ +using System; +using li_std_listNamespace; + +public class li_std_list_runme { + private static readonly int collectionSize = 20; + + public static void Main() { + // Setup a list of int + IntList list = new IntList(); + IntList.IntListNode node; + + for (int i = 0; i < 20; i++) { + int nb = i * 10; + list.Add(nb); + } + + // Count property test + if (list.Count != collectionSize) + throw new Exception("Count test failed"); + + // IsReadOnly property test + if (list.IsReadOnly) + throw new Exception("IsReadOnly test failed"); + + // Contains method test + if (!list.Contains(0)) + throw new Exception("Contains method test 1 failed"); + if (!list.Contains(2 * 10)) + throw new Exception("Contains method test 2 failed"); + if (!list.Contains(19 * 10)) + throw new Exception("Contains method test 3 failed"); + if (list.Contains(20 * 10)) + throw new Exception("Contains method test 4 failed"); + + // Nodes comparison method overload + { + IntList.IntListNode temp = new IntList.IntListNode(3); + if (list.First == temp) + throw new Exception("== overload method test (1) failed"); + temp = new IntList.IntListNode(0); + if (list.First == temp) + throw new Exception("== overload method test (2) failed"); + IntList.IntListNode temp2 = new IntList.IntListNode(0); + if (temp == temp2) + throw new Exception("== overload method test (3) failed"); + if (!(list.First == list.First)) + throw new Exception("== overload method test (4) failed"); + if (list.First != list.First) + throw new Exception("!= overload method test (1) failed"); + if (!(temp != temp2)) + throw new Exception("!= overload method test (2) failed"); + if (list.First.Equals(temp)) + throw new Exception("Equals method test failed"); + if (list.First.GetHashCode() == temp.GetHashCode()) + throw new Exception("GetHashCode method test (1) failed"); + if (list.First.GetHashCode() == list.First.GetHashCode()) + throw new Exception("GetHashCode method test (2) failed"); + + } + + // Getter test + { + if (list.First == null) + throw new Exception("First getter test (1) failed"); + if (list.Last == null) + throw new Exception("Last getter test (1) failed"); + if (list.Last.Next != null) + throw new Exception("Next getter test (1) failed"); + if (list.First.Next == null) + throw new Exception("Next getter test (2) failed"); + if (list.First.Previous != null) + throw new Exception("Previous getter test (1) failed"); + if (list.Last.Previous == null) + throw new Exception("Previous getter test (2) failed"); + } + + // AddFirst method test + node = list.AddFirst(34); + if (list.First.Value != 34 || node.Value != 34 || node != list.First) + throw new Exception("AddFirst method test failed"); + try { + list.AddFirst(null); + } catch (ArgumentNullException) { + try { + list.AddFirst(list.First); + } catch (InvalidOperationException) { + } + } + + // RemoveFirst method test + int tmp = list.First.Value; + list.RemoveFirst(); + if (list.First.Value == tmp || list.First.Value != 0 * 10) + throw new Exception("RemoveFirst method test failed"); + + // AddLast method test + node = list.AddLast(8); + if (list.Last.Value != 8 || node.Value != 8 || node != list.Last) + throw new Exception("AddLast method test failed"); + try { + list.AddLast(null); + } catch (ArgumentNullException) { + try { + list.AddLast(list.First); + } catch (InvalidOperationException) { + } + } + + // RemoveLast method test + int tmp2 = list.Last.Value; + list.RemoveLast(); + if (list.Last.Value == tmp2 || list.Last.Value != (list.Count - 1) * 10) + throw new Exception("RemoveLast method test failed"); + + // AddBefore method test + node = list.AddBefore(list.Last, 17); + if (list.Last.Previous.Value != 17 || node.Value != 17 || node != list.Last.Previous) + throw new Exception("AddBefore method test (1) failed"); + try { + node = null; + list.AddBefore(list.Last, node); + throw new Exception("AddBefore method test (2) failed"); + } catch (ArgumentNullException) { + try { + node = new IntList.IntListNode(1); + list.AddBefore(null, node); + throw new Exception("AddBefore method test (3) failed"); + } catch (ArgumentNullException) { + try { + list.AddBefore(list.Last, list.First); + } catch (InvalidOperationException) { + } + } + } + + // AddAfter method test + node = list.AddAfter(list.First, 47); + if (list.First.Next.Value != 47 || node.Value != 47 || node != list.First.Next) + throw new Exception("AddAfter method test (1) failed"); + try { + node = null; + list.AddAfter(list.First.Next, node); + throw new Exception("AddAfter method test (2) failed"); + } catch (ArgumentNullException) { + try { + list.AddAfter(list.First, list.Last); + } catch (InvalidOperationException) { + } + } + + // Find method test + node = list.Find(0); + if (node == null || node.Value != 0) + throw new Exception("Find method test (1) failed"); + node = list.Find(47); + if (node == null || node.Value != 47) + throw new Exception("Find method test (2) failed"); + node = list.Find(190); + if (node == null || node.Value != 190) + throw new Exception("Find method test (3) failed"); + node = list.Find(-3); + if (node != null) + throw new Exception("Find method test (4) failed"); + + // Remove method test + if (!list.Remove(17) || list.Contains(17) || list.Last.Previous.Value == 17) + throw new Exception("Remove method test (1) failed"); + if (!list.Remove(47) || list.Contains(47) || list.First.Next.Value == 47) + throw new Exception("Remove method test (2) failed"); + if (!list.Remove(0) || list.Contains(0) || list.First.Value == 0) + throw new Exception("Remove method test (3) failed"); + if (!list.Remove(190) || list.Contains(190) || list.Last.Value == 190) + throw new Exception("Remove method test (4) failed"); + try { + node = null; + list.Remove(node); + throw new Exception("Remove method test (5) failed"); + } catch (ArgumentNullException) { + try { + node = new IntList.IntListNode(4); + list.Remove(node); + throw new Exception("Remove method test (5) failed"); + } catch (InvalidOperationException) { + } + } + + // ICollection constructor test + { + int[] intArray = new int[] { 0, 11, 22, 33, 44, 55, 33 }; + IntList il = new IntList(intArray); + if (intArray.Length != il.Count) + throw new Exception("ICollection constructor length check failed: " + intArray.Length + "-" + il.Count); + node = il.First; + for (int i = 0; i < intArray.Length; i++) { + if (intArray[i] != node.Value) + throw new Exception("ICollection constructor failed, index:" + i); + node = node.Next; + } + try { + new IntList((System.Collections.ICollection)null); + throw new Exception("ICollection constructor null test failed"); + } catch (ArgumentNullException) { + } + } + + // Enumerator test + { + node = list.First; + System.Collections.IEnumerator myEnumerator = list.GetEnumerator(); + while (myEnumerator.MoveNext()) { + if ((int)myEnumerator.Current != node.Value) + throw new Exception("Enumerator (1) test failed"); + node = node.Next; + } + } + { + node = list.First; + System.Collections.Generic.IEnumerator myEnumerator = list.GetEnumerator(); + while (myEnumerator.MoveNext()) { + if (myEnumerator.Current != node.Value) + throw new Exception("Enumerator (2) test failed"); + node = node.Next; + } + } + { + node = list.First; + IntList.IntListEnumerator myEnumerator = list.GetEnumerator(); + while (myEnumerator.MoveNext()) { + if (myEnumerator.Current != node.Value) + throw new Exception("Enumerator (3) test failed"); + node = node.Next; + } + } + { + node = list.First; + foreach (var elem in list) { + if (elem != node.Value) + throw new Exception("Enumerator (4) test failed"); + node = node.Next; + } + } + + // CopyTo method test + { + int[] outputarray = new int[collectionSize - 2]; + list.CopyTo(outputarray, 0); + int index = 0; + IntList.IntListNode temp = list.First; + foreach (int val in outputarray) { + if (temp.Value != val) { + throw new Exception("CopyTo method test (1) failed, index:" + index); + } + index++; + temp = temp.Next; + } + } + { + DoubleList inputlist = new DoubleList(); + int arrayLen = 10; + for (int i = 0; i < arrayLen; i++) { + double num = i * 10.1; + inputlist.Add(num); + } + double[] outputarray = new double[arrayLen]; + inputlist.CopyTo(outputarray, 0); + DoubleList.DoubleListNode temp = inputlist.First; + for (int i = 0; i < arrayLen; i++) { + if (outputarray[i] != temp.Value) + throw new Exception("CopyTo method test (2) failed, index:" + i); + temp = temp.Next; + } + } + { + StructList inputlist = new StructList(); + int arrayLen = 10; + for (int i = 0; i < arrayLen; i++) + inputlist.Add(new Struct(i / 10.0)); + Struct[] outputarray = new Struct[arrayLen]; + inputlist.CopyTo(outputarray, 0); + StructList.StructListNode temp = inputlist.First; + for (int i = 0; i < arrayLen; i++) { + if (outputarray[i].num != temp.Value.num) + throw new Exception("CopyTo method test (3) failed, index:" + i); + temp = temp.Next; + } + foreach (Struct s in inputlist) { + s.num += 20.0; + } + temp = inputlist.First; + for (int i = 0; i < arrayLen; i++) { + if (outputarray[i].num != temp.Value.num) + throw new Exception("CopyTo method test (4) failed, index:" + i); + temp = temp.Next; + } + } + try { + list.CopyTo(null, 0); + throw new Exception("CopyTo method test (5) failed"); + } catch (ArgumentNullException) { + } + + // Clear() test + list.Clear(); + if (list.Count != 0) + throw new Exception("Clear method failed"); + + // Finally test the methods being wrapped + { + IntList il = new IntList(); + for (int i = 0; i < 4; i++) { + il.Add(i); + } + + double x = li_std_list.average(il); + x += li_std_list.average(new IntList(new int[] { 1, 2, 3, 4 })); + + DoubleList dlist = new DoubleList(); + for (int i = 0; i < 10; i++) { + dlist.Add(i / 2.0); + } + li_std_list.halve_in_place(dlist); + } + + // Dispose() + { + using (StructList ls = new StructList(new Struct[] { new Struct(0.0), new Struct(11.1) })) + using (DoubleList ld = new DoubleList(new double[] { 0.0, 11.1 })) { } + } + + // More wrapped methods + { + FloatList l0 = li_std_list.listreal(new FloatList()); + float flo = 123.456f; + l0.Add(flo); + flo = l0.First.Value; + + IntList l1 = li_std_list.listint(new IntList()); + IntPtrList l2 = li_std_list.listintptr(new IntPtrList()); + IntConstPtrList l3 = li_std_list.listintconstptr(new IntConstPtrList()); + + l1.Add(123); + l2.Clear(); + l3.Clear(); + + StructList l4 = li_std_list.liststruct(new StructList()); + StructPtrList l5 = li_std_list.liststructptr(new StructPtrList()); + StructConstPtrList l6 = li_std_list.liststructconstptr(new StructConstPtrList()); + + l4.Add(new Struct(123)); + l5.Add(new Struct(123)); + l6.Add(new Struct(123)); + } + + // Test lists of pointers + { + StructPtrList inputlist = new StructPtrList(); + int arrayLen = 10; + for (int i = 0; i < arrayLen; i++) { + inputlist.Add(new Struct(i / 10.0)); + } + Struct[] outputarray = new Struct[arrayLen]; + inputlist.CopyTo(outputarray, 0); + StructPtrList.StructPtrListNode temp = inputlist.First; + for (int i = 0; i < arrayLen; i++) { + if (outputarray[i].num != temp.Value.num) + throw new Exception("StructPtrList test (1) failed, i:" + i); + temp = temp.Next; + } + foreach (Struct s in inputlist) { + s.num += 20.0; + } + for (int i = 0; i < arrayLen; i++) { + if (outputarray[i].num != 20.0 + i / 10.0) + throw new Exception("StructPtrList test (2) failed (a deep copy was incorrectly made), i:" + i); + } + } + + // Test lists of const pointers + { + StructConstPtrList inputlist = new StructConstPtrList(); + int arrayLen = 10; + for (int i = 0; i < arrayLen; i++) { + inputlist.Add(new Struct(i / 10.0)); + } + Struct[] outputarray = new Struct[arrayLen]; + inputlist.CopyTo(outputarray, 0); + StructConstPtrList.StructConstPtrListNode temp = inputlist.First; + for (int i = 0; i < arrayLen; i++) { + if (outputarray[i].num != temp.Value.num) + throw new Exception("StructConstPtrList test (1) failed, i:" + i); + temp = temp.Next; + } + foreach (Struct s in inputlist) { + s.num += 20.0; + } + for (int i = 0; i < arrayLen; i++) { + if (outputarray[i].num != 20.0 + i / 10.0) + throw new Exception("StructConstPtrList test (2) failed (a deep copy was incorrectly made), i:" + i); + } + } + } +} \ No newline at end of file diff --git a/Examples/test-suite/li_std_list.i b/Examples/test-suite/li_std_list.i index d1ec4e7e4..6a60f032c 100644 --- a/Examples/test-suite/li_std_list.i +++ b/Examples/test-suite/li_std_list.i @@ -38,13 +38,23 @@ struct Struct { double num; Struct() : num(0.0) {} Struct(double d) : num(d) {} -// bool operator==(const Struct &other) { return (num == other.num); } + bool operator==(const Struct &other) { return (num == other.num); } }; const std::list & CopyContainerStruct(const std::list & container) { return container; } const std::list & CopyContainerStructPtr(const std::list & container) { return container; } const std::list & CopyContainerStructConstPtr(const std::list & container) { return container; } +const std::list & listreal(const std::list & list) { return list; } + +const std::list & listint(const std::list & list) { return list; } +const std::list & listintptr(const std::list & list) { return list; } +const std::list & listintconstptr(const std::list & list) { return list; } + +const std::list & liststruct(const std::list & list) { return list; } +const std::list & liststructptr(const std::list & list) { return list; } +const std::list & liststructconstptr(const std::list & list) { return list; } + enum Fruit { APPLE, BANANNA, @@ -53,8 +63,11 @@ enum Fruit { }; %} +#if !defined(SWIGR) +%template(IntPtrList) std::list; +%template(IntConstPtrList) std::list; +#endif %template(StructList) std::list; -%template(StructPtrList) std::list; +%template(StructPtrList) std::list; %template(StructConstPtrList) std::list; - -%template(FruitList) std::list; +%template(FruitList) std::list; \ No newline at end of file diff --git a/Lib/csharp/std_list.i b/Lib/csharp/std_list.i new file mode 100644 index 000000000..6194f94ea --- /dev/null +++ b/Lib/csharp/std_list.i @@ -0,0 +1,483 @@ +/* ----------------------------------------------------------------------------- + * std_list.i + * + * SWIG typemaps for std::list + * C# implementation + * The C# wrapper is made to look and feel like a C# System.Collections.Generic.LinkedList<> collection. + * + * ----------------------------------------------------------------------------- */ + +%include +%define SWIG_STD_LIST_MINIMUM_INTERNAL(CONST_REFERENCE, CTYPE...) +%typemap(csinterfaces) std::list< CTYPE > "global::System.Collections.Generic.ICollection<$typemap(cstype, CTYPE)>, global::System.Collections.Generic.IEnumerable<$typemap(cstype, CTYPE)>, global::System.Collections.IEnumerable, global::System.IDisposable" +%proxycode %{ + public $csclassname(global::System.Collections.IEnumerable c) : this() { + if (c == null) + throw new global::System.ArgumentNullException("c"); + foreach ($typemap(cstype, CTYPE) element in c) { + this.AddLast(element); + } + } + + public bool IsReadOnly { + get { + return false; + } + } + + public int Count { + get { + return (int)size(); + } + } + + public $csclassnameNode First { + get { + if (Count == 0) + return null; + return new $csclassnameNode(getFirstIter(), this); + } + } + + public $csclassnameNode Last { + get { + if (Count == 0) + return null; + return new $csclassnameNode(getLastIter(), this); + } + } + + public $csclassnameNode AddFirst($typemap(cstype, CTYPE) value) { + push_front(value); + return new $csclassnameNode(getFirstIter(), this); + } + + public void AddFirst($csclassnameNode newNode) { + ValidateNewNode(newNode); + if (!newNode.inlist) { + push_front(newNode.csharpvalue); + newNode.iter = getFirstIter(); + newNode.inlist = true; + } else { + throw new global::System.InvalidOperationException("The " + newNode.GetType().Name + " node already belongs to a " + this.GetType().Name); + } + } + + public $csclassnameNode AddLast($typemap(cstype, CTYPE) value) { + push_back(value); + return new $csclassnameNode(getLastIter(), this); + } + + public void AddLast($csclassnameNode newNode) { + ValidateNewNode(newNode); + if (!newNode.inlist) { + push_back(newNode.csharpvalue); + newNode.iter = getLastIter(); + newNode.inlist = true; + } else { + throw new global::System.InvalidOperationException("The " + newNode.GetType().Name + " node already belongs to a " + this.GetType().Name); + } + } + + public $csclassnameNode AddBefore($csclassnameNode node, $typemap(cstype, CTYPE) value) { + return new $csclassnameNode(insertNode(node.iter, value), this); + } + + public void AddBefore($csclassnameNode node, $csclassnameNode newNode) { + ValidateNode(node); + ValidateNewNode(newNode); + if (!newNode.inlist) { + newNode.iter = insertNode(node.iter, newNode.csharpvalue); + newNode.inlist = true; + } else { + throw new global::System.InvalidOperationException("The " + newNode.GetType().Name + " node already belongs to a " + this.GetType().Name); + } + } + + public $csclassnameNode AddAfter($csclassnameNode node, $typemap(cstype, CTYPE) value) { + node = node.Next; + return new $csclassnameNode(insertNode(node.iter, value), this); + } + + public void AddAfter($csclassnameNode node, $csclassnameNode newNode) { + ValidateNode(node); + ValidateNewNode(newNode); + if (!newNode.inlist) { + if (node == this.Last) + AddLast(newNode); + else + { + node = node.Next; + newNode.iter = insertNode(node.iter, newNode.csharpvalue); + newNode.inlist = true; + } + } else { + throw new global::System.InvalidOperationException("The " + newNode.GetType().Name + " node already belongs to a " + this.GetType().Name); + } + } + + public void Add($typemap(cstype, CTYPE) value) { + AddLast(value); + } + + public bool Remove($typemap(cstype, CTYPE) value) { + var node = Find(value); + if (node == null) + return false; + Remove(node); + return true; + } + + public void Remove($csclassnameNode node) { + ValidateNode(node); + eraseIter(node.iter); + } + + public $csclassnameNode Find($typemap(cstype, CTYPE) value) { + System.IntPtr tmp = find(value); + if (tmp != System.IntPtr.Zero) { + return new $csclassnameNode(tmp, this); + } + return null; + } + + public void CopyTo($typemap(cstype, CTYPE)[] array, int index) { + if (array == null) + throw new global::System.ArgumentNullException("array"); + if (index < 0 || index > array.Length) + throw new global::System.ArgumentOutOfRangeException("index", "Value is less than zero"); + if (array.Rank > 1) + throw new global::System.ArgumentException("Multi dimensional array.", "array"); + $csclassnameNode node = this.First; + if (node != null) { + do { + array[index++] = node.Value; + node = node.Next; + } while (node != null); + } + } + + internal void ValidateNode($csclassnameNode node) { + if (node == null) { + throw new System.ArgumentNullException("node"); + } + if (!node.inlist || node.list != this) { + throw new System.InvalidOperationException("node"); + } + } + + internal void ValidateNewNode($csclassnameNode node) { + if (node == null) { + throw new System.ArgumentNullException("node"); + } + } + + global::System.Collections.Generic.IEnumerator<$typemap(cstype, CTYPE)> global::System.Collections.Generic.IEnumerable<$typemap(cstype, CTYPE)>.GetEnumerator() { + return new $csclassnameEnumerator(this); + } + + global::System.Collections.IEnumerator global::System.Collections.IEnumerable.GetEnumerator() { + return new $csclassnameEnumerator(this); + } + + public $csclassnameEnumerator GetEnumerator() { + return new $csclassnameEnumerator(this); + } + + public sealed class $csclassnameEnumerator : global::System.Collections.IEnumerator, + global::System.Collections.Generic.IEnumerator<$typemap(cstype, CTYPE)> + { + private $csclassname collectionRef; + private $csclassnameNode currentNode; + private int currentIndex; + private object currentObject; + private int currentSize; + + public $csclassnameEnumerator($csclassname collection) { + collectionRef = collection; + currentNode = collection.First; + currentIndex = 0; + currentObject = null; + currentSize = collectionRef.Count; + } + + // Type-safe iterator Current + public $typemap(cstype, CTYPE) Current { + get { + if (currentIndex == -1) + throw new global::System.InvalidOperationException("Enumeration not started."); + if (currentIndex > currentSize) + throw new global::System.InvalidOperationException("Enumeration finished."); + if (currentObject == null) + throw new global::System.InvalidOperationException("Collection modified."); + return ($typemap(cstype, CTYPE))currentObject; + } + } + + // Type-unsafe IEnumerator.Current + object global::System.Collections.IEnumerator.Current { + get { + return Current; + } + } + + public bool MoveNext() { + if (currentNode == null) { + currentIndex = collectionRef.Count + 1; + return false; + } + ++currentIndex; + currentObject = currentNode.Value; + currentNode = currentNode.Next; + return true; + } + + public void Reset() { + currentIndex = -1; + currentObject = null; + if (collectionRef.Count != currentSize) { + throw new global::System.InvalidOperationException("Collection modified."); + } + } + + public void Dispose() { + currentIndex = -1; + currentObject = null; + } + } + + public sealed class $csclassnameNode { + internal $csclassname list; + internal System.IntPtr iter; + internal $typemap(cstype, CTYPE) csharpvalue; + internal bool inlist; + + public $csclassnameNode($typemap(cstype, CTYPE) value) { + csharpvalue = value; + inlist = false; + } + + internal $csclassnameNode(System.IntPtr _iter, $csclassname _list) { + list = _list; + iter = _iter; + inlist = true; + } + + public $csclassname List { + get { + return this.list; + } + } + + public $csclassnameNode Next { + get { + if (list.getNextIter(iter) == System.IntPtr.Zero) + return null; + return new $csclassnameNode(list.getNextIter(iter), list); + } + } + + public $csclassnameNode Previous { + get { + if (list.getPrevIter(iter) == System.IntPtr.Zero) + return null; + return new $csclassnameNode(list.getPrevIter(iter), list); + } + } + + public $typemap(cstype, CTYPE) Value { + get { + return list.getItem(this.iter); + } + set { + list.setItem(this.iter, value); + } + } + + public static bool operator== ($csclassnameNode node1, $csclassnameNode node2) { + if (object.ReferenceEquals(node1, null) && object.ReferenceEquals(node2, null)) + return true; + if (object.ReferenceEquals(node1, null) || object.ReferenceEquals(node2, null)) + return false; + return node1.Equals(node2); + } + + public static bool operator!= ($csclassnameNode node1, $csclassnameNode node2) { + if (node1 == null && node2 == null) + return false; + if (node1 == null || node2 == null) + return true; + return !node1.Equals(node2); + } + + public bool Equals($csclassnameNode node) { + if (node == null) + return false; + if (!node.inlist || !this.inlist) + return object.ReferenceEquals(this, node); + return list.equals(this.iter, node.iter); + } + + public override bool Equals(object node) { + return Equals(($csclassnameNode)node); + } + + public override int GetHashCode() { + int hash = 13; + if (inlist) { + hash = (hash * 7) + this.list.GetHashCode(); + hash = (hash * 7) + this.Value.GetHashCode(); + hash = (hash * 7) + this.list.getNextIter(this.iter).GetHashCode(); + hash = (hash * 7) + this.list.getPrevIter(this.iter).GetHashCode(); + } else { + hash = (hash * 7) + this.csharpvalue.GetHashCode(); + } + return hash; + } + + public void Dispose() { + list.deleteIter(this.iter); + } + } +%} + +public: + typedef size_t size_type; + typedef CTYPE value_type; + typedef CONST_REFERENCE const_reference; + void push_front(CTYPE const& x); + void push_back(CTYPE const& x); + %rename(RemoveFirst) pop_front; + void pop_front(); + %rename(RemoveLast) pop_back; + void pop_back(); + size_type size() const; + %rename(Clear) clear; + void clear(); + %extend { + CONST_REFERENCE getItem(void *iter) { + std::list< CTYPE >::iterator it = *reinterpret_cast::iterator*>(iter); + return *it; + } + + void setItem(void *iter, CTYPE const& val) { + std::list< CTYPE >::iterator* it = reinterpret_cast::iterator*>(iter); + *(*it) = val; + } + + void *getFirstIter() { + if ($self->size() == 0) + return NULL; + std::list< CTYPE >::iterator* it = new std::list< CTYPE >::iterator($self->begin()); + return reinterpret_cast(it); + } + + void *getLastIter() { + if ($self->size() == 0) + return NULL; + std::list< CTYPE >::iterator* it = new std::list< CTYPE >::iterator(--$self->end()); + return reinterpret_cast(it); + } + + void *getNextIter(void *iter) { + std::list< CTYPE >::iterator it = *(reinterpret_cast::iterator *>(iter)); + if (std::distance(it, --$self->end()) != 0) { + std::list< CTYPE >::iterator* itnext = new std::list< CTYPE >::iterator(++it); + return reinterpret_cast(itnext); + } + return NULL; + } + + void *getPrevIter(void *iter) { + std::list< CTYPE >::iterator it = *(reinterpret_cast::iterator *>(iter)); + if (std::distance($self->begin(), it) != 0) { + std::list< CTYPE >::iterator* itprev = new std::list< CTYPE >::iterator(--it); + return reinterpret_cast(itprev); + } + return NULL; + } + + void *insertNode(void *iter, CTYPE const& value) { + std::list< CTYPE >::iterator it = $self->insert(*(reinterpret_cast::iterator *>(iter)), value); + void* newit = reinterpret_cast(new std::list< CTYPE >::iterator(it)); + return newit; + } + + void *find(CTYPE const& value) { + if (std::find($self->begin(), $self->end(), value) != $self->end()) { + void* it = reinterpret_cast(new std::list< CTYPE >::iterator(std::find($self->begin(), $self->end(), value))); + return it; + } + return NULL; + } + + void eraseIter(void *iter) { + std::list< CTYPE >::iterator it = *reinterpret_cast::iterator*>(iter); + $self->erase(it); + } + + void deleteIter(void *iter) { + std::list< CTYPE >::iterator* it = reinterpret_cast::iterator*>(iter); + delete it; + } + + bool equals(void *iter1, void *iter2) { + if (iter1 == NULL && iter2 == NULL) + return true; + std::list< CTYPE >::iterator it1 = *reinterpret_cast::iterator*>(iter1); + std::list< CTYPE >::iterator it2 = *reinterpret_cast::iterator*>(iter2); + return it1 == it2; + } + + bool Contains(CTYPE const& value) { + return std::find($self->begin(), $self->end(), value) != $self->end(); + } + } +%enddef + +%apply void *VOID_INT_PTR { void *iter1, void *iter2, void *iter, void *find, void *insertNode, void *getPrevIter, void *getNextIter, void *getFirstIter, void *getLastIter } + +%define SWIG_STD_LIST_ENHANCED(CTYPE...) +namespace std { + template<> class list< CTYPE > { + SWIG_STD_LIST_MINIMUM_INTERNAL(%arg(CTYPE const&), %arg(CTYPE)); + }; +} +%enddef + + + +%{ +#include +#include +#include +#include +%} + +%csmethodmodifiers std::list::size "private" +%csmethodmodifiers std::list::getItem "private" +%csmethodmodifiers std::list::setItem "private" +%csmethodmodifiers std::list::push_front "private" +%csmethodmodifiers std::list::push_back "private" +%csmethodmodifiers std::list::getFirstIter "private" +%csmethodmodifiers std::list::getNextIter "private" +%csmethodmodifiers std::list::getPrevIter "private" +%csmethodmodifiers std::list::getLastIter "private" +%csmethodmodifiers std::list::find "private" +%csmethodmodifiers std::list::deleteIter "private" + +namespace std { + template + class list { + SWIG_STD_LIST_MINIMUM_INTERNAL(T const&, T) + }; + template + class list + { + SWIG_STD_LIST_MINIMUM_INTERNAL(T *const&, T *) + }; + template<> + class list { + SWIG_STD_LIST_MINIMUM_INTERNAL(bool, bool) + }; +} From 78051fdd33b5dc5fca0ec5787821ce5f9030af93 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 22 Mar 2019 07:42:44 +0000 Subject: [PATCH 064/134] C# std::list changes to support types that are not assignable Assignable fixes are based on those used by C# std::vector where the default wrappers work if there is no operator== available in the template type. Enhanced wrappers are obtained via a macro: SWIG_STD_LIST_ENHANCED(SomeNamespace::Klass) %template(ListKlass) std::list; Remove bool specialization (left over from the original std::vector wrappers). Add in missing typedefs. --- .../test-suite/csharp/li_std_list_runme.cs | 2 +- Examples/test-suite/li_std_list.i | 3 +- Lib/csharp/std_list.i | 124 ++++++++++++------ Lib/csharp/std_vector.i | 7 +- 4 files changed, 85 insertions(+), 51 deletions(-) diff --git a/Examples/test-suite/csharp/li_std_list_runme.cs b/Examples/test-suite/csharp/li_std_list_runme.cs index fdcd0d9ac..1a5b1562d 100644 --- a/Examples/test-suite/csharp/li_std_list_runme.cs +++ b/Examples/test-suite/csharp/li_std_list_runme.cs @@ -399,4 +399,4 @@ public class li_std_list_runme { } } } -} \ No newline at end of file +} diff --git a/Examples/test-suite/li_std_list.i b/Examples/test-suite/li_std_list.i index 6a60f032c..9cc6220d2 100644 --- a/Examples/test-suite/li_std_list.i +++ b/Examples/test-suite/li_std_list.i @@ -38,7 +38,6 @@ struct Struct { double num; Struct() : num(0.0) {} Struct(double d) : num(d) {} - bool operator==(const Struct &other) { return (num == other.num); } }; const std::list & CopyContainerStruct(const std::list & container) { return container; } @@ -70,4 +69,4 @@ enum Fruit { %template(StructList) std::list; %template(StructPtrList) std::list; %template(StructConstPtrList) std::list; -%template(FruitList) std::list; \ No newline at end of file +%template(FruitList) std::list; diff --git a/Lib/csharp/std_list.i b/Lib/csharp/std_list.i index 6194f94ea..e6e7fd260 100644 --- a/Lib/csharp/std_list.i +++ b/Lib/csharp/std_list.i @@ -5,11 +5,21 @@ * C# implementation * The C# wrapper is made to look and feel like a C# System.Collections.Generic.LinkedList<> collection. * + * Note that IEnumerable<> is implemented in the proxy class which is useful for using LINQ with + * C++ std::list wrappers. The ICollection<> interface is also implemented to provide enhanced functionality + * whenever we are confident that the required C++ operator== is available. This is the case for when + * T is a primitive type or a pointer. If T does define an operator==, then use the SWIG_STD_LIST_ENHANCED + * macro to obtain this enhanced functionality, for example: + * + * SWIG_STD_LIST_ENHANCED(SomeNamespace::Klass) + * %template(ListKlass) std::list; * ----------------------------------------------------------------------------- */ %include -%define SWIG_STD_LIST_MINIMUM_INTERNAL(CONST_REFERENCE, CTYPE...) -%typemap(csinterfaces) std::list< CTYPE > "global::System.Collections.Generic.ICollection<$typemap(cstype, CTYPE)>, global::System.Collections.Generic.IEnumerable<$typemap(cstype, CTYPE)>, global::System.Collections.IEnumerable, global::System.IDisposable" + +// MACRO for use within the std::list class body +%define SWIG_STD_LIST_MINIMUM_INTERNAL(CSINTERFACE, CTYPE...) +%typemap(csinterfaces) std::list< CTYPE > "global::System.IDisposable, global::System.Collections.IEnumerable, global::System.Collections.Generic.CSINTERFACE<$typemap(cstype, CTYPE)>\n"; %proxycode %{ public $csclassname(global::System.Collections.IEnumerable c) : this() { if (c == null) @@ -120,27 +130,11 @@ AddLast(value); } - public bool Remove($typemap(cstype, CTYPE) value) { - var node = Find(value); - if (node == null) - return false; - Remove(node); - return true; - } - public void Remove($csclassnameNode node) { ValidateNode(node); eraseIter(node.iter); } - public $csclassnameNode Find($typemap(cstype, CTYPE) value) { - System.IntPtr tmp = find(value); - if (tmp != System.IntPtr.Zero) { - return new $csclassnameNode(tmp, this); - } - return null; - } - public void CopyTo($typemap(cstype, CTYPE)[] array, int index) { if (array == null) throw new global::System.ArgumentNullException("array"); @@ -257,9 +251,9 @@ inlist = false; } - internal $csclassnameNode(System.IntPtr _iter, $csclassname _list) { - list = _list; - iter = _iter; + internal $csclassnameNode(System.IntPtr iter, $csclassname list) { + this.list = list; + this.iter = iter; inlist = true; } @@ -343,8 +337,13 @@ public: typedef size_t size_type; + typedef ptrdiff_t difference_type; typedef CTYPE value_type; - typedef CONST_REFERENCE const_reference; + typedef value_type* pointer; + typedef const value_type* const_pointer; + typedef value_type& reference; + typedef const value_type& const_reference; + void push_front(CTYPE const& x); void push_back(CTYPE const& x); %rename(RemoveFirst) pop_front; @@ -355,7 +354,7 @@ public: %rename(Clear) clear; void clear(); %extend { - CONST_REFERENCE getItem(void *iter) { + const_reference getItem(void *iter) { std::list< CTYPE >::iterator it = *reinterpret_cast::iterator*>(iter); return *it; } @@ -403,14 +402,6 @@ public: return newit; } - void *find(CTYPE const& value) { - if (std::find($self->begin(), $self->end(), value) != $self->end()) { - void* it = reinterpret_cast(new std::list< CTYPE >::iterator(std::find($self->begin(), $self->end(), value))); - return it; - } - return NULL; - } - void eraseIter(void *iter) { std::list< CTYPE >::iterator it = *reinterpret_cast::iterator*>(iter); $self->erase(it); @@ -428,27 +419,59 @@ public: std::list< CTYPE >::iterator it2 = *reinterpret_cast::iterator*>(iter2); return it1 == it2; } + } +%enddef +// Extra methods added to the collection class if operator== is defined for the class being wrapped +// The class will then implement ICollection<>, which adds extra functionality +%define SWIG_STD_LIST_EXTRA_OP_EQUALS_EQUALS(CTYPE...) + %extend { bool Contains(CTYPE const& value) { return std::find($self->begin(), $self->end(), value) != $self->end(); } + + bool Remove(CTYPE const& value) { + std::list< CTYPE >::iterator it = std::find($self->begin(), $self->end(), value); + if (it != $self->end()) { + $self->erase(it); + return true; + } + return false; + } + + void *find(CTYPE const& value) { + if (std::find($self->begin(), $self->end(), value) != $self->end()) { + void* it = reinterpret_cast(new std::list< CTYPE >::iterator(std::find($self->begin(), $self->end(), value))); + return it; + } + return NULL; + } } +%proxycode %{ + public $csclassnameNode Find($typemap(cstype, CTYPE) value) { + System.IntPtr tmp = find(value); + if (tmp != System.IntPtr.Zero) { + return new $csclassnameNode(tmp, this); + } + return null; + } +%} %enddef %apply void *VOID_INT_PTR { void *iter1, void *iter2, void *iter, void *find, void *insertNode, void *getPrevIter, void *getNextIter, void *getFirstIter, void *getLastIter } +// Macros for std::list class specializations/enhancements %define SWIG_STD_LIST_ENHANCED(CTYPE...) namespace std { template<> class list< CTYPE > { - SWIG_STD_LIST_MINIMUM_INTERNAL(%arg(CTYPE const&), %arg(CTYPE)); + SWIG_STD_LIST_MINIMUM_INTERNAL(ICollection, %arg(CTYPE)); + SWIG_STD_LIST_EXTRA_OP_EQUALS_EQUALS(CTYPE) }; } %enddef - %{ -#include #include #include #include @@ -467,17 +490,34 @@ namespace std { %csmethodmodifiers std::list::deleteIter "private" namespace std { + // primary (unspecialized) class template for std::list + // does not require operator== to be defined template class list { - SWIG_STD_LIST_MINIMUM_INTERNAL(T const&, T) + SWIG_STD_LIST_MINIMUM_INTERNAL(IEnumerable, T) }; + // specialization for pointers template - class list - { - SWIG_STD_LIST_MINIMUM_INTERNAL(T *const&, T *) - }; - template<> - class list { - SWIG_STD_LIST_MINIMUM_INTERNAL(bool, bool) + class list { + SWIG_STD_LIST_MINIMUM_INTERNAL(ICollection, T *) + SWIG_STD_LIST_EXTRA_OP_EQUALS_EQUALS(T *) }; } + +// template specializations for std::list +// these provide extra collections methods as operator== is defined +SWIG_STD_LIST_ENHANCED(char) +SWIG_STD_LIST_ENHANCED(signed char) +SWIG_STD_LIST_ENHANCED(unsigned char) +SWIG_STD_LIST_ENHANCED(short) +SWIG_STD_LIST_ENHANCED(unsigned short) +SWIG_STD_LIST_ENHANCED(int) +SWIG_STD_LIST_ENHANCED(unsigned int) +SWIG_STD_LIST_ENHANCED(long) +SWIG_STD_LIST_ENHANCED(unsigned long) +SWIG_STD_LIST_ENHANCED(long long) +SWIG_STD_LIST_ENHANCED(unsigned long long) +SWIG_STD_LIST_ENHANCED(float) +SWIG_STD_LIST_ENHANCED(double) +SWIG_STD_LIST_ENHANCED(std::string) // also requires a %include +SWIG_STD_LIST_ENHANCED(std::wstring) // also requires a %include diff --git a/Lib/csharp/std_vector.i b/Lib/csharp/std_vector.i index b1e8da963..e8eeb8411 100644 --- a/Lib/csharp/std_vector.i +++ b/Lib/csharp/std_vector.i @@ -13,18 +13,13 @@ * * SWIG_STD_VECTOR_ENHANCED(SomeNamespace::Klass) * %template(VectKlass) std::vector; - * - * Warning: heavy macro usage in this file. Use swig -E to get a sane view on the real file contents! * ----------------------------------------------------------------------------- */ -// Warning: Use the typemaps here in the expectation that the macros they are in will change name. - - %include // MACRO for use within the std::vector class body %define SWIG_STD_VECTOR_MINIMUM_INTERNAL(CSINTERFACE, CONST_REFERENCE, CTYPE...) -%typemap(csinterfaces) std::vector< CTYPE > "global::System.IDisposable, global::System.Collections.IEnumerable\n , global::System.Collections.Generic.CSINTERFACE<$typemap(cstype, CTYPE)>\n"; +%typemap(csinterfaces) std::vector< CTYPE > "global::System.IDisposable, global::System.Collections.IEnumerable, global::System.Collections.Generic.CSINTERFACE<$typemap(cstype, CTYPE)>\n"; %proxycode %{ public $csclassname(global::System.Collections.IEnumerable c) : this() { if (c == null) From 59030cb3d22aaa3aa7cc4607b0e936de4aac5724 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 25 Mar 2019 08:02:32 +0000 Subject: [PATCH 065/134] Replace void* with iterator* in C# std::list wrappers Better to use the actual type rather than void* in the implementaton. It also mean the %apply that was used in the implementation won't inadvertently affect users other use of void* types. --- CHANGES.current | 13 ++++++++ Lib/csharp/std_list.i | 70 ++++++++++++++++++++----------------------- 2 files changed, 46 insertions(+), 37 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 5022e3097..68657f562 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,19 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-03-25: Liryna + [C#] #1143 Add std_list.i for std::list support. + The C# std::list wrappers are made to look and feel like a C# + System.Collections.Generic.LinkedList<> collection. + The IEnumerable<> interface is implemented in the proxy class. + The ICollection<> interface can also be implemented to provide enhanced functionality + whenever a C++ operator== is available. This is the case for when T is a + primitive type or a pointer. If T does define an operator==, then use the + SWIG_STD_LIST_ENHANCED macro to obtain this enhanced functionality, for example: + + SWIG_STD_LIST_ENHANCED(SomeNamespace::Klass) + %template(ListKlass) std::list; + 2019-03-18: richardbeare [R] #1328 Non-trivial enums are working now. The enum values are now obtained from the C/C++ layer. const reference enums and C++11 enum classes are also now working. diff --git a/Lib/csharp/std_list.i b/Lib/csharp/std_list.i index e6e7fd260..674aba0ab 100644 --- a/Lib/csharp/std_list.i +++ b/Lib/csharp/std_list.i @@ -20,6 +20,9 @@ // MACRO for use within the std::list class body %define SWIG_STD_LIST_MINIMUM_INTERNAL(CSINTERFACE, CTYPE...) %typemap(csinterfaces) std::list< CTYPE > "global::System.IDisposable, global::System.Collections.IEnumerable, global::System.Collections.Generic.CSINTERFACE<$typemap(cstype, CTYPE)>\n"; + +%apply void *VOID_INT_PTR { std::list< CTYPE >::iterator * }; + %proxycode %{ public $csclassname(global::System.Collections.IEnumerable c) : this() { if (c == null) @@ -288,7 +291,7 @@ } } - public static bool operator== ($csclassnameNode node1, $csclassnameNode node2) { + public static bool operator==($csclassnameNode node1, $csclassnameNode node2) { if (object.ReferenceEquals(node1, null) && object.ReferenceEquals(node2, null)) return true; if (object.ReferenceEquals(node1, null) || object.ReferenceEquals(node2, null)) @@ -296,7 +299,7 @@ return node1.Equals(node2); } - public static bool operator!= ($csclassnameNode node1, $csclassnameNode node2) { + public static bool operator!=($csclassnameNode node1, $csclassnameNode node2) { if (node1 == null && node2 == null) return false; if (node1 == null || node2 == null) @@ -344,6 +347,8 @@ public: typedef value_type& reference; typedef const value_type& const_reference; + class iterator; + void push_front(CTYPE const& x); void push_back(CTYPE const& x); %rename(RemoveFirst) pop_front; @@ -354,69 +359,63 @@ public: %rename(Clear) clear; void clear(); %extend { - const_reference getItem(void *iter) { - std::list< CTYPE >::iterator it = *reinterpret_cast::iterator*>(iter); - return *it; + const_reference getItem(iterator *iter) { + return **iter; } - void setItem(void *iter, CTYPE const& val) { - std::list< CTYPE >::iterator* it = reinterpret_cast::iterator*>(iter); - *(*it) = val; + void setItem(iterator *iter, CTYPE const& val) { + *(*iter) = val; } - void *getFirstIter() { + iterator *getFirstIter() { if ($self->size() == 0) return NULL; - std::list< CTYPE >::iterator* it = new std::list< CTYPE >::iterator($self->begin()); - return reinterpret_cast(it); + return new std::list< CTYPE >::iterator($self->begin()); } - void *getLastIter() { + iterator *getLastIter() { if ($self->size() == 0) return NULL; - std::list< CTYPE >::iterator* it = new std::list< CTYPE >::iterator(--$self->end()); - return reinterpret_cast(it); + return new std::list< CTYPE >::iterator(--$self->end()); } - void *getNextIter(void *iter) { - std::list< CTYPE >::iterator it = *(reinterpret_cast::iterator *>(iter)); + iterator *getNextIter(iterator *iter) { + std::list< CTYPE >::iterator it = *iter; if (std::distance(it, --$self->end()) != 0) { std::list< CTYPE >::iterator* itnext = new std::list< CTYPE >::iterator(++it); - return reinterpret_cast(itnext); + return itnext; } return NULL; } - void *getPrevIter(void *iter) { - std::list< CTYPE >::iterator it = *(reinterpret_cast::iterator *>(iter)); + iterator *getPrevIter(iterator *iter) { + std::list< CTYPE >::iterator it = *iter; if (std::distance($self->begin(), it) != 0) { std::list< CTYPE >::iterator* itprev = new std::list< CTYPE >::iterator(--it); - return reinterpret_cast(itprev); + return itprev; } return NULL; } - void *insertNode(void *iter, CTYPE const& value) { - std::list< CTYPE >::iterator it = $self->insert(*(reinterpret_cast::iterator *>(iter)), value); - void* newit = reinterpret_cast(new std::list< CTYPE >::iterator(it)); - return newit; + iterator *insertNode(iterator *iter, CTYPE const& value) { + std::list< CTYPE >::iterator it = $self->insert(*iter, value); + return new std::list< CTYPE >::iterator(it); } - void eraseIter(void *iter) { - std::list< CTYPE >::iterator it = *reinterpret_cast::iterator*>(iter); + void eraseIter(iterator *iter) { + std::list< CTYPE >::iterator it = *iter; $self->erase(it); } - void deleteIter(void *iter) { - std::list< CTYPE >::iterator* it = reinterpret_cast::iterator*>(iter); - delete it; + void deleteIter(iterator *iter) { + delete iter; } - bool equals(void *iter1, void *iter2) { + bool equals(iterator *iter1, iterator *iter2) { if (iter1 == NULL && iter2 == NULL) return true; - std::list< CTYPE >::iterator it1 = *reinterpret_cast::iterator*>(iter1); - std::list< CTYPE >::iterator it2 = *reinterpret_cast::iterator*>(iter2); + std::list< CTYPE >::iterator it1 = *iter1; + std::list< CTYPE >::iterator it2 = *iter2; return it1 == it2; } } @@ -439,10 +438,9 @@ public: return false; } - void *find(CTYPE const& value) { + iterator *find(CTYPE const& value) { if (std::find($self->begin(), $self->end(), value) != $self->end()) { - void* it = reinterpret_cast(new std::list< CTYPE >::iterator(std::find($self->begin(), $self->end(), value))); - return it; + return new std::list< CTYPE >::iterator(std::find($self->begin(), $self->end(), value)); } return NULL; } @@ -458,8 +456,6 @@ public: %} %enddef -%apply void *VOID_INT_PTR { void *iter1, void *iter2, void *iter, void *find, void *insertNode, void *getPrevIter, void *getNextIter, void *getFirstIter, void *getLastIter } - // Macros for std::list class specializations/enhancements %define SWIG_STD_LIST_ENHANCED(CTYPE...) namespace std { From c0e212b9cf6c0179689b763cf61659fd77c2b616 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 25 Mar 2019 18:48:51 +0000 Subject: [PATCH 066/134] More C# std::list testing --- Examples/test-suite/stl_no_default_constructor.i | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Examples/test-suite/stl_no_default_constructor.i b/Examples/test-suite/stl_no_default_constructor.i index 164710bd5..32aff2b46 100644 --- a/Examples/test-suite/stl_no_default_constructor.i +++ b/Examples/test-suite/stl_no_default_constructor.i @@ -13,7 +13,7 @@ struct NoDefaultCtor { %template(VectorNoDefaultCtor) std::vector; #endif -#if defined(SWIGJAVA) +#if defined(SWIGJAVA) || defined(SWIGJAVA) %include %template(ListNoDefaultCtor) std::list; #endif From cedf4a2c2fddd5c6c45d7c12bb455db0458014b0 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 25 Mar 2019 18:54:08 +0000 Subject: [PATCH 067/134] More python std::list testing --- Examples/test-suite/python/Makefile.in | 1 + 1 file changed, 1 insertion(+) diff --git a/Examples/test-suite/python/Makefile.in b/Examples/test-suite/python/Makefile.in index 1402239b9..0151f5918 100644 --- a/Examples/test-suite/python/Makefile.in +++ b/Examples/test-suite/python/Makefile.in @@ -45,6 +45,7 @@ CPP_TEST_CASES += \ li_factory \ li_implicit \ li_std_containers_int \ + li_std_list \ li_std_map_member \ li_std_multimap \ li_std_pair_extra \ From b092055ca87a9e6f9d489d967d2ff27870687ce4 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 26 Mar 2019 07:48:33 +0000 Subject: [PATCH 068/134] Fix parallel 'make check-ocaml-examples' Some versions of ocamlc create a file of the same name in the tmp directory when invoking using ocalmc on swigp4.ml. The name is the same even from different example directories. TMPDIR is a workaround to make ocamlc use a different directory for this temp file. Parallel make (-j) broke because different instances of ocamlc tried to create the same temp file. Issue #1503 --- Examples/Makefile.in | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/Examples/Makefile.in b/Examples/Makefile.in index 7022166a0..2688b16f3 100644 --- a/Examples/Makefile.in +++ b/Examples/Makefile.in @@ -865,12 +865,15 @@ NOLINK ?= false OCAMLPP= -pp "camlp4o ./swigp4.cmo" OCAMLP4WHERE=`$(COMPILETOOL) @CAMLP4@ -where` OCAMLCORE=\ - (test -f swig.mli || $(SWIG) -ocaml -co swig.mli 2>/dev/null) && \ - (test -f swig.ml || $(SWIG) -ocaml -co swig.ml 2>/dev/null) && \ - (test -f swigp4.ml || $(SWIG) -ocaml -co swigp4.ml 2>/dev/null) && \ - (test -f swig.cmi || $(OCC) -c swig.mli) && \ - (test -f swig.cmo || $(OCC) -c swig.ml) && \ - (test -f swigp4.cmi || $(OCC) -I $(OCAMLP4WHERE) -pp "camlp4o pa_extend.cmo q_MLast.cmo" -c swigp4.ml) + $(SWIG) -ocaml -co swig.mli 2>/dev/null && \ + $(SWIG) -ocaml -co swig.ml 2>/dev/null && \ + $(SWIG) -ocaml -co swigp4.ml 2>/dev/null && \ + $(OCC) -c swig.mli && \ + $(OCC) -c swig.ml && \ + mkdir -p ./localtmp && \ + env TMPDIR=./localtmp $(OCC) -I $(OCAMLP4WHERE) -pp "camlp4o pa_extend.cmo q_MLast.cmo" -c swigp4.ml && \ + rm -rf ./localtmp +# TMPDIR above is a workaround for some ocamlc versions, such as 4.05.0, which always create a temp file of the same name breaking parallel make ocaml_static: $(SRCDIR_SRCS) $(OCAMLCORE) @@ -957,6 +960,7 @@ ocaml_clean: rm -f *_wrap* *~ .~* *.cmo *.cmi *.mli $(TARGET).ml $(RUNME) $(RUNME)_top swig.ml swigp4.ml rm -f core @EXTRA_CLEAN@ rm -f *.@OBJEXT@ *@SO@ + rm -rf ./localtmp ################################################################## ##### RUBY ###### From 166b683e8918c655dcfa9c9c3d99727bbf6288ef Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 26 Mar 2019 19:51:09 +0000 Subject: [PATCH 069/134] More ocaml parallel make fixes The previous commit removed a pile of 'test -f' hacks which were sort of working for parallel builds and broke parallel test-suite builds. Now this is fixed properly - these files are safely created in the test-suite already. Now we create them safely in the examples. --- Examples/Makefile.in | 39 +++++++++++-------------- Examples/ocaml/argout_ref/Makefile | 4 +++ Examples/ocaml/callback/Makefile | 4 +++ Examples/ocaml/class/Makefile | 4 +++ Examples/ocaml/contract/Makefile | 4 +++ Examples/ocaml/scoped_enum/Makefile | 4 +++ Examples/ocaml/shapes/Makefile | 4 +++ Examples/ocaml/simple/Makefile | 4 +++ Examples/ocaml/std_string/Makefile | 4 +++ Examples/ocaml/std_vector/Makefile | 4 +++ Examples/ocaml/stl/Makefile | 4 +++ Examples/ocaml/string_from_ptr/Makefile | 4 +++ Examples/ocaml/strings_test/Makefile | 4 +++ 13 files changed, 65 insertions(+), 22 deletions(-) diff --git a/Examples/Makefile.in b/Examples/Makefile.in index 2688b16f3..5ffc0095e 100644 --- a/Examples/Makefile.in +++ b/Examples/Makefile.in @@ -858,34 +858,33 @@ mzscheme_clean: ################################################################## OCC=$(COMPILETOOL) @OCAMLC@ +OCC_WITH_PP=env TMPDIR=./localtmp $(OCC) +# TMPDIR above is a workaround for some ocamlc versions, such as 4.05.0, which always create a temp file of the same name breaking parallel make (seemingly only when -pp is used) OCAMLDLGEN=$(COMPILETOOL) @OCAMLDLGEN@ OCAMLFIND=$(COMPILETOOL) @OCAMLFIND@ OCAMLMKTOP=$(COMPILETOOL) @OCAMLMKTOP@ NOLINK ?= false OCAMLPP= -pp "camlp4o ./swigp4.cmo" OCAMLP4WHERE=`$(COMPILETOOL) @CAMLP4@ -where` -OCAMLCORE=\ - $(SWIG) -ocaml -co swig.mli 2>/dev/null && \ - $(SWIG) -ocaml -co swig.ml 2>/dev/null && \ - $(SWIG) -ocaml -co swigp4.ml 2>/dev/null && \ - $(OCC) -c swig.mli && \ - $(OCC) -c swig.ml && \ - mkdir -p ./localtmp && \ - env TMPDIR=./localtmp $(OCC) -I $(OCAMLP4WHERE) -pp "camlp4o pa_extend.cmo q_MLast.cmo" -c swigp4.ml && \ - rm -rf ./localtmp -# TMPDIR above is a workaround for some ocamlc versions, such as 4.05.0, which always create a temp file of the same name breaking parallel make + +ocaml_core: + mkdir -p ./localtmp + $(SWIG) -ocaml -co swig.mli 2>/dev/null + $(SWIG) -ocaml -co swig.ml 2>/dev/null + $(SWIG) -ocaml -co swigp4.ml 2>/dev/null + $(OCC) -c swig.mli + $(OCC) -c swig.ml + $(OCC_WITH_PP) -I $(OCAMLP4WHERE) -pp "camlp4o pa_extend.cmo q_MLast.cmo" -c swigp4.ml ocaml_static: $(SRCDIR_SRCS) - $(OCAMLCORE) $(SWIG) -ocaml $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) $(OCC) -g -c -ccopt -g -ccopt "$(INCLUDES)" $(ISRCS) $(SRCDIR_SRCS) $(OCC) -g -c $(INTERFACE:%.i=%.mli) $(OCC) -w -U -g -c $(INTERFACE:%.i=%.ml) - test -z "$(PROGFILE)" || $(OCC) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) + test -z "$(PROGFILE)" || $(OCC_WITH_PP) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) $(NOLINK) || $(OCC) -g -ccopt -g -cclib -g -custom -o $(RUNME) swig.cmo $(INTERFACE:%.i=%.cmo) $(PROGFILE:%.ml=%.cmo) $(INTERFACE:%.i=%_wrap.@OBJEXT@) $(OBJS) -cclib "$(LIBS)" ocaml_dynamic: $(SRCDIR_SRCS) - $(OCAMLCORE) $(SWIG) -ocaml $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) $(OCC) -g -c -ccopt -g -ccopt "$(INCLUDES)" $(ISRCS) $(SRCDIR_SRCS) $(CXXSHARED) $(CPPFLAGS) $(CXXFLAGS) $(LDFLAGS) $(CCSHARED) -o $(INTERFACE:%.i=%@SO@) $(INTERFACE:%.i=%_wrap.@OBJEXT@) $(OBJS) $(LIBS) @@ -893,40 +892,36 @@ ocaml_dynamic: $(SRCDIR_SRCS) mv $(INTERFACE:%.i=%_dynamic.ml) $(INTERFACE:%.i=%.ml) rm $(INTERFACE:%.i=%.mli) $(OCAMLFIND) $(OCC) -g -c -package dl $(INTERFACE:%.i=%.ml) - test -z "$(PROGFILE)" || $(OCC) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) + test -z "$(PROGFILE)" || $(OCC_WITH_PP) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) $(NOLINK) || $(OCAMLFIND) $(OCC) -g -ccopt -g -cclib -g -custom -o $(RUNME) swig.cmo -package dl -linkpkg $(INTERFACE:%.i=%.cmo) $(PROGFILE:%.ml=%.cmo) ocaml_static_toplevel: $(SRCDIR_SRCS) - $(OCAMLCORE) $(SWIG) -ocaml $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) $(OCC) -g -c -ccopt -g -ccopt "$(INCLUDES)" $(ISRCS) $(SRCDIR_SRCS) $(OCC) -g -c $(INTERFACE:%.i=%.mli) $(OCC) -w -U -g -c $(INTERFACE:%.i=%.ml) - test -z "$(PROGFILE)" || $(OCC) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) + test -z "$(PROGFILE)" || $(OCC_WITH_PP) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) $(NOLINK) || $(OCAMLMKTOP) swig.cmo -I $(OCAMLP4WHERE) dynlink.cma camlp4o.cma swigp4.cmo -cclib "$(LIBS)" -g -ccopt -g -cclib -g -custom -o $(RUNME)_top $(INTERFACE:%.i=%.cmo) $(INTERFACE:%.i=%_wrap.@OBJEXT@) $(OBJS) ocaml_static_cpp: $(SRCDIR_SRCS) - $(OCAMLCORE) $(SWIG) -ocaml -c++ $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) cp $(ICXXSRCS) $(ICXXSRCS:%.cxx=%.c) $(OCC) -cc '$(CXX) $(CPPFLAGS)' -g -c -ccopt -g -ccopt "-xc++ $(INCLUDES)" $(ICXXSRCS:%.cxx=%.c) $(SRCDIR_SRCS) $(SRCDIR_CXXSRCS) $(OCC) -g -c $(INTERFACE:%.i=%.mli) $(OCC) -w -U -g -c $(INTERFACE:%.i=%.ml) - test -z "$(PROGFILE)" || $(OCC) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) + test -z "$(PROGFILE)" || $(OCC_WITH_PP) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) $(NOLINK) || $(OCC) -g -ccopt -g -cclib -g -custom -o $(RUNME) swig.cmo $(INTERFACE:%.i=%.cmo) $(PROGFILE:%.ml=%.cmo) $(INTERFACE:%.i=%_wrap.@OBJEXT@) $(OBJS) -cclib "$(LIBS)" -cc '$(CXX)' ocaml_static_cpp_toplevel: $(SRCDIR_SRCS) - $(OCAMLCORE) $(SWIG) -ocaml -c++ $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) cp $(ICXXSRCS) $(ICXXSRCS:%.cxx=%.c) $(OCC) -cc '$(CXX) $(CPPFLAGS)' -g -c -ccopt -g -ccopt "-xc++ $(INCLUDES)" $(ICXXSRCS:%.cxx=%.c) $(SRCDIR_SRCS) $(SRCDIR_CXXSRCS) $(OCC) -g -c $(INTERFACE:%.i=%.mli) $(OCC) -w -U -g -c $(INTERFACE:%.i=%.ml) - test -z "$(PROGFILE)" || $(OCC) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) + test -z "$(PROGFILE)" || $(OCC_WITH_PP) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) $(NOLINK) || $(OCAMLMKTOP) -cc '$(CXX) $(CPPFLAGS)' swig.cmo -I $(OCAMLP4WHERE) dynlink.cma camlp4o.cma swigp4.cmo -cclib "$(LIBS)" -g -ccopt -g -cclib -g -custom -o $(RUNME)_top $(INTERFACE:%.i=%.cmo) $(INTERFACE:%.i=%_wrap.@OBJEXT@) $(OBJS) ocaml_dynamic_cpp: $(SRCDIR_SRCS) - $(OCAMLCORE) $(SWIG) -ocaml -c++ $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) cp $(ICXXSRCS) $(ICXXSRCS:%.cxx=%.c) $(OCC) -cc '$(CXX) $(CPPFLAGS)' -g -c -ccopt -g -ccopt "-xc++ $(INCLUDES)" $(ICXXSRCS:%.cxx=%.c) $(SRCDIR_SRCS) $(SRCDIR_CXXSRCS) -ccopt -fPIC @@ -935,7 +930,7 @@ ocaml_dynamic_cpp: $(SRCDIR_SRCS) mv $(INTERFACE:%.i=%_dynamic.ml) $(INTERFACE:%.i=%.ml) rm $(INTERFACE:%.i=%.mli) $(OCAMLFIND) $(OCC) -g -c -package dl $(INTERFACE:%.i=%.ml) - test -z "$(PROGFILE)" || $(OCC) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) + test -z "$(PROGFILE)" || $(OCC_WITH_PP) -o $(PROGFILE:%.ml=%) $(OCAMLPP) -c $(SRCDIR)$(PROGFILE) $(NOLINK) || $(OCAMLFIND) swig.cmo $(OCC) -cclib -export-dynamic -g -ccopt -g -cclib -g -custom -o $(RUNME) -package dl -linkpkg $(INTERFACE:%.i=%.cmo) $(PROGFILE:%.ml=%.cmo) -cc '$(CXX)' # ----------------------------------------------------------------- diff --git a/Examples/ocaml/argout_ref/Makefile b/Examples/ocaml/argout_ref/Makefile index 234713da5..09370940f 100644 --- a/Examples/ocaml/argout_ref/Makefile +++ b/Examples/ocaml/argout_ref/Makefile @@ -13,6 +13,10 @@ check: build build: static static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/callback/Makefile b/Examples/ocaml/callback/Makefile index 7344485f6..b81b5ac1b 100644 --- a/Examples/ocaml/callback/Makefile +++ b/Examples/ocaml/callback/Makefile @@ -14,6 +14,10 @@ check: build build: static static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ SWIGOPT='$(SWIGOPT)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/class/Makefile b/Examples/ocaml/class/Makefile index 7344485f6..b81b5ac1b 100644 --- a/Examples/ocaml/class/Makefile +++ b/Examples/ocaml/class/Makefile @@ -14,6 +14,10 @@ check: build build: static static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ SWIGOPT='$(SWIGOPT)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/contract/Makefile b/Examples/ocaml/contract/Makefile index 1f36642e4..8148de142 100644 --- a/Examples/ocaml/contract/Makefile +++ b/Examples/ocaml/contract/Makefile @@ -20,6 +20,10 @@ dynamic: ocaml_dynamic static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/scoped_enum/Makefile b/Examples/ocaml/scoped_enum/Makefile index f0f53173f..cfed474ef 100644 --- a/Examples/ocaml/scoped_enum/Makefile +++ b/Examples/ocaml/scoped_enum/Makefile @@ -20,6 +20,10 @@ dynamic: ocaml_dynamic_cpp static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/shapes/Makefile b/Examples/ocaml/shapes/Makefile index a9932793b..eab86d298 100644 --- a/Examples/ocaml/shapes/Makefile +++ b/Examples/ocaml/shapes/Makefile @@ -14,6 +14,10 @@ check: build build: static toplevel static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ SWIGOPT='$(SWIGOPT)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/simple/Makefile b/Examples/ocaml/simple/Makefile index 3b24a6bcb..27fdb20f5 100644 --- a/Examples/ocaml/simple/Makefile +++ b/Examples/ocaml/simple/Makefile @@ -20,6 +20,10 @@ dynamic: ocaml_dynamic static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/std_string/Makefile b/Examples/ocaml/std_string/Makefile index 099b1fcee..655465692 100644 --- a/Examples/ocaml/std_string/Makefile +++ b/Examples/ocaml/std_string/Makefile @@ -12,6 +12,10 @@ check: build build: static static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/std_vector/Makefile b/Examples/ocaml/std_vector/Makefile index 099b1fcee..655465692 100644 --- a/Examples/ocaml/std_vector/Makefile +++ b/Examples/ocaml/std_vector/Makefile @@ -12,6 +12,10 @@ check: build build: static static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/stl/Makefile b/Examples/ocaml/stl/Makefile index 683d34c36..ceaa80d1d 100644 --- a/Examples/ocaml/stl/Makefile +++ b/Examples/ocaml/stl/Makefile @@ -12,6 +12,10 @@ check: build build: static static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/string_from_ptr/Makefile b/Examples/ocaml/string_from_ptr/Makefile index 6917e4638..5ab5c44a9 100644 --- a/Examples/ocaml/string_from_ptr/Makefile +++ b/Examples/ocaml/string_from_ptr/Makefile @@ -13,6 +13,10 @@ check: build build: static toplevel static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ diff --git a/Examples/ocaml/strings_test/Makefile b/Examples/ocaml/strings_test/Makefile index 9474f5364..7609b31c6 100644 --- a/Examples/ocaml/strings_test/Makefile +++ b/Examples/ocaml/strings_test/Makefile @@ -12,6 +12,10 @@ check: build build: static toplevel static: + $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ + ocaml_core $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ From 33f8c36813f731d54f6220b089248311d3134279 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 26 Mar 2019 21:24:00 +0000 Subject: [PATCH 070/134] Correct ocaml dynamic targets --- Examples/ocaml/stl/Makefile | 2 +- Examples/ocaml/strings_test/Makefile | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Examples/ocaml/stl/Makefile b/Examples/ocaml/stl/Makefile index ceaa80d1d..363311d95 100644 --- a/Examples/ocaml/stl/Makefile +++ b/Examples/ocaml/stl/Makefile @@ -25,7 +25,7 @@ dynamic: $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ - ocaml_static_cpp + ocaml_dynamic_cpp toplevel: $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ diff --git a/Examples/ocaml/strings_test/Makefile b/Examples/ocaml/strings_test/Makefile index 7609b31c6..38cf234da 100644 --- a/Examples/ocaml/strings_test/Makefile +++ b/Examples/ocaml/strings_test/Makefile @@ -25,7 +25,7 @@ dynamic: $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ PROGFILE='$(PROGFILE)' TARGET='$(TARGET)' INTERFACE='$(INTERFACE)' \ - ocaml_static_cpp + ocaml_dynamic_cpp toplevel: static $(MAKE) -f $(TOP)/Makefile SRCDIR='$(SRCDIR)' SRCS='$(SRCS)' \ From 06462acdf9b7738a19dce5579d90b1c91b3f9cfb Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 30 Mar 2019 12:18:40 +0000 Subject: [PATCH 071/134] Fix C# CA1063 warning by implementing the recommended Dispose methods. Previously just the Dispose() method was generated. Now the Dispose() and Dispose(bool disposing) methods are generated. Changes are required if custom "csfinalize", "csdestruct" or "csdestruct_derived" typemaps are being used. Details in #421 on Github. SWIG will error out if one of the "csfinalize, "csdestruct" or "csdestruct_derived" typemaps are found. Example error message: foo.h:60: Error: A deprecated csfinalize typemap was found for Foo, please remove it and replace all csdestruct, csdestruct_derived and csfinalize typemaps by the csdispose, csdispose_derived, csdisposing and csdisposing_derived typemaps. Closes #421 --- CHANGES.current | 15 ++++ Doc/Manual/CSharp.html | 4 +- Examples/test-suite/allprotected.i | 4 + .../test-suite/csharp/allprotected_runme.cs | 14 ++++ Examples/test-suite/minherit2.i | 4 +- Lib/csharp/boost_intrusive_ptr.i | 16 ++-- Lib/csharp/boost_shared_ptr.i | 8 +- Lib/csharp/csharp.swg | 19 +++-- Source/Modules/csharp.cxx | 74 ++++++++++++++----- 9 files changed, 113 insertions(+), 45 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 68657f562..4cea8d91b 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,21 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-03-30: wsfulton + [C#] #421 Fix CA1063 warning by implementing the recommended Dispose methods for + the IDisposable interface. Previously just the Dispose() method was generated. + Now the Dispose() and Dispose(bool disposing) methods are generated. + Changes are required if custom "csfinalize", "csdestruct" or "csdestruct_derived" + typemaps are being used. Details in #421 on Github. SWIG will error out if one of + the "csfinalize, "csdestruct" or "csdestruct_derived" typemaps are found. Example + error message: + + foo.h:60: Error: A deprecated csfinalize typemap was found for Foo, please remove + it and replace all csdestruct, csdestruct_derived and csfinalize typemaps by the + csdispose, csdispose_derived, csdisposing and csdisposing_derived typemaps. + + *** POTENTIAL INCOMPATIBILITY *** + 2019-03-25: Liryna [C#] #1143 Add std_list.i for std::list support. The C# std::list wrappers are made to look and feel like a C# diff --git a/Doc/Manual/CSharp.html b/Doc/Manual/CSharp.html index d485a9714..0526766b5 100644 --- a/Doc/Manual/CSharp.html +++ b/Doc/Manual/CSharp.html @@ -232,8 +232,8 @@ javacode -> cscode javaimports -> csimports javabody -> csbody javafinalize -> csfinalize -javadestruct -> csdestruct -javadestruct_derived -> csdestruct_derived +javadestruct -> csdisposing and csdispose +javadestruct_derived -> csdisposing_derived and csdispose_derived javainterfacecode -> csinterfacecode diff --git a/Examples/test-suite/allprotected.i b/Examples/test-suite/allprotected.i index 086cfb245..e9b4eb341 100644 --- a/Examples/test-suite/allprotected.i +++ b/Examples/test-suite/allprotected.i @@ -79,5 +79,9 @@ protected: }; int ProtectedBase::staticMemberVariable = 10; +class ProtectedDerived : public ProtectedBase { +public: + ProtectedDerived(const char *s) : ProtectedBase(s) {} +}; %} diff --git a/Examples/test-suite/csharp/allprotected_runme.cs b/Examples/test-suite/csharp/allprotected_runme.cs index 99a791d58..6b04feb25 100644 --- a/Examples/test-suite/csharp/allprotected_runme.cs +++ b/Examples/test-suite/csharp/allprotected_runme.cs @@ -13,6 +13,20 @@ public class runme { MyProtectedBase mpb = new MyProtectedBase("MyProtectedBase"); mpb.accessProtected(); + try { + // C++ destructor is protected + mpb.Dispose(); + throw new Exception("failed to catch MethodAccessException"); + } catch (MethodAccessException) { + // Exception message: C++ destructor does not have public access + } + ProtectedDerived pd = new ProtectedDerived("ProtectedDerived"); + // Destroying via the ProtectedDerived's destructor should work + pd.Dispose(); + + ProtectedBase pb = new ProtectedDerived("ProtectedDerived"); + // ProtectedDerived's destructor should be called via the Dispose(disposing) virtual call + pb.Dispose(); } } diff --git a/Examples/test-suite/minherit2.i b/Examples/test-suite/minherit2.i index 7d470d30e..2baea6495 100644 --- a/Examples/test-suite/minherit2.i +++ b/Examples/test-suite/minherit2.i @@ -17,8 +17,8 @@ #if defined(SWIGCSHARP) #define javaclassmodifiers csclassmodifiers #define javabody csbody -#define javafinalize csfinalize -#define javadestruct csdestruct +#define javafinalize csdispose +#define javadestruct csdisposing #define javaout csout #define javainterfaces csinterfaces #define javabase csbase diff --git a/Lib/csharp/boost_intrusive_ptr.i b/Lib/csharp/boost_intrusive_ptr.i index 6b0392d3d..fa3f53a20 100644 --- a/Lib/csharp/boost_intrusive_ptr.i +++ b/Lib/csharp/boost_intrusive_ptr.i @@ -314,7 +314,7 @@ } %} -%typemap(csdestruct, methodname="Dispose", methodmodifiers="public") TYPE { +%typemap(csdisposing, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") TYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwnBase) { @@ -323,11 +323,10 @@ } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); } } -%typemap(csdestruct_derived, methodname="Dispose", methodmodifiers="public") TYPE { +%typemap(csdisposing_derived, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") TYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwnDerived) { @@ -336,8 +335,7 @@ } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); - base.Dispose(); + base.Dispose(disposing); } } @@ -473,7 +471,7 @@ } %} -%typemap(csdestruct, methodname="Dispose", methodmodifiers="public") TYPE { +%typemap(csdisposing, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") TYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwnBase) { @@ -482,11 +480,10 @@ } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); } } -%typemap(csdestruct_derived, methodname="Dispose", methodmodifiers="public") TYPE { +%typemap(csdisposing_derived, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") TYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwnDerived) { @@ -495,8 +492,7 @@ } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); - base.Dispose(); + base.Dispose(disposing); } } diff --git a/Lib/csharp/boost_shared_ptr.i b/Lib/csharp/boost_shared_ptr.i index 73212dddc..508c0ec14 100644 --- a/Lib/csharp/boost_shared_ptr.i +++ b/Lib/csharp/boost_shared_ptr.i @@ -282,7 +282,7 @@ } %} -%typemap(csdestruct, methodname="Dispose", methodmodifiers="public") TYPE { +%typemap(csdisposing, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") TYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwnBase) { @@ -291,11 +291,10 @@ } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); } } -%typemap(csdestruct_derived, methodname="Dispose", methodmodifiers="public") TYPE { +%typemap(csdisposing_derived, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") TYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwnDerived) { @@ -304,8 +303,7 @@ } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); - base.Dispose(); + base.Dispose(disposing); } } diff --git a/Lib/csharp/csharp.swg b/Lib/csharp/csharp.swg index e1554dcb8..832206386 100644 --- a/Lib/csharp/csharp.swg +++ b/Lib/csharp/csharp.swg @@ -959,17 +959,24 @@ SWIGINTERN const char * SWIG_UnpackData(const char *c, void *ptr, size_t sz) { SWIG_CSBODY_PROXY(internal, internal, SWIGTYPE) SWIG_CSBODY_TYPEWRAPPER(internal, protected, internal, SWIGTYPE) -%typemap(csfinalize) SWIGTYPE %{ +%typemap(csdispose) SWIGTYPE %{ ~$csclassname() { - Dispose(); + Dispose(false); + } + + public void Dispose() { + Dispose(true); + global::System.GC.SuppressFinalize(this); } %} +%typemap(csdispose_derived) SWIGTYPE "" + %typemap(csconstruct, excode=SWIGEXCODE,directorconnect="\n SwigDirectorConnect();") SWIGTYPE %{: this($imcall, true) {$excode$directorconnect } %} -%typemap(csdestruct, methodname="Dispose", methodmodifiers="public") SWIGTYPE { +%typemap(csdisposing, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") SWIGTYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwn) { @@ -978,11 +985,10 @@ SWIG_CSBODY_TYPEWRAPPER(internal, protected, internal, SWIGTYPE) } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); } } -%typemap(csdestruct_derived, methodname="Dispose", methodmodifiers="public") SWIGTYPE { +%typemap(csdisposing_derived, methodname="Dispose", methodmodifiers="protected", parameters="bool disposing") SWIGTYPE { lock(this) { if (swigCPtr.Handle != global::System.IntPtr.Zero) { if (swigCMemOwn) { @@ -991,8 +997,7 @@ SWIG_CSBODY_TYPEWRAPPER(internal, protected, internal, SWIGTYPE) } swigCPtr = new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero); } - global::System.GC.SuppressFinalize(this); - base.Dispose(); + base.Dispose(disposing); } } diff --git a/Source/Modules/csharp.cxx b/Source/Modules/csharp.cxx index bd00ffaf3..ff73c3075 100644 --- a/Source/Modules/csharp.cxx +++ b/Source/Modules/csharp.cxx @@ -1873,38 +1873,56 @@ public: typemapLookup(n, "csbody", typemap_lookup_type, WARN_CSHARP_TYPEMAP_CSBODY_UNDEF), // main body of class NIL); - // C++ destructor is wrapped by the Dispose method - // Note that the method name is specified in a typemap attribute called methodname + // C++ destructor is wrapped by the Finalize and Dispose methods + + const char *tmap_method = derived ? "csdestruct_derived" : "csdestruct"; + const String *tm = typemapExists(n, tmap_method, typemap_lookup_type); + if (tm) { + Swig_error(Getfile(tm), Getline(tm), + "A deprecated %s typemap was found for %s, please remove it and replace all csdestruct, csdestruct_derived and csfinalize typemaps by the csdispose, csdispose_derived, csdisposing and csdisposing_derived typemaps.\n", + tmap_method, proxy_class_name); + } + tmap_method = "csfinalize"; + tm = typemapExists(n, tmap_method, typemap_lookup_type); + if (tm) { + Swig_error(Getfile(tm), Getline(tm), + "A deprecated %s typemap was found for %s, please remove it and replace all csdestruct, csdestruct_derived and csfinalize typemaps by the csdispose, csdispose_derived, csdisposing and csdisposing_derived typemaps.\n", + tmap_method, proxy_class_name); + } + + tmap_method = derived ? "csdisposing_derived" : "csdisposing"; String *destruct = NewString(""); - const String *tm = NULL; attributes = NewHash(); - String *destruct_methodname = NULL; - String *destruct_methodmodifiers = NULL; + const String *destruct_methodname = NULL; + const String *destruct_methodmodifiers = NULL; + const String *destruct_parameters = NULL; if (derived) { - tm = typemapLookup(n, "csdestruct_derived", typemap_lookup_type, WARN_NONE, attributes); - destruct_methodname = Getattr(attributes, "tmap:csdestruct_derived:methodname"); - destruct_methodmodifiers = Getattr(attributes, "tmap:csdestruct_derived:methodmodifiers"); + tm = typemapLookup(n, "csdisposing_derived", typemap_lookup_type, WARN_NONE, attributes); + destruct_methodname = Getattr(attributes, "tmap:csdisposing_derived:methodname"); + destruct_methodmodifiers = Getattr(attributes, "tmap:csdisposing_derived:methodmodifiers"); + destruct_parameters = Getattr(attributes, "tmap:csdisposing_derived:parameters"); } else { - tm = typemapLookup(n, "csdestruct", typemap_lookup_type, WARN_NONE, attributes); - destruct_methodname = Getattr(attributes, "tmap:csdestruct:methodname"); - destruct_methodmodifiers = Getattr(attributes, "tmap:csdestruct:methodmodifiers"); + tm = typemapLookup(n, "csdisposing", typemap_lookup_type, WARN_NONE, attributes); + destruct_methodname = Getattr(attributes, "tmap:csdisposing:methodname"); + destruct_methodmodifiers = Getattr(attributes, "tmap:csdisposing:methodmodifiers"); + destruct_parameters = Getattr(attributes, "tmap:csdisposing:parameters"); } if (tm && *Char(tm)) { if (!destruct_methodname) { - Swig_error(Getfile(n), Getline(n), "No methodname attribute defined in csdestruct%s typemap for %s\n", (derived ? "_derived" : ""), proxy_class_name); + Swig_error(Getfile(n), Getline(n), "No methodname attribute defined in %s typemap for %s\n", tmap_method, proxy_class_name); } if (!destruct_methodmodifiers) { Swig_error(Getfile(n), Getline(n), - "No methodmodifiers attribute defined in csdestruct%s typemap for %s.\n", (derived ? "_derived" : ""), proxy_class_name); + "No methodmodifiers attribute defined in %s typemap for %s.\n", tmap_method, proxy_class_name); } + if (!destruct_parameters) + destruct_parameters = empty_string; } // Emit the Finalize and Dispose methods if (tm) { - // Finalize method - if (*Char(destructor_call)) { - Printv(proxy_class_def, typemapLookup(n, "csfinalize", typemap_lookup_type, WARN_NONE), NIL); - } - // Dispose method + // Finalize and Dispose methods + Printv(proxy_class_def, typemapLookup(n, derived ? "csdispose_derived" : "csdispose", typemap_lookup_type, WARN_NONE), NIL); + // Dispose(bool disposing) method Printv(destruct, tm, NIL); if (*Char(destructor_call)) Replaceall(destruct, "$imcall", destructor_call); @@ -1917,7 +1935,7 @@ public: Printv(proxy_class_def, methodmods, NIL); else Printv(proxy_class_def, destruct_methodmodifiers, " ", derived ? "override" : "virtual", NIL); - Printv(proxy_class_def, " void ", destruct_methodname, "() ", destruct, "\n", NIL); + Printv(proxy_class_def, " void ", destruct_methodname, "(", destruct_parameters, ") ", destruct, "\n", NIL); } } if (*Char(interface_upcasts)) @@ -3552,6 +3570,24 @@ public: return tm; } + /* ----------------------------------------------------------------------------- + * typemapExists() + * n - for input only and must contain info for Getfile(n) and Getline(n) to work + * tmap_method - typemap method name + * type - typemap type to lookup + * returns found typemap or NULL if not found + * ----------------------------------------------------------------------------- */ + + const String *typemapExists(Node *n, const_String_or_char_ptr tmap_method, SwigType *type) { + Node *node = NewHash(); + Setattr(node, "type", type); + Setfile(node, Getfile(n)); + Setline(node, Getline(n)); + const String *tm = Swig_typemap_lookup(tmap_method, node, "", 0); + Delete(node); + return tm; + } + /* ----------------------------------------------------------------------------- * canThrow() * Determine whether the code in the typemap can throw a C# exception. From 831fae3c698fd6a690d06aac257c381e69d474ea Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 30 Mar 2019 12:34:06 +0000 Subject: [PATCH 072/134] Add the parameters typemap attribute to D and Java destructor wrapper typemaps Added to the javadestruct, javadestruct_derived, ddispose, ddispose_derived typemaps to mirror enhanced flexibility in the csdisposing and csdisposing_derived (C#) typemaps. If provided the contents are generated as the delete/dispose method's parameters declaration. --- CHANGES.current | 6 ++++++ Doc/Manual/D.html | 4 ++-- Doc/Manual/Java.html | 6 ++++-- Lib/d/dclassgen.swg | 4 ++-- Lib/java/java.swg | 4 ++-- Source/Modules/d.cxx | 11 ++++++++--- Source/Modules/java.cxx | 11 ++++++++--- 7 files changed, 32 insertions(+), 14 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 4cea8d91b..9e4b02d4d 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,12 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-03-30: wsfulton + [Java, D] Add the parameters typemap attribute to the javadestruct, + javadestruct_derived, ddispose, ddispose_derived typemaps to mirror enhanced + flexibility in the csdisposing and csdisposing_derived (C#) typemaps. If provided + the contents are generated as the delete/dispose method's parameters declaration. + 2019-03-30: wsfulton [C#] #421 Fix CA1063 warning by implementing the recommended Dispose methods for the IDisposable interface. Previously just the Dispose() method was generated. diff --git a/Doc/Manual/D.html b/Doc/Manual/D.html index a252650ff..f1b3404a6 100644 --- a/Doc/Manual/D.html +++ b/Doc/Manual/D.html @@ -107,8 +107,8 @@ csimports <-> dimports csbody <-> dbody csfinalize <-> ddestructor - csdestruct <-> ddispose - csdestruct_derived <-> ddispose_derived + csdisposing <-> ddispose + csdisposing_derived <-> ddispose_derived diff --git a/Doc/Manual/Java.html b/Doc/Manual/Java.html index 3a04b8a79..cdefba6b4 100644 --- a/Doc/Manual/Java.html +++ b/Doc/Manual/Java.html @@ -6552,7 +6552,7 @@ As there can only be one "javacode" typemap per class, also consider using the and offers nearly identical functionality. -

    %typemap(javadestruct, methodname="delete", methodmodifiers="public synchronized")

    +

    %typemap(javadestruct, methodname="delete", methodmodifiers="public synchronized", parameters="")

    destructor wrapper - the delete() method (proxy classes only), used for all proxy classes except those which have a base class @@ -6563,9 +6563,10 @@ Note that the delete() method name is configurable and is specified by The method modifiers are also configurable via the methodmodifiers attribute. If a %javamethodmodifiers is attached to the class' destructor, it will be used in preference to the methodmodifiers typemap attribute for the class. +The delete method's parameters declaration can be provided in the optional parameters typemap attribute.
    -

    %typemap(javadestruct_derived, methodname="delete", methodmodifiers="public synchronized")

    +

    %typemap(javadestruct_derived, methodname="delete", methodmodifiers="public synchronized", parameters="")

    destructor wrapper - the delete() method (proxy classes only), same as "javadestruct" but only used for derived proxy classes @@ -6576,6 +6577,7 @@ Note that the delete() method name is configurable and is specified by The method modifiers are also configurable via the methodmodifiers attribute. If a %javamethodmodifiers is attached to the class' destructor, it will be used in preference to the methodmodifiers typemap attribute for the class. +The delete method's parameters declaration can be provided in the optional parameters typemap attribute.

    %typemap(javaimports)

    diff --git a/Lib/d/dclassgen.swg b/Lib/d/dclassgen.swg index 68910b412..84fa03a0b 100644 --- a/Lib/d/dclassgen.swg +++ b/Lib/d/dclassgen.swg @@ -33,7 +33,7 @@ // We do not use »override« attribute for generated dispose() methods to stay // somewhat compatible to Phobos and older Tango versions where Object.dispose() // does not exist. -%typemap(ddispose, methodname="dispose", methodmodifiers="public") SWIGTYPE { +%typemap(ddispose, methodname="dispose", methodmodifiers="public", parameters="") SWIGTYPE { synchronized(this) { if (swigCPtr !is null) { if (swigCMemOwn) { @@ -45,7 +45,7 @@ } } -%typemap(ddispose_derived, methodname="dispose", methodmodifiers="public") SWIGTYPE { +%typemap(ddispose_derived, methodname="dispose", methodmodifiers="public", parameters="") SWIGTYPE { synchronized(this) { if (swigCPtr !is null) { if (swigCMemOwn) { diff --git a/Lib/java/java.swg b/Lib/java/java.swg index a5b7bbab1..e9309331a 100644 --- a/Lib/java/java.swg +++ b/Lib/java/java.swg @@ -1313,7 +1313,7 @@ SWIG_PROXY_CONSTRUCTOR(true, false, TYPENAME) // Set the default for SWIGTYPE: Java owns the C/C++ object. SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) -%typemap(javadestruct, methodname="delete", methodmodifiers="public synchronized") SWIGTYPE { +%typemap(javadestruct, methodname="delete", methodmodifiers="public synchronized", parameters="") SWIGTYPE { if (swigCPtr != 0) { if (swigCMemOwn) { swigCMemOwn = false; @@ -1323,7 +1323,7 @@ SWIG_PROXY_CONSTRUCTOR(true, true, SWIGTYPE) } } -%typemap(javadestruct_derived, methodname="delete", methodmodifiers="public synchronized") SWIGTYPE { +%typemap(javadestruct_derived, methodname="delete", methodmodifiers="public synchronized", parameters="") SWIGTYPE { if (swigCPtr != 0) { if (swigCMemOwn) { swigCMemOwn = false; diff --git a/Source/Modules/d.cxx b/Source/Modules/d.cxx index 4fa30dd60..5e82dfda3 100644 --- a/Source/Modules/d.cxx +++ b/Source/Modules/d.cxx @@ -3274,17 +3274,20 @@ private: // attribute called »methodname«. const String *tm = NULL; - String *dispose_methodname; - String *dispose_methodmodifiers; + const String *dispose_methodname; + const String *dispose_methodmodifiers; + const String *dispose_parameters; attributes = NewHash(); if (derived) { tm = lookupCodeTypemap(n, "ddispose_derived", typemap_lookup_type, WARN_NONE, attributes); dispose_methodname = Getattr(attributes, "tmap:ddispose_derived:methodname"); dispose_methodmodifiers = Getattr(attributes, "tmap:ddispose_derived:methodmodifiers"); + dispose_parameters = Getattr(attributes, "tmap:ddispose_derived:parameters"); } else { tm = lookupCodeTypemap(n, "ddispose", typemap_lookup_type, WARN_NONE, attributes); dispose_methodname = Getattr(attributes, "tmap:ddispose:methodname"); dispose_methodmodifiers = Getattr(attributes, "tmap:ddispose:methodmodifiers"); + dispose_parameters = Getattr(attributes, "tmap:ddispose:parameters"); } if (tm && *Char(tm)) { @@ -3298,6 +3301,8 @@ private: "No methodmodifiers attribute defined in ddispose%s typemap for %s.\n", (derived ? "_derived" : ""), proxy_class_name); } + if (!dispose_parameters) + dispose_parameters = empty_string; } if (tm) { @@ -3324,7 +3329,7 @@ private: Printv(body, methodmods, NIL); else Printv(body, dispose_methodmodifiers, (derived ? " override" : ""), NIL); - Printv(body, " void ", dispose_methodname, "() ", dispose_code, "\n", NIL); + Printv(body, " void ", dispose_methodname, "(", dispose_parameters, ") ", dispose_code, "\n", NIL); } } diff --git a/Source/Modules/java.cxx b/Source/Modules/java.cxx index ac845cb09..94087369a 100644 --- a/Source/Modules/java.cxx +++ b/Source/Modules/java.cxx @@ -2035,16 +2035,19 @@ public: String *destruct = NewString(""); const String *tm = NULL; attributes = NewHash(); - String *destruct_methodname = NULL; - String *destruct_methodmodifiers = NULL; + const String *destruct_methodname = NULL; + const String *destruct_methodmodifiers = NULL; + const String *destruct_parameters = NULL; if (derived) { tm = typemapLookup(n, "javadestruct_derived", typemap_lookup_type, WARN_NONE, attributes); destruct_methodname = Getattr(attributes, "tmap:javadestruct_derived:methodname"); destruct_methodmodifiers = Getattr(attributes, "tmap:javadestruct_derived:methodmodifiers"); + destruct_parameters = Getattr(attributes, "tmap:javadestruct_derived:parameters"); } else { tm = typemapLookup(n, "javadestruct", typemap_lookup_type, WARN_NONE, attributes); destruct_methodname = Getattr(attributes, "tmap:javadestruct:methodname"); destruct_methodmodifiers = Getattr(attributes, "tmap:javadestruct:methodmodifiers"); + destruct_parameters = Getattr(attributes, "tmap:javadestruct:parameters"); } if (tm && *Char(tm)) { if (!destruct_methodname) { @@ -2053,6 +2056,8 @@ public: if (!destruct_methodmodifiers) { Swig_error(Getfile(n), Getline(n), "No methodmodifiers attribute defined in javadestruct%s typemap for %s.\n", (derived ? "_derived" : ""), proxy_class_name); } + if (!destruct_parameters) + destruct_parameters = empty_string; } // Emit the finalize and delete methods if (tm) { @@ -2073,7 +2078,7 @@ public: Printv(proxy_class_def, methodmods, NIL); else Printv(proxy_class_def, destruct_methodmodifiers, NIL); - Printv(proxy_class_def, " void ", destruct_methodname, "()", destructor_throws_clause, " ", destruct, "\n", NIL); + Printv(proxy_class_def, " void ", destruct_methodname, "(", destruct_parameters, ") ", destructor_throws_clause, " ", destruct, "\n", NIL); } } if (*Char(interface_upcasts)) From 3d99cc6b2f636796aadfbf037e8e4e9e54185a79 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 07:57:39 +0100 Subject: [PATCH 073/134] Add a few options to the mkdist.py script for building the distribution tarball --- Tools/mkdist.py | 78 +++++++++++++++++++++++++++---------------------- 1 file changed, 43 insertions(+), 35 deletions(-) diff --git a/Tools/mkdist.py b/Tools/mkdist.py index 11a0dd6cd..284e7de9b 100755 --- a/Tools/mkdist.py +++ b/Tools/mkdist.py @@ -9,27 +9,31 @@ import os import subprocess def failed(): - print "mkdist.py failed to complete" - sys.exit(2) + print "mkdist.py failed to complete" + sys.exit(2) +import argparse +parser = argparse.ArgumentParser(description="Build a SWIG distribution tarball swig-x.y.z.tar.gz") +parser.add_argument("version", help="version string in format x.y.z") +parser.add_argument("-b", "--branch", required=False, default="master", help="git branch name to create tarball from [master]") +parser.add_argument("-f", "--force-tag", required=False, action="store_true", help="force tag (replace git tag if it already exists)") +parser.add_argument("-s", "--skip-checks", required=False, action="store_true", help="skip checks (that local and remote repos are in sync)") +args = parser.parse_args() -try: - version = sys.argv[1] - dirname = "swig-" + version - branch = sys.argv[2] -except: - print "Usage: mkdist.py version branch, where version should be x.y.z and branch is normally 'master'" - sys.exit(1) +version = args.version +branch = args.branch +dirname = "swig-" + version +force_tag = args.force_tag +skip_checks = args.skip_checks if sys.version_info[0:2] < (2, 7): - print "Error: Python 2.7 is required" - sys.exit(3) - + print "Error: Python 2.7 is required" + sys.exit(3) # Check name matches normal unix conventions if string.lower(dirname) != dirname: - print "directory name ("+dirname+") should be in lowercase" - sys.exit(3) + print "directory name ("+dirname+") should be in lowercase" + sys.exit(3) # If directory and tarball exist, remove it print "Removing ", dirname @@ -43,36 +47,40 @@ os.system("rm -f "+dirname+".tar") # Grab the code from git -print "Checking git repository is in sync with remote repository" +print "Checking there are no local changes in git repo" os.system("git remote update origin") == 0 or failed() command = ["git", "status", "--porcelain", "-uno"] out = subprocess.check_output(command) if out.strip() != "": - print "Local git repository has modifications" - print " ".join(command) - print out - sys.exit(3) + print "Local git repository has modifications" + print " ".join(command) + print out + sys.exit(3) -command = ["git", "log", "--oneline", branch + "..origin/" + branch] -out = subprocess.check_output(command) -if out.strip() != "": - print "Remote repository has additional modifications to local repository" - print " ".join(command) - print out - sys.exit(3) +if not skip_checks: + print "Checking git repository is in sync with remote repository" + command = ["git", "log", "--oneline", branch + "..origin/" + branch] + out = subprocess.check_output(command) + if out.strip() != "": + print "Remote repository has additional modifications to local repository" + print " ".join(command) + print out + sys.exit(3) -command = ["git", "log", "--oneline", "origin/" + branch + ".." + branch] -out = subprocess.check_output(command) -if out.strip() != "": - print "Local repository has modifications not pushed to the remote repository" - print "These should be pushed and checked that they pass Continuous Integration testing before continuing" - print " ".join(command) - print out - sys.exit(3) + command = ["git", "log", "--oneline", "origin/" + branch + ".." + branch] + out = subprocess.check_output(command) + if out.strip() != "": + print "Local repository has modifications not pushed to the remote repository" + print "These should be pushed and checked that they pass Continuous Integration testing before continuing" + print " ".join(command) + print out + sys.exit(3) print "Tagging release" tag = "'rel-" + version + "'" -os.system("git tag -a -m " + tag + " " + tag) == 0 or failed() +force = "-f " if force_tag else "" +print("force {}".format(force)) +os.system("git tag -a -m " + tag + " " + force + tag) == 0 or failed() outdir = os.path.basename(os.getcwd()) + "/" + dirname + "/" print "Grabbing tagged release git repository using 'git archive' into " + outdir From 320254eb140f50dda2960a3b8fcf8f7bee5668cd Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 18:35:32 +0100 Subject: [PATCH 074/134] Port mkdist.py to Python 3 --- Tools/mkdist.py | 73 +++++++++++++++++++++++-------------------------- 1 file changed, 34 insertions(+), 39 deletions(-) diff --git a/Tools/mkdist.py b/Tools/mkdist.py index 284e7de9b..47cf8e765 100755 --- a/Tools/mkdist.py +++ b/Tools/mkdist.py @@ -1,15 +1,11 @@ #!/usr/bin/env python -# This script builds a swig-x.y.z distribution. -# Usage: mkdist.py version branch, where version should be x.y.z and branch is normally 'master' - import sys -import string import os import subprocess def failed(): - print "mkdist.py failed to complete" + print("mkdist.py failed to complete") sys.exit(2) import argparse @@ -27,82 +23,81 @@ force_tag = args.force_tag skip_checks = args.skip_checks if sys.version_info[0:2] < (2, 7): - print "Error: Python 2.7 is required" + print("Error: Python 2.7 or higher is required") sys.exit(3) # Check name matches normal unix conventions -if string.lower(dirname) != dirname: - print "directory name ("+dirname+") should be in lowercase" +if dirname.lower() != dirname: + print("directory name (" + dirname + ") should be in lowercase") sys.exit(3) # If directory and tarball exist, remove it -print "Removing ", dirname -os.system("rm -rf "+dirname) +print("Removing " + dirname) +os.system("rm -rf " + dirname) -print "Removing "+dirname+".tar if exists" -os.system("rm -f "+dirname+".tar.gz") +print("Removing " + dirname + ".tar if exists") +os.system("rm -f " + dirname + ".tar.gz") -print "Removing "+dirname+".tar.gz if exists" -os.system("rm -f "+dirname+".tar") +print("Removing " + dirname + ".tar.gz if exists") +os.system("rm -f " + dirname + ".tar") # Grab the code from git -print "Checking there are no local changes in git repo" +print("Checking there are no local changes in git repo") os.system("git remote update origin") == 0 or failed() command = ["git", "status", "--porcelain", "-uno"] out = subprocess.check_output(command) if out.strip() != "": - print "Local git repository has modifications" - print " ".join(command) - print out + print("Local git repository has modifications") + print(" ".join(command)) + print(out) sys.exit(3) if not skip_checks: - print "Checking git repository is in sync with remote repository" + print("Checking git repository is in sync with remote repository") command = ["git", "log", "--oneline", branch + "..origin/" + branch] out = subprocess.check_output(command) if out.strip() != "": - print "Remote repository has additional modifications to local repository" - print " ".join(command) - print out + print("Remote repository has additional modifications to local repository") + print(" ".join(command)) + print(out) sys.exit(3) command = ["git", "log", "--oneline", "origin/" + branch + ".." + branch] out = subprocess.check_output(command) if out.strip() != "": - print "Local repository has modifications not pushed to the remote repository" - print "These should be pushed and checked that they pass Continuous Integration testing before continuing" - print " ".join(command) - print out + print("Local repository has modifications not pushed to the remote repository") + print("These should be pushed and checked that they pass Continuous Integration testing before continuing") + print(" ".join(command)) + print(out) sys.exit(3) -print "Tagging release" +print("Tagging release") tag = "'rel-" + version + "'" force = "-f " if force_tag else "" -print("force {}".format(force)) os.system("git tag -a -m " + tag + " " + force + tag) == 0 or failed() outdir = os.path.basename(os.getcwd()) + "/" + dirname + "/" -print "Grabbing tagged release git repository using 'git archive' into " + outdir +print("Grabbing tagged release git repository using 'git archive' into " + outdir) os.system("(cd .. && git archive --prefix=" + outdir + " " + tag + " . | tar -xf -)") == 0 or failed() # Go build the system -print "Building system" -os.system("cd "+dirname+" && ./autogen.sh") == 0 or failed() -os.system("cd "+dirname+"/Source/CParse && bison -y -d parser.y && mv y.tab.c parser.c && mv y.tab.h parser.h") == 0 or failed() -os.system("cd "+dirname+" && make -f Makefile.in libfiles srcdir=./") == 0 or failed() +print("Building system") +os.system("cd " + dirname + " && ./autogen.sh") == 0 or failed() +os.system("cd " + dirname + "/Source/CParse && bison -y -d parser.y && mv y.tab.c parser.c && mv y.tab.h parser.h") == 0 or failed() +os.system("cd " + dirname + " && make -f Makefile.in libfiles srcdir=./") == 0 or failed() # Remove autoconf files -os.system("find "+dirname+" -name autom4te.cache -exec rm -rf {} \\;") +os.system("find " + dirname + " -name autom4te.cache -exec rm -rf {} \\;") # Build documentation -print "Building html documentation" -os.system("cd "+dirname+"/Doc/Manual && make all clean-baks") == 0 or failed() +print("Building html documentation") +os.system("cd " + dirname + "/Doc/Manual && make all clean-baks") == 0 or failed() # Build the tar-ball -os.system("tar -cf "+dirname+".tar "+dirname) == 0 or failed() -os.system("gzip "+dirname+".tar") == 0 or failed() +os.system("tar -cf " + dirname + ".tar " + dirname) == 0 or failed() +os.system("gzip " + dirname + ".tar") == 0 or failed() -print "Finished building "+dirname+".tar.gz" +print("Finished building " + dirname + ".tar.gz") From 66d5d76a29f5323aeb1a3cb204d02c8385fe6bf6 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 19:07:53 +0100 Subject: [PATCH 075/134] mkrelease.py improvements Make python3 compatible. Add optional command line arguments. --- Tools/mkrelease.py | 63 +++++++++++++++++++++++++--------------------- 1 file changed, 35 insertions(+), 28 deletions(-) diff --git a/Tools/mkrelease.py b/Tools/mkrelease.py index ec9a2b76a..014cef227 100755 --- a/Tools/mkrelease.py +++ b/Tools/mkrelease.py @@ -1,49 +1,56 @@ #!/usr/bin/env python -# This script builds the SWIG source tarball, creates the Windows executable and the Windows zip package -# and uploads them both to SF ready for release. Also uploaded are the release notes. import sys -import string import os def failed(message): if message == "": - print "mkrelease.py failed to complete" + print("mkrelease.py failed to complete") else: - print message + print(message) sys.exit(2) -try: - version = sys.argv[1] - branch = sys.argv[2] - username = sys.argv[3] -except: - print "Usage: python mkrelease.py version branch username" - print "where version should be x.y.z and username is your SF username" - sys.exit(1) +import argparse +parser = argparse.ArgumentParser(description="Build a SWIG distribution source tarball swig-x.y.z.tar.gz and the Windows zip package swigwin-x.y.z.zip.\nUpload them both to SourceForge ready for release.\nThe release notes are also uploaded.") +parser.add_argument("version", help="version string in format x.y.z") +parser.add_argument("-b", "--branch", required=False, default="master", help="git branch name to create tarball from [master]") +parser.add_argument("-f", "--force-tag", required=False, action="store_true", help="force tag (replace git tag if it already exists)") +parser.add_argument("-s", "--skip-checks", required=False, action="store_true", help="skip checks (that local and remote repos are in sync)") +parser.add_argument("-u", "--username", required=False, help="SourceForge username (upload to SourceForge will be skipped if not provided)") +args = parser.parse_args() -print "Looking for rsync" +version = args.version +branch = args.branch +dirname = "swig-" + version +force_tag = args.force_tag +skip_checks = args.skip_checks +username = args.username + +print("Looking for rsync") os.system("which rsync") and failed("rsync not installed/found. Please install.") -print "Making source tarball" -os.system("python ./mkdist.py " + version + " " + branch) and failed("") +print("Making source tarball") +force = "--force-tag" if force_tag else "" +skip = "--skip-checks" if skip_checks else "" +os.system("python ./mkdist.py {} {} --branch {} {}".format(force, skip, branch, version)) and failed("") -print "Build Windows package" +print("Build Windows package") os.system("./mkwindows.sh " + version) and failed("") -print "Uploading to SourceForge" +if username: + print("Uploading to SourceForge") -swig_dir_sf = username + ",swig@frs.sourceforge.net:/home/frs/project/s/sw/swig/swig/swig-" + version + "/" -swigwin_dir_sf = username + ",swig@frs.sourceforge.net:/home/frs/project/s/sw/swig/swigwin/swigwin-" + version + "/" + swig_dir_sf = username + ",swig@frs.sourceforge.net:/home/frs/project/s/sw/swig/swig/swig-" + version + "/" + swigwin_dir_sf = username + ",swig@frs.sourceforge.net:/home/frs/project/s/sw/swig/swigwin/swigwin-" + version + "/" -# If a file with 'readme' in the name exists in the same folder as the zip/tarball, it gets automatically displayed as the release notes by SF -full_readme_file = "readme-" + version + ".txt" -os.system("rm -f " + full_readme_file) -os.system("cat swig-" + version + "/README " + "swig-" + version + "/CHANGES.current " + "swig-" + version + "/RELEASENOTES " + "> " + full_readme_file) + # If a file with 'readme' in the name exists in the same folder as the zip/tarball, it gets automatically displayed as the release notes by SF + full_readme_file = "readme-" + version + ".txt" + os.system("rm -f " + full_readme_file) + os.system("cat swig-" + version + "/README " + "swig-" + version + "/CHANGES.current " + "swig-" + version + "/RELEASENOTES " + "> " + full_readme_file) -os.system("rsync --archive --verbose -P --times -e ssh " + "swig-" + version + ".tar.gz " + full_readme_file + " " + swig_dir_sf) and failed("") -os.system("rsync --archive --verbose -P --times -e ssh " + "swigwin-" + version + ".zip " + full_readme_file + " " + swigwin_dir_sf) and failed("") + os.system("rsync --archive --verbose -P --times -e ssh " + "swig-" + version + ".tar.gz " + full_readme_file + " " + swig_dir_sf) and failed("") + os.system("rsync --archive --verbose -P --times -e ssh " + "swigwin-" + version + ".zip " + full_readme_file + " " + swigwin_dir_sf) and failed("") -print "Finished" + print("Finished") -print "Now log in to SourceForge and set the operating systems applicable to the newly uploaded tarball and zip file. Also remember to do a 'git push --tags'." + print("Now log in to SourceForge and set the operating systems applicable to the newly uploaded tarball and zip file. Also remember to do a 'git push --tags'.") From ad60edef576683a94ebc288ff5b2066c32198a5c Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 19:08:59 +0100 Subject: [PATCH 076/134] Make obs-buildlogs.py Python3 compatible --- Tools/obs-buildlogs.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Tools/obs-buildlogs.py b/Tools/obs-buildlogs.py index eaf0f613b..b97e7dba1 100755 --- a/Tools/obs-buildlogs.py +++ b/Tools/obs-buildlogs.py @@ -15,7 +15,7 @@ def download(): for line in repos.stdout: command = ['osc', 'buildlog', '--last'] + line.split() filename = "-".join(line.split()) + ".log" - print "Downloading logs using: {}".format(" ".join(command)) + print("Downloading logs using: {}".format(" ".join(command))) buildlog = subprocess.Popen(command, stdout=subprocess.PIPE) print("Writing log to {}".format(filename)) From 0303e821efad926f81888ff8fc2c24dadd0a82a5 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 19:11:44 +0100 Subject: [PATCH 077/134] html documentation fixes --- Doc/Manual/R.html | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Doc/Manual/R.html b/Doc/Manual/R.html index 9ca39c99f..45e5541d0 100644 --- a/Doc/Manual/R.html +++ b/Doc/Manual/R.html @@ -209,6 +209,7 @@ defineEnumeration("_colour", +

    which will create an environment named .__E___colour. The enumeration values are initialised via calls to C/C++ code, allowing complex values for enumerations to be used. Calls to the C/C++ code require @@ -225,7 +226,7 @@ appropriate environments and thus translate between characters and integers. The relevant functions, for debugging purposes, are enumToInteger and -enumFromInteger. +enumFromInteger. Anonymous enumerations are ignored by the binding generation process, leaving no way of accessing the value of anonymous enumerations from R From bf9065395a977e2813403dd3040ee91e69141cd0 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 19:33:59 +0100 Subject: [PATCH 078/134] C++11 test fixes for Visual Studio 2017 --- .../cpp11_alias_nested_template_scoping.i | 12 ++++++------ Examples/test-suite/cpp11_alignment.i | 3 ++- Examples/test-suite/cpp11_template_explicit.i | 15 +++++++++++---- 3 files changed, 19 insertions(+), 11 deletions(-) diff --git a/Examples/test-suite/cpp11_alias_nested_template_scoping.i b/Examples/test-suite/cpp11_alias_nested_template_scoping.i index 0cf5ea35a..72814aa88 100644 --- a/Examples/test-suite/cpp11_alias_nested_template_scoping.i +++ b/Examples/test-suite/cpp11_alias_nested_template_scoping.i @@ -19,17 +19,17 @@ template struct Y { typedef T2 another_type; }; value_type create1() const { return T(); } - Y::value_type create2() const { return T(); } - Y::value_type create3() const { return T(); } - YY::value_type create4() const { return T(); } - Y::YY::value_type create5() const { return T(); } + typename Y::value_type create2() const { return T(); } + typename Y::value_type create3() const { return T(); } + typename YY::value_type create4() const { return T(); } + typename Y::YY::value_type create5() const { return T(); } Y::YYY::value_type create6() const { return T(); } typename Y::template ZZZ::another_type create7() const { return T(); } // With global scope prefix - ::Y::value_type create13() const { return T(); } + typename ::Y::value_type create13() const { return T(); } - ::Y::YY::value_type create15() const { return T(); } + typename ::Y::YY::value_type create15() const { return T(); } ::Y::YYY::value_type create16() const { return T(); } typename ::Y::template ZZZ::another_type create17() const { return T(); } }; diff --git a/Examples/test-suite/cpp11_alignment.i b/Examples/test-suite/cpp11_alignment.i index fb25c4ebb..135f63641 100644 --- a/Examples/test-suite/cpp11_alignment.i +++ b/Examples/test-suite/cpp11_alignment.i @@ -4,7 +4,8 @@ struct A { int member; }; -const int align1 = alignof(A::member); +const int align1 = alignof(int); +const int align2 = alignof(int *); %} %{ diff --git a/Examples/test-suite/cpp11_template_explicit.i b/Examples/test-suite/cpp11_template_explicit.i index f8fca4fae..71752f822 100644 --- a/Examples/test-suite/cpp11_template_explicit.i +++ b/Examples/test-suite/cpp11_template_explicit.i @@ -8,7 +8,8 @@ %inline %{ -template struct Temper { +template class Temper { +public: T val; }; @@ -18,14 +19,20 @@ public: int memberFunction() { return 100; } }; +class B { +public: + short member; + short memberFunction() { return 100; } +}; + template class Temper; -extern template class Temper; +extern template class Temper; template class Temper; -extern template class Temper; +extern template class Temper; template class Temper; -extern template class Temper; +extern template class Temper; %} %template(TemperInt) Temper; From a8055b45d755360580b327fdecc393c66fc06061 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 19:37:00 +0100 Subject: [PATCH 079/134] Check Dispose is called in C# auto_ptr test --- Examples/test-suite/csharp/li_std_auto_ptr_runme.cs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/Examples/test-suite/csharp/li_std_auto_ptr_runme.cs b/Examples/test-suite/csharp/li_std_auto_ptr_runme.cs index 1f66042a6..863b86701 100644 --- a/Examples/test-suite/csharp/li_std_auto_ptr_runme.cs +++ b/Examples/test-suite/csharp/li_std_auto_ptr_runme.cs @@ -19,6 +19,13 @@ public class li_std_auto_ptr_runme { if (Klass.getTotal_count() != 2) throw new Exception("number of objects should be 2"); + using (Klass k3 = li_std_auto_ptr.makeKlassAutoPtr("second")) { + if (Klass.getTotal_count() != 3) + throw new Exception("number of objects should be 3"); + } + if (Klass.getTotal_count() != 2) + throw new Exception("number of objects should be 2"); + k1 = null; { int countdown = 500; From be8061c7f58bb574450725aeba3151b6c9c9ae56 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 8 Apr 2019 19:44:10 +0100 Subject: [PATCH 080/134] Cosmetic C# Makefile tweak --- Examples/Makefile.in | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Examples/Makefile.in b/Examples/Makefile.in index 5ffc0095e..b2cbb65da 100644 --- a/Examples/Makefile.in +++ b/Examples/Makefile.in @@ -1094,7 +1094,7 @@ CSHARPCFLAGS = @CSHARPCFLAGS@ CSHARPFLAGS = CSHARPOPTIONS = CSHARPSO = @CSHARPSO@ -CSHARP_RUNME = $(CSHARPCILINTERPRETER) $(CSHARPCILINTERPRETER_FLAGS) ./$(RUNME).exe +CSHARP_RUNME = ./$(RUNME).exe # ---------------------------------------------------------------- # Build a CSharp dynamically loadable module (C) @@ -1132,7 +1132,7 @@ csharp_compile: $(SRCDIR_SRCS) # ----------------------------------------------------------------- csharp_run: - env LD_LIBRARY_PATH=$$PWD $(RUNTOOL) $(CSHARP_RUNME) $(RUNPIPE) + env LD_LIBRARY_PATH=$$PWD $(RUNTOOL) $(CSHARPCILINTERPRETER) $(CSHARPCILINTERPRETER_FLAGS) $(CSHARP_RUNME) $(RUNPIPE) # ----------------------------------------------------------------- # Version display From d6746379a1d63b9c588d9642cd1d0d6608629e20 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 9 Apr 2019 06:50:25 +0100 Subject: [PATCH 081/134] Use wine on Linux to test executable when building windows zip file --- Tools/mkwindows.sh | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/Tools/mkwindows.sh b/Tools/mkwindows.sh index 0651bbd60..e6ae84350 100755 --- a/Tools/mkwindows.sh +++ b/Tools/mkwindows.sh @@ -9,6 +9,8 @@ # path to zip program zip= +wine= + # options for configure extraconfigureoptions= compileflags="-O2 -Wall -Wextra" @@ -41,6 +43,11 @@ else echo "Building native Windows executable on Linux" if test x$zip = x; then zip=zip + wine=$(which wine) + fi + if test x$wine = x; then + echo "Could not detect wine - please install wine-stable package." + exit 1; fi echo "Checking that mingw 32-bit gcc is installed/available" if test -n "`which i686-w64-mingw32-gcc`" ; then @@ -109,9 +116,9 @@ if test -f "$tarball"; then echo "Compiling (quietly)..." make > build.log echo "Simple check to see if swig.exe runs..." - env LD_LIBRARY_PATH= PATH= ./swig.exe -version || exit 1 + env LD_LIBRARY_PATH= PATH= $wine ./swig.exe -version || exit 1 echo "Simple check to see if ccache-swig.exe runs..." - env LD_LIBRARY_PATH= PATH= ./CCache/ccache-swig.exe -V || exit 1 + env LD_LIBRARY_PATH= PATH= $wine ./CCache/ccache-swig.exe -V || exit 1 echo "Creating $swigwinbasename.zip..." cd .. cp $swigbasename/swig.exe $swigwinbasename From 00528a1ef68dc2adbe3c34c23e9841a0715c428b Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 9 Apr 2019 19:15:12 +0100 Subject: [PATCH 082/134] Fix C# wrappers FxCop warning CA2002 in SWIGPendingException Fixes two warnings in each wrapper: warning : CA2002 : Microsoft.Reliability : 'examplePINVOKE.SWIGPendingException.Retrieve()' locks on a reference of type 'Type'. Replace this with a lock against an object with strong-identity. warning : CA2002 : Microsoft.Reliability : 'examplePINVOKE.SWIGPendingException.Set(Exception)' locks on a reference of type 'Type'. Replace this with a lock against an object with strong-identity. Use lock statement advice not to use typeof for locks, see https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/keywords/lock-statement --- CHANGES.current | 4 ++++ Lib/csharp/csharphead.swg | 9 +++++++-- 2 files changed, 11 insertions(+), 2 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 9e4b02d4d..6529ac87d 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,10 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-04-09: wsfulton + [C#] Fix FxCop warning CA2002 in SWIGPendingException - a lock on a reference of + type 'Type'. + 2019-03-30: wsfulton [Java, D] Add the parameters typemap attribute to the javadestruct, javadestruct_derived, ddispose, ddispose_derived typemaps to mirror enhanced diff --git a/Lib/csharp/csharphead.swg b/Lib/csharp/csharphead.swg index 0b55635b3..7db4c0e3c 100644 --- a/Lib/csharp/csharphead.swg +++ b/Lib/csharp/csharphead.swg @@ -244,6 +244,7 @@ SWIGEXPORT void SWIGSTDCALL SWIGRegisterExceptionArgumentCallbacks_$module( [global::System.ThreadStatic] private static global::System.Exception pendingException = null; private static int numExceptionsPending = 0; + private static global::System.Object exceptionsLock = null; public static bool Pending { get { @@ -259,7 +260,7 @@ SWIGEXPORT void SWIGSTDCALL SWIGRegisterExceptionArgumentCallbacks_$module( if (pendingException != null) throw new global::System.ApplicationException("FATAL: An earlier pending exception from unmanaged code was missed and thus not thrown (" + pendingException.ToString() + ")", e); pendingException = e; - lock(typeof($imclassname)) { + lock(exceptionsLock) { numExceptionsPending++; } } @@ -270,13 +271,17 @@ SWIGEXPORT void SWIGSTDCALL SWIGRegisterExceptionArgumentCallbacks_$module( if (pendingException != null) { e = pendingException; pendingException = null; - lock(typeof($imclassname)) { + lock(exceptionsLock) { numExceptionsPending--; } } } return e; } + + static SWIGPendingException() { + exceptionsLock = new global::System.Object(); + } } %} #endif // SWIG_CSHARP_NO_EXCEPTION_HELPER From 65056349cf436c9f2dc505cc9d51a51c309648b0 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 11 Apr 2019 19:13:10 +0100 Subject: [PATCH 083/134] Add release notes summary --- CHANGES.current | 18 ++++++++---------- RELEASENOTES | 29 +++++++++++++++++++++++++++++ 2 files changed, 37 insertions(+), 10 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 6529ac87d..3c819bd88 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -18,7 +18,7 @@ Version 4.0.0 (in progress) the contents are generated as the delete/dispose method's parameters declaration. 2019-03-30: wsfulton - [C#] #421 Fix CA1063 warning by implementing the recommended Dispose methods for + [C#] #421 Fix FxCop warning CA1063 by implementing the recommended Dispose methods for the IDisposable interface. Previously just the Dispose() method was generated. Now the Dispose() and Dispose(bool disposing) methods are generated. Changes are required if custom "csfinalize", "csdestruct" or "csdestruct_derived" @@ -99,13 +99,13 @@ Version 4.0.0 (in progress) string. 2019-02-22: tamuratak - #984 Add support for RTypedData introduced in Ruby 1.9.3. + [Ruby] #984 Add support for RTypedData introduced in Ruby 1.9.3. 2019-02-22: ZackerySpytz #1483 Fix compilation failures when a director class has final methods. 2019-02-21: wsfulton - #1240 Suppress Java 9 deprecation warnings on finalize method. + [Java] #1240 Suppress Java 9 deprecation warnings on finalize method. 2019-02-21: ZackerySpytz #1480 Fix some rejections of valid floating-point literals. @@ -933,7 +933,7 @@ Version 4.0.0 (in progress) u"\udcff" to the C layer (Python 3). 2017-11-24: joequant - Fix #1124 and return R_NilValue for null pointers + [R] Fix #1124 and return R_NilValue for null pointers 2017-11-29: wsfulton [Java] director exception handling improvements. @@ -978,7 +978,7 @@ Version 4.0.0 (in progress) 2017-10-07: olly Fix preprocessor handling of empty macro arguments to match that of - C/C++ compilers. Fixes https://github.com/swig/swig/pull/1111 and + C/C++ compilers. Fixes issue #1111 and https://sourceforge.net/p/swig/bugs/826/ 2017-10-06: wsfulton @@ -999,7 +999,7 @@ Version 4.0.0 (in progress) 2017-10-01: joequant allow R package names with docs allowing multiple get accessors in R - fix smrt-pointer and NAMESPACE support + fix smart-pointer and NAMESPACE support constructors now returning smart pointers (if class declared as such) smart-pointer classes deriving from parent smart-pointers @@ -1259,8 +1259,7 @@ Version 4.0.0 (in progress) 2017-08-05: olly [C++11] Allow static_assert at the top level (and disallow it right - after template). Fixes https://github.com/swig/swig/issues/1031 - reported by Artem V L. + after template). Fixes issue 1031 reported by Artem V L. 2017-08-02: wsfulton Fix incorrectly shown warning when an empty template instantiation was used on a @@ -1364,8 +1363,7 @@ Version 4.0.0 (in progress) 2017-06-13: olly [Perl] Fix testsuite to work without . in @INC - it was removed in Perl 5.26 for security reasons, and has also been removed from - older versions in some distros. Fixes - https://github.com/swig/swig/issues/997 reported by lfam. + older versions in some distros. Fixes #997 reported by lfam. 2017-06-03: wsfulton Fix %import on a file containing a file scope %fragment forced inclusion to not diff --git a/RELEASENOTES b/RELEASENOTES index 5f6560c3c..3fe78f2e2 100644 --- a/RELEASENOTES +++ b/RELEASENOTES @@ -7,6 +7,35 @@ Release Notes Detailed release notes are available with the release and are also published on the SWIG web site at http://swig.org/release.html. +SWIG-4.0.0 summary: +- Support for Doxygen documentation comments which are parsed and + converted into JavaDoc or PyDoc comments. +- STL wrappers improved for C#, Java and Ruby. +- C++11 STL containers added for Java, Python and Ruby. +- Improved support for parsing C++11 and C++14 code. +- Various fixes for shared_ptr. +- Various C preprocessor corner case fixes. +- Corner case fixes for member function pointers. +- Python module overhaul by simplifying the generated code and turning + most optimizations on by default. +- %template improvements wrt scoping to align with C++ explicit + template instantiations. +- Added support for a command-line options file (sometimes called a + response file). +- Numerous enhancements and fixes for all supported target languages. +- SWIG now classifies the status of target languages into either + 'Experimental' or 'Supported' to indicate the expected maturity + level. +- Support for CFFI, Allegrocl, Chicken, CLISP, S-EXP, UFFI, Pike, + Modula3 has been removed. +- Octave 4.4-5.1 support added. +- PHP5 support removed, PHP7 is now the supported PHP version. +- Minimum Python version required is now 2.7, 3.2-3.7 are the only + other versions supported. +- Added support for Javascript NodeJS versions 2-10. +- OCaml support is much improved and updated, minimum OCaml version + required is now 3.12.0. + SWIG-3.0.12 summary: - Add support for Octave-4.2. - Enhance %extend to support template functions. From 892f0fdc6ba2260f058f97b1e5e989baf7c56112 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 11 Apr 2019 19:42:40 +0100 Subject: [PATCH 084/134] Update ax_boost_base.m4 to latest from autoconf archive Updated to serial #45. This is in preparation to a possible fix for issue #1435. The use of AS_CASE requires autoconf-2.60 or later. --- Tools/config/ax_boost_base.m4 | 248 ++++++++++++++++++---------------- configure.ac | 10 +- 2 files changed, 133 insertions(+), 125 deletions(-) diff --git a/Tools/config/ax_boost_base.m4 b/Tools/config/ax_boost_base.m4 index 0e0f266dc..d54039576 100644 --- a/Tools/config/ax_boost_base.m4 +++ b/Tools/config/ax_boost_base.m4 @@ -1,5 +1,5 @@ # =========================================================================== -# http://www.gnu.org/software/autoconf-archive/ax_boost_base.html +# https://www.gnu.org/software/autoconf-archive/ax_boost_base.html # =========================================================================== # # SYNOPSIS @@ -10,7 +10,7 @@ # # Test for the Boost C++ libraries of a particular version (or newer) # -# If no path to the installed boost library is given the macro searches +# If no path to the installed boost library is given the macro searchs # under /usr, /usr/local, /opt and /opt/local and evaluates the # $BOOST_ROOT environment variable. Further documentation is available at # . @@ -33,7 +33,15 @@ # and this notice are preserved. This file is offered as-is, without any # warranty. -#serial 26 +#serial 45 + +# example boost program (need to pass version) +m4_define([_AX_BOOST_BASE_PROGRAM], + [AC_LANG_PROGRAM([[ +#include +]],[[ +(void) ((void)sizeof(char[1 - 2*!!((BOOST_VERSION) < ($1))])); +]])]) AC_DEFUN([AX_BOOST_BASE], [ @@ -44,104 +52,121 @@ AC_ARG_WITH([boost], or disable it (ARG=no) @<:@ARG=yes@:>@ ])], [ - if test "$withval" = "no"; then - want_boost="no" - elif test "$withval" = "yes"; then - want_boost="yes" - ac_boost_path="" - else - want_boost="yes" - ac_boost_path="$withval" - fi + AS_CASE([$withval], + [no],[want_boost="no";_AX_BOOST_BASE_boost_path=""], + [yes],[want_boost="yes";_AX_BOOST_BASE_boost_path=""], + [want_boost="yes";_AX_BOOST_BASE_boost_path="$withval"]) ], [want_boost="yes"]) AC_ARG_WITH([boost-libdir], - AS_HELP_STRING([--with-boost-libdir=LIB_DIR], - [Force given directory for boost libraries. Note that this will override library path detection, so use this parameter only if default library detection fails and you know exactly where your boost libraries are located.]), - [ - if test -d "$withval" - then - ac_boost_lib_path="$withval" - else - AC_MSG_ERROR(--with-boost-libdir expected directory name) - fi - ], - [ac_boost_lib_path=""] -) + [AS_HELP_STRING([--with-boost-libdir=LIB_DIR], + [Force given directory for boost libraries. + Note that this will override library path detection, + so use this parameter only if default library detection fails + and you know exactly where your boost libraries are located.])], + [ + AS_IF([test -d "$withval"], + [_AX_BOOST_BASE_boost_lib_path="$withval"], + [AC_MSG_ERROR([--with-boost-libdir expected directory name])]) + ], + [_AX_BOOST_BASE_boost_lib_path=""]) -if test "x$want_boost" = "xyes"; then - boost_lib_version_req=ifelse([$1], ,1.20.0,$1) - boost_lib_version_req_shorten=`expr $boost_lib_version_req : '\([[0-9]]*\.[[0-9]]*\)'` - boost_lib_version_req_major=`expr $boost_lib_version_req : '\([[0-9]]*\)'` - boost_lib_version_req_minor=`expr $boost_lib_version_req : '[[0-9]]*\.\([[0-9]]*\)'` - boost_lib_version_req_sub_minor=`expr $boost_lib_version_req : '[[0-9]]*\.[[0-9]]*\.\([[0-9]]*\)'` - if test "x$boost_lib_version_req_sub_minor" = "x" ; then - boost_lib_version_req_sub_minor="0" - fi - WANT_BOOST_VERSION=`expr $boost_lib_version_req_major \* 100000 \+ $boost_lib_version_req_minor \* 100 \+ $boost_lib_version_req_sub_minor` - AC_MSG_CHECKING(for boostlib >= $boost_lib_version_req) +BOOST_LDFLAGS="" +BOOST_CPPFLAGS="" +AS_IF([test "x$want_boost" = "xyes"], + [_AX_BOOST_BASE_RUNDETECT([$1],[$2],[$3])]) +AC_SUBST(BOOST_CPPFLAGS) +AC_SUBST(BOOST_LDFLAGS) +]) + + +# convert a version string in $2 to numeric and affect to polymorphic var $1 +AC_DEFUN([_AX_BOOST_BASE_TONUMERICVERSION],[ + AS_IF([test "x$2" = "x"],[_AX_BOOST_BASE_TONUMERICVERSION_req="1.20.0"],[_AX_BOOST_BASE_TONUMERICVERSION_req="$2"]) + _AX_BOOST_BASE_TONUMERICVERSION_req_shorten=`expr $_AX_BOOST_BASE_TONUMERICVERSION_req : '\([[0-9]]*\.[[0-9]]*\)'` + _AX_BOOST_BASE_TONUMERICVERSION_req_major=`expr $_AX_BOOST_BASE_TONUMERICVERSION_req : '\([[0-9]]*\)'` + AS_IF([test "x$_AX_BOOST_BASE_TONUMERICVERSION_req_major" = "x"], + [AC_MSG_ERROR([You should at least specify libboost major version])]) + _AX_BOOST_BASE_TONUMERICVERSION_req_minor=`expr $_AX_BOOST_BASE_TONUMERICVERSION_req : '[[0-9]]*\.\([[0-9]]*\)'` + AS_IF([test "x$_AX_BOOST_BASE_TONUMERICVERSION_req_minor" = "x"], + [_AX_BOOST_BASE_TONUMERICVERSION_req_minor="0"]) + _AX_BOOST_BASE_TONUMERICVERSION_req_sub_minor=`expr $_AX_BOOST_BASE_TONUMERICVERSION_req : '[[0-9]]*\.[[0-9]]*\.\([[0-9]]*\)'` + AS_IF([test "X$_AX_BOOST_BASE_TONUMERICVERSION_req_sub_minor" = "X"], + [_AX_BOOST_BASE_TONUMERICVERSION_req_sub_minor="0"]) + _AX_BOOST_BASE_TONUMERICVERSION_RET=`expr $_AX_BOOST_BASE_TONUMERICVERSION_req_major \* 100000 \+ $_AX_BOOST_BASE_TONUMERICVERSION_req_minor \* 100 \+ $_AX_BOOST_BASE_TONUMERICVERSION_req_sub_minor` + AS_VAR_SET($1,$_AX_BOOST_BASE_TONUMERICVERSION_RET) +]) + +dnl Run the detection of boost should be run only if $want_boost +AC_DEFUN([_AX_BOOST_BASE_RUNDETECT],[ + _AX_BOOST_BASE_TONUMERICVERSION(WANT_BOOST_VERSION,[$1]) succeeded=no + + AC_REQUIRE([AC_CANONICAL_HOST]) dnl On 64-bit systems check for system libraries in both lib64 and lib. dnl The former is specified by FHS, but e.g. Debian does not adhere to dnl this (as it rises problems for generic multi-arch support). dnl The last entry in the list is chosen by default when no libraries dnl are found, e.g. when only header-only libraries are installed! - libsubdirs="lib" - ax_arch=`uname -m` - case $ax_arch in - x86_64) - libsubdirs="lib64 libx32 lib lib64" - ;; - ppc64|s390x|sparc64|aarch64|ppc64le) - libsubdirs="lib64 lib lib64 ppc64le" - ;; - esac + AS_CASE([${host_cpu}], + [x86_64],[libsubdirs="lib64 libx32 lib lib64"], + [ppc64|powerpc64|s390x|sparc64|aarch64|ppc64le|powerpc64le|riscv64],[libsubdirs="lib64 lib lib64"], + [libsubdirs="lib"] + ) dnl allow for real multi-arch paths e.g. /usr/lib/x86_64-linux-gnu. Give dnl them priority over the other paths since, if libs are found there, they dnl are almost assuredly the ones desired. - AC_REQUIRE([AC_CANONICAL_HOST]) - libsubdirs="lib/${host_cpu}-${host_os} $libsubdirs" - - case ${host_cpu} in - i?86) - libsubdirs="lib/i386-${host_os} $libsubdirs" - ;; - esac + AS_CASE([${host_cpu}], + [i?86],[multiarch_libsubdir="lib/i386-${host_os}"], + [multiarch_libsubdir="lib/${host_cpu}-${host_os}"] + ) dnl first we check the system location for boost libraries dnl this location ist chosen if boost libraries are installed with the --layout=system option dnl or if you install boost with RPM - if test "$ac_boost_path" != ""; then - BOOST_CPPFLAGS="-I$ac_boost_path/include" - for ac_boost_path_tmp in $libsubdirs; do - if test -d "$ac_boost_path"/"$ac_boost_path_tmp" ; then - BOOST_LDFLAGS="-L$ac_boost_path/$ac_boost_path_tmp" - break - fi - done - elif test "$cross_compiling" != yes; then - for ac_boost_path_tmp in /usr /usr/local /opt /opt/local ; do - if test -d "$ac_boost_path_tmp/include/boost" && test -r "$ac_boost_path_tmp/include/boost"; then - for libsubdir in $libsubdirs ; do - if ls "$ac_boost_path_tmp/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi + AS_IF([test "x$_AX_BOOST_BASE_boost_path" != "x"],[ + AC_MSG_CHECKING([for boostlib >= $1 ($WANT_BOOST_VERSION) includes in "$_AX_BOOST_BASE_boost_path/include"]) + AS_IF([test -d "$_AX_BOOST_BASE_boost_path/include" && test -r "$_AX_BOOST_BASE_boost_path/include"],[ + AC_MSG_RESULT([yes]) + BOOST_CPPFLAGS="-I$_AX_BOOST_BASE_boost_path/include" + for _AX_BOOST_BASE_boost_path_tmp in $multiarch_libsubdir $libsubdirs; do + AC_MSG_CHECKING([for boostlib >= $1 ($WANT_BOOST_VERSION) lib path in "$_AX_BOOST_BASE_boost_path/$_AX_BOOST_BASE_boost_path_tmp"]) + AS_IF([test -d "$_AX_BOOST_BASE_boost_path/$_AX_BOOST_BASE_boost_path_tmp" && test -r "$_AX_BOOST_BASE_boost_path/$_AX_BOOST_BASE_boost_path_tmp" ],[ + AC_MSG_RESULT([yes]) + BOOST_LDFLAGS="-L$_AX_BOOST_BASE_boost_path/$_AX_BOOST_BASE_boost_path_tmp"; + break; + ], + [AC_MSG_RESULT([no])]) + done],[ + AC_MSG_RESULT([no])]) + ],[ + if test X"$cross_compiling" = Xyes; then + search_libsubdirs=$multiarch_libsubdir + else + search_libsubdirs="$multiarch_libsubdir $libsubdirs" + fi + for _AX_BOOST_BASE_boost_path_tmp in /usr /usr/local /opt /opt/local ; do + if test -d "$_AX_BOOST_BASE_boost_path_tmp/include/boost" && test -r "$_AX_BOOST_BASE_boost_path_tmp/include/boost" ; then + for libsubdir in $search_libsubdirs ; do + if ls "$_AX_BOOST_BASE_boost_path_tmp/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi done - BOOST_LDFLAGS="-L$ac_boost_path_tmp/$libsubdir" - BOOST_CPPFLAGS="-I$ac_boost_path_tmp/include" + BOOST_LDFLAGS="-L$_AX_BOOST_BASE_boost_path_tmp/$libsubdir" + BOOST_CPPFLAGS="-I$_AX_BOOST_BASE_boost_path_tmp/include" break; fi done - fi + ]) dnl overwrite ld flags if we have required special directory with dnl --with-boost-libdir parameter - if test "$ac_boost_lib_path" != ""; then - BOOST_LDFLAGS="-L$ac_boost_lib_path" - fi + AS_IF([test "x$_AX_BOOST_BASE_boost_lib_path" != "x"], + [BOOST_LDFLAGS="-L$_AX_BOOST_BASE_boost_lib_path"]) + AC_MSG_CHECKING([for boostlib >= $1 ($WANT_BOOST_VERSION)]) CPPFLAGS_SAVED="$CPPFLAGS" CPPFLAGS="$CPPFLAGS $BOOST_CPPFLAGS" export CPPFLAGS @@ -152,15 +177,7 @@ if test "x$want_boost" = "xyes"; then AC_REQUIRE([AC_PROG_CXX]) AC_LANG_PUSH(C++) - AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[ - @%:@include - ]], [[ - #if BOOST_VERSION >= $WANT_BOOST_VERSION - // Everything is okay - #else - # error Boost version is too old - #endif - ]])],[ + AC_COMPILE_IFELSE([_AX_BOOST_BASE_PROGRAM($WANT_BOOST_VERSION)],[ AC_MSG_RESULT(yes) succeeded=yes found_system=yes @@ -172,40 +189,50 @@ if test "x$want_boost" = "xyes"; then dnl if we found no boost with system layout we search for boost libraries dnl built and installed without the --layout=system option or for a staged(not installed) version - if test "x$succeeded" != "xyes"; then + if test "x$succeeded" != "xyes" ; then CPPFLAGS="$CPPFLAGS_SAVED" LDFLAGS="$LDFLAGS_SAVED" BOOST_CPPFLAGS= - BOOST_LDFLAGS= + if test -z "$_AX_BOOST_BASE_boost_lib_path" ; then + BOOST_LDFLAGS= + fi _version=0 - if test "$ac_boost_path" != ""; then - if test -d "$ac_boost_path" && test -r "$ac_boost_path"; then - for i in `ls -d $ac_boost_path/include/boost-* 2>/dev/null`; do - _version_tmp=`echo $i | sed "s#$ac_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'` + if test -n "$_AX_BOOST_BASE_boost_path" ; then + if test -d "$_AX_BOOST_BASE_boost_path" && test -r "$_AX_BOOST_BASE_boost_path"; then + for i in `ls -d $_AX_BOOST_BASE_boost_path/include/boost-* 2>/dev/null`; do + _version_tmp=`echo $i | sed "s#$_AX_BOOST_BASE_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'` V_CHECK=`expr $_version_tmp \> $_version` - if test "$V_CHECK" = "1" ; then + if test "x$V_CHECK" = "x1" ; then _version=$_version_tmp fi VERSION_UNDERSCORE=`echo $_version | sed 's/\./_/'` - BOOST_CPPFLAGS="-I$ac_boost_path/include/boost-$VERSION_UNDERSCORE" + BOOST_CPPFLAGS="-I$_AX_BOOST_BASE_boost_path/include/boost-$VERSION_UNDERSCORE" done dnl if nothing found search for layout used in Windows distributions if test -z "$BOOST_CPPFLAGS"; then - if test -d "$ac_boost_path/boost" && test -r "$ac_boost_path/boost"; then - BOOST_CPPFLAGS="-I$ac_boost_path" + if test -d "$_AX_BOOST_BASE_boost_path/boost" && test -r "$_AX_BOOST_BASE_boost_path/boost"; then + BOOST_CPPFLAGS="-I$_AX_BOOST_BASE_boost_path" fi fi + dnl if we found something and BOOST_LDFLAGS was unset before + dnl (because "$_AX_BOOST_BASE_boost_lib_path" = ""), set it here. + if test -n "$BOOST_CPPFLAGS" && test -z "$BOOST_LDFLAGS"; then + for libsubdir in $libsubdirs ; do + if ls "$_AX_BOOST_BASE_boost_path/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi + done + BOOST_LDFLAGS="-L$_AX_BOOST_BASE_boost_path/$libsubdir" + fi fi else - if test "$cross_compiling" != yes; then - for ac_boost_path in /usr /usr/local /opt /opt/local ; do - if test -d "$ac_boost_path" && test -r "$ac_boost_path"; then - for i in `ls -d $ac_boost_path/include/boost-* 2>/dev/null`; do - _version_tmp=`echo $i | sed "s#$ac_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'` + if test "x$cross_compiling" != "xyes" ; then + for _AX_BOOST_BASE_boost_path in /usr /usr/local /opt /opt/local ; do + if test -d "$_AX_BOOST_BASE_boost_path" && test -r "$_AX_BOOST_BASE_boost_path" ; then + for i in `ls -d $_AX_BOOST_BASE_boost_path/include/boost-* 2>/dev/null`; do + _version_tmp=`echo $i | sed "s#$_AX_BOOST_BASE_boost_path##" | sed 's/\/include\/boost-//' | sed 's/_/./'` V_CHECK=`expr $_version_tmp \> $_version` - if test "$V_CHECK" = "1" ; then + if test "x$V_CHECK" = "x1" ; then _version=$_version_tmp - best_path=$ac_boost_path + best_path=$_AX_BOOST_BASE_boost_path fi done fi @@ -213,7 +240,7 @@ if test "x$want_boost" = "xyes"; then VERSION_UNDERSCORE=`echo $_version | sed 's/\./_/'` BOOST_CPPFLAGS="-I$best_path/include/boost-$VERSION_UNDERSCORE" - if test "$ac_boost_lib_path" = ""; then + if test -z "$_AX_BOOST_BASE_boost_lib_path" ; then for libsubdir in $libsubdirs ; do if ls "$best_path/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi done @@ -221,7 +248,7 @@ if test "x$want_boost" = "xyes"; then fi fi - if test "x$BOOST_ROOT" != "x"; then + if test -n "$BOOST_ROOT" ; then for libsubdir in $libsubdirs ; do if ls "$BOOST_ROOT/stage/$libsubdir/libboost_"* >/dev/null 2>&1 ; then break; fi done @@ -230,7 +257,7 @@ if test "x$want_boost" = "xyes"; then stage_version=`echo $version_dir | sed 's/boost_//' | sed 's/_/./g'` stage_version_shorten=`expr $stage_version : '\([[0-9]]*\.[[0-9]]*\)'` V_CHECK=`expr $stage_version_shorten \>\= $_version` - if test "$V_CHECK" = "1" -a "$ac_boost_lib_path" = "" ; then + if test "x$V_CHECK" = "x1" && test -z "$_AX_BOOST_BASE_boost_lib_path" ; then AC_MSG_NOTICE(We will use a staged boost library from $BOOST_ROOT) BOOST_CPPFLAGS="-I$BOOST_ROOT" BOOST_LDFLAGS="-L$BOOST_ROOT/stage/$libsubdir" @@ -245,15 +272,7 @@ if test "x$want_boost" = "xyes"; then export LDFLAGS AC_LANG_PUSH(C++) - AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[ - @%:@include - ]], [[ - #if BOOST_VERSION >= $WANT_BOOST_VERSION - // Everything is okay - #else - # error Boost version is too old - #endif - ]])],[ + AC_COMPILE_IFELSE([_AX_BOOST_BASE_PROGRAM($WANT_BOOST_VERSION)],[ AC_MSG_RESULT(yes) succeeded=yes found_system=yes @@ -262,17 +281,15 @@ if test "x$want_boost" = "xyes"; then AC_LANG_POP([C++]) fi - if test "$succeeded" != "yes" ; then - if test "$_version" = "0" ; then - AC_MSG_NOTICE([[We could not detect the boost libraries (version $boost_lib_version_req_shorten or higher). If you have a staged boost library (still not installed) please specify \$BOOST_ROOT in your environment and do not give a PATH to --with-boost option. If you are sure you have boost installed, then check your version number looking in . See http://randspringer.de/boost for more documentation.]]) + if test "x$succeeded" != "xyes" ; then + if test "x$_version" = "x0" ; then + AC_MSG_NOTICE([[We could not detect the boost libraries (version $1 or higher). If you have a staged boost library (still not installed) please specify \$BOOST_ROOT in your environment and do not give a PATH to --with-boost option. If you are sure you have boost installed, then check your version number looking in . See http://randspringer.de/boost for more documentation.]]) else AC_MSG_NOTICE([Your boost libraries seems to old (version $_version).]) fi # execute ACTION-IF-NOT-FOUND (if present): ifelse([$3], , :, [$3]) else - AC_SUBST(BOOST_CPPFLAGS) - AC_SUBST(BOOST_LDFLAGS) AC_DEFINE(HAVE_BOOST,,[define if the Boost library is available]) # execute ACTION-IF-FOUND (if present): ifelse([$2], , :, [$2]) @@ -280,6 +297,5 @@ if test "x$want_boost" = "xyes"; then CPPFLAGS="$CPPFLAGS_SAVED" LDFLAGS="$LDFLAGS_SAVED" -fi ]) diff --git a/configure.ac b/configure.ac index 6380260f1..1873797d6 100644 --- a/configure.ac +++ b/configure.ac @@ -3,10 +3,7 @@ dnl The macros which aren't shipped with the autotools are stored in the dnl Tools/config directory in .m4 files. AC_INIT([swig],[4.0.0],[http://www.swig.org]) - -dnl NB: When this requirement is increased to 2.60 or later, AC_PROG_SED -dnl definition below can be removed -AC_PREREQ(2.58) +AC_PREREQ(2.60) AC_CONFIG_SRCDIR([Source/Swig/swig.h]) AC_CONFIG_AUX_DIR([Tools/config]) @@ -44,11 +41,6 @@ AC_CHECK_FUNC(popen, AC_DEFINE(HAVE_POPEN, 1, [Define if popen is available]), A fi dnl PCRE - -dnl AX_PATH_GENERIC() relies on AC_PROG_SED() but it is defined only in -dnl autoconf 2.60 so trivially predefine it ourselves for the older versions -m4_ifdef([AC_PROG_SED],, [AC_DEFUN([AC_PROG_SED], [AC_PATH_PROG([SED], sed)])]) - AC_ARG_WITH([pcre], [AS_HELP_STRING([--without-pcre], [Disable support for regular expressions using PCRE])], From 1955758f276279d82916608aa49cb8456367844e Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 11 Apr 2019 19:51:23 +0100 Subject: [PATCH 085/134] Update ax_path_generic.m4 to latest from autoconf archive Purely cosmetic change Updated to serial #17. --- Tools/config/ax_path_generic.m4 | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Tools/config/ax_path_generic.m4 b/Tools/config/ax_path_generic.m4 index f77fc78d6..87966890b 100644 --- a/Tools/config/ax_path_generic.m4 +++ b/Tools/config/ax_path_generic.m4 @@ -1,5 +1,5 @@ # =========================================================================== -# http://www.gnu.org/software/autoconf-archive/ax_path_generic.html +# https://www.gnu.org/software/autoconf-archive/ax_path_generic.html # =========================================================================== # # SYNOPSIS @@ -14,11 +14,11 @@ # The script must support `--cflags' and `--libs' args. If MINIMUM-VERSION # is specified, the script must also support the `--version' arg. If the # `--with-library-[exec-]prefix' arguments to ./configure are given, it -# must also support `--prefix' and `--exec-prefix'. Prefereable use +# must also support `--prefix' and `--exec-prefix'. Preferably use # CONFIG-SCRIPTS as config script, CFLAGS-ARG instead of `--cflags` and # LIBS-ARG instead of `--libs`, if given. # -# The SED-EXPR-EXTRACTOR parameter representes the expression used in sed +# The SED-EXPR-EXTRACTOR parameter represents the expression used in sed # to extract the version number. Use it if your 'foo-config --version' # dumps something like 'Foo library v1.0.0 (alfa)' instead of '1.0.0'. # @@ -69,7 +69,7 @@ # and this notice are preserved. This file is offered as-is, without any # warranty. -#serial 13 +#serial 17 AU_ALIAS([AC_PATH_GENERIC], [AX_PATH_GENERIC]) AC_DEFUN([AX_PATH_GENERIC],[ From e15c11248070169847f51feb2d2256a82502bec3 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 11 Apr 2019 19:56:30 +0100 Subject: [PATCH 086/134] Update ax_compare_version.m4 to latest from autoconf archive Purely cosmetic changes Updated to serial #13 --- Tools/config/ax_compare_version.m4 | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Tools/config/ax_compare_version.m4 b/Tools/config/ax_compare_version.m4 index 74dc0fdd9..ffb4997e8 100644 --- a/Tools/config/ax_compare_version.m4 +++ b/Tools/config/ax_compare_version.m4 @@ -1,5 +1,5 @@ # =========================================================================== -# http://www.gnu.org/software/autoconf-archive/ax_compare_version.html +# https://www.gnu.org/software/autoconf-archive/ax_compare_version.html # =========================================================================== # # SYNOPSIS @@ -79,7 +79,7 @@ # and this notice are preserved. This file is offered as-is, without any # warranty. -#serial 11 +#serial 13 dnl ######################################################################### AC_DEFUN([AX_COMPARE_VERSION], [ @@ -146,7 +146,7 @@ x$B" | sed 's/^ *//' | sort -r | sed "s/x${A}/true/;s/x${B}/false/;1q"` ], [.+],[ AC_WARNING( - [illegal OP numeric parameter: $2]) + [invalid OP numeric parameter: $2]) ],[]) # Pad zeros at end of numbers to make same length. @@ -162,7 +162,7 @@ x$B" | sed 's/^ *//' | sort -r | sed "s/x${A}/true/;s/x${B}/false/;1q"` [ne],[ test "x$A" != "x$B" && ax_compare_version=true ],[ - AC_WARNING([illegal OP parameter: $2]) + AC_WARNING([invalid OP parameter: $2]) ]) ]) From dc4fb85d003ac6fa5402fe795aceffb76f5e2f3b Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 11 Apr 2019 20:13:44 +0100 Subject: [PATCH 087/134] cpp11_thread_local testcase fix for Visual C++ --- Examples/test-suite/cpp11_thread_local.i | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Examples/test-suite/cpp11_thread_local.i b/Examples/test-suite/cpp11_thread_local.i index 6a1019824..21f21859b 100644 --- a/Examples/test-suite/cpp11_thread_local.i +++ b/Examples/test-suite/cpp11_thread_local.i @@ -20,8 +20,10 @@ extern "C++" thread_local int ecpptval; thread_local int ThreadLocals::stval = 11; thread_local int ThreadLocals::tsval = 22; +#if !defined(_MSC_VER) thread_local const int ThreadLocals::stcval88; thread_local const int ThreadLocals::tscval99; +#endif %} %{ From bc615e8a6e4428db5736636dad0377e2f8301a31 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 15 Apr 2019 19:01:52 +0100 Subject: [PATCH 088/134] Correct out of date html links --- Doc/Manual/Android.html | 4 ++-- Doc/Manual/CCache.html | 2 +- Doc/Manual/CSharp.html | 10 +++++----- Doc/Manual/Doxygen.html | 18 +++++++++--------- Doc/Manual/Go.html | 2 +- Doc/Manual/Introduction.html | 2 +- Doc/Manual/Java.html | 13 ++++++------- Doc/Manual/Javascript.html | 10 +++++----- Doc/Manual/Mzscheme.html | 2 +- Doc/Manual/Php.html | 2 +- Doc/Manual/Python.html | 6 +++--- Doc/Manual/Scilab.html | 4 ++-- Doc/Manual/Typemaps.html | 4 ++-- Doc/Manual/Windows.html | 2 +- 14 files changed, 40 insertions(+), 41 deletions(-) diff --git a/Doc/Manual/Android.html b/Doc/Manual/Android.html index 894724188..944a88d65 100644 --- a/Doc/Manual/Android.html +++ b/Doc/Manual/Android.html @@ -48,7 +48,7 @@ This chapter contains a few Android specific notes and examples.

    -The examples require the Android SDK and Android NDK which can be installed as per instructions in the links. +The examples require the Android SDK and Android NDK which can be installed as per instructions in the links. The Eclipse version is not required for these examples as just the command line tools are used (shown for Linux as the host, but Windows will be very similar, if not identical in most places). Add the SDK tools and NDK tools to your path and create a directory somewhere for your Android projects (adjust PATH as necessary to where you installed the tools):

    @@ -326,7 +326,7 @@ include $(BUILD_SHARED_LIBRARY)

    -See the Android NDK documentation for more on the NDK build system and getting started with the NDK. +See the Android NDK documentation for more on the NDK build system and getting started with the NDK. A simple invocation of ndk-build will compile the .c files and generate a shared object/system library. Output will be similar to:

    diff --git a/Doc/Manual/CCache.html b/Doc/Manual/CCache.html index 3a7db5c7b..edd435fa1 100644 --- a/Doc/Manual/CCache.html +++ b/Doc/Manual/CCache.html @@ -458,7 +458,7 @@ Thanks to the following people for their contributions to ccache

    ccache was written by Andrew Tridgell -http://samba.org/~tridge/. +https://www.samba.org/~tridge/. ccache was adapted to create ccache-swig for use with SWIG by William Fulton.

    If you wish to report a problem or make a suggestion then please email diff --git a/Doc/Manual/CSharp.html b/Doc/Manual/CSharp.html index 0526766b5..1fc2d211e 100644 --- a/Doc/Manual/CSharp.html +++ b/Doc/Manual/CSharp.html @@ -64,15 +64,15 @@ The wrapper code implementation uses C# and the Platform Invoke (PInvoke) interf The PInvoke interface has been chosen over Microsoft's Managed C++ interface as it is portable to both Microsoft Windows and non-Microsoft platforms. PInvoke is part of the ECMA/ISO C# specification. It is also better suited for robust production environments due to the Managed C++ flaw called the -Mixed DLL Loading Problem. +Mixed DLL Loading Problem. SWIG C# works equally well on non-Microsoft operating systems such as Linux, Solaris and Apple Mac using -Mono and Portable.NET. +Mono and Portable.NET.

    To get the most out of this chapter an understanding of interop is required. -The Microsoft Developer Network (MSDN) has a good reference guide in a section titled "Interop Marshaling". -Monodoc, available from the Mono project, has a very useful section titled Interop with native libraries. +The Microsoft Developer Network (MSDN) has a good reference guide in a section titled "Interop Marshaling". +Monodoc, available from the Mono project, has a very useful section titled Interop with native libraries.

    22.1.1 SWIG 2 Compatibility

    @@ -763,7 +763,7 @@ another thread may produce enough garbage to trigger garbage collection.

    -For more information, see the fixed statement in the C# language reference. +For more information, see the fixed statement in the C# language reference.

    diff --git a/Doc/Manual/Doxygen.html b/Doc/Manual/Doxygen.html index b14b05ba3..8a847bb7e 100644 --- a/Doc/Manual/Doxygen.html +++ b/Doc/Manual/Doxygen.html @@ -63,13 +63,13 @@ supported.

    The Doxygen Translation module of SWIG adds an extra layer of functionality to SWIG, allowing automated translation of Doxygen formatted comments +"http://www.doxygen.nl/manual/">Doxygen formatted comments from input files into a documentation language more suited for the target language. Currently this module only translates into Javadoc and Pydoc for the SWIG Java and Python modules. Other extensions could be added at a later date. The Doxygen Translation module originally started as -a Google Summer of +a Google Summer of Code proposal from Summer 2008.

    @@ -79,14 +79,14 @@ Code proposal from Summer 2008.

    To make use of the comment translation system, your documentation comments must be in properly formatted Doxygen. Doxygen comments can be +"http://www.doxygen.nl/manual/">Doxygen. Doxygen comments can be present in your main SWIG interface file or any header file that it imports. You are advised to be validate that your comments compile properly with Doxygen before you try to translate them. Doxygen itself is a more comprehensive tool and can provide you better feedback for correcting any syntax errors that may be present. Please look at Doxygen's Documenting the +"http://www.doxygen.nl/manual/docblocks.html"> Documenting the code for the full comment format specifications. However, SWIG's Doxygen parser will still report many errors and warnings found in comments (like unterminated strings or missing ending tags). @@ -94,7 +94,7 @@ in comments (like unterminated strings or missing ending tags).

    Currently, the whole subset of Doxygen comment styles is supported -(See +(See Documenting the code). Here they are:

    @@ -293,7 +293,7 @@ make much sense for the other languages without explicit ownership management.

    Doxygen syntax is rather rich and, in addition to simple commands such as @transferfull, it is also possible to define commands with arguments. -As explained in Doxygen documentation, +As explained in Doxygen documentation, the arguments can have a range of a single word, everything until the end of line or everything until the end of the next paragraph. Currently, only the "end of line" case is supported using the range="line" argument of the @@ -818,7 +818,7 @@ Here is the list of all Doxygen tags and the description of how they are transla

    Doxygen has a wealth of tags such as @latexonly that have no equivalent in Javadoc (all supported tags are listed in -Javadoc documentation). +Javadoc documentation). As a result several tags have no translation or particular use, such as some linking and section tags. These are suppressed with their content just printed out (if the tag has any @@ -1223,9 +1223,9 @@ completely (doxygen:notranslate feature). Then SWIG will just copy the comments to the proxy file and reformat them if needed, but all the comment content will be left as is. As Doxygen doesn't support special commands in Python comments -(see Doxygen +(see Doxygen docs), you may want to use some tool like doxypy -(http://code.foosel.org/doxypy) +(doxypy) to do the work.

    diff --git a/Doc/Manual/Go.html b/Doc/Manual/Go.html index 047b46edf..b16c764fb 100644 --- a/Doc/Manual/Go.html +++ b/Doc/Manual/Go.html @@ -1291,7 +1291,7 @@ fraction := modulename.Modf(5.0, ptr)

    Since this is ugly, you may want to wrap the swig-generated API with -some additional functions written in go that +some additional functions written in go that hide the ugly details.

    There are no char *OUTPUT typemaps. However you can diff --git a/Doc/Manual/Introduction.html b/Doc/Manual/Introduction.html index 1a2e26a6d..149e86877 100644 --- a/Doc/Manual/Introduction.html +++ b/Doc/Manual/Introduction.html @@ -464,7 +464,7 @@ for further information on this and other Autoconf macros.

    -There is growing support for SWIG in some build tools, for example CMake +There is growing support for SWIG in some build tools, for example CMake is a cross-platform, open-source build manager with built in support for SWIG. CMake can detect the SWIG executable and many of the target language libraries for linking against. CMake knows how to build shared libraries and loadable modules on many different operating systems. diff --git a/Doc/Manual/Java.html b/Doc/Manual/Java.html index cdefba6b4..e0c6aed03 100644 --- a/Doc/Manual/Java.html +++ b/Doc/Manual/Java.html @@ -1113,11 +1113,10 @@ Typesafe enums have their advantages over using plain integers in that they can However, there are limitations. For example, they cannot be used in switch statements and serialization is an issue. Please look at the following references for further information: -http://java.sun.com/developer/Books/shiftintojava/page1.html#replaceenums Replace Enums with Classes in Effective Java Programming on the Sun website, -Create enumerated constants in Java JavaWorld article, -Java Tip 133: More on typesafe enums and -Java Tip 122: Beware of Java typesafe enumerations JavaWorld tips. +Create enumerated constants in Java JavaWorld article, +Java Tip 133: More on typesafe enums and +Java Tip 122: Beware of Java typesafe enumerations JavaWorld tips.

    @@ -2763,7 +2762,7 @@ The finalize() method calls delete() which frees any malloc'd The idea is for delete() to be called when you have finished with the C/C++ object. Ideally you need not call delete(), but rather leave it to the garbage collector to call it from the finalizer. When a program exits, the garbage collector does not guarantee to call all finalizers. -An insight into the reasoning behind this can be obtained from Hans Boehm's Destructors, Finalizers, and Synchronization paper. +An insight into the reasoning behind this can be obtained from Hans Boehm's Destructors, Finalizers, and Synchronization paper. Depending on what the finalizers do and which operating system you use, this may or may not be a problem.

    @@ -2787,7 +2786,7 @@ Call the System.runFinalizersOnExit(true) or Runtime.getRuntime().r This method is inherently unsafe. It may result in finalizers being called on live objects while other threads are concurrently manipulating those objects, resulting in erratic behavior or deadlock.

    In many cases you will be lucky and find that it works, but it is not to be advocated. -Have a look at Java web site and search for runFinalizersOnExit. +Have a look at Java web site and search for runFinalizersOnExit.

  • @@ -5645,7 +5644,7 @@ This section describes how you can modify SWIG's default wrapping behavior for various C/C++ datatypes using the %typemap directive. You are advised to be familiar with the material in the "Typemaps" chapter. While not absolutely essential knowledge, this section assumes some familiarity with the Java Native Interface (JNI). -JNI documentation can be consulted either online at Sun's Java web site or from a good JNI book. +JNI documentation can be consulted either online at the Java web site or from a good JNI book. The following two books are recommended:

      diff --git a/Doc/Manual/Javascript.html b/Doc/Manual/Javascript.html index c328bbb6b..021d4e380 100644 --- a/Doc/Manual/Javascript.html +++ b/Doc/Manual/Javascript.html @@ -56,10 +56,10 @@

      Javascript is a prototype-based scripting language that is dynamic, weakly typed and has first-class functions. Its arguably the most popular language for web development. -Javascript has gone beyond being a browser-based scripting language and with node.js, it is also used as a backend development language.

      +Javascript has gone beyond being a browser-based scripting language and with node.js, it is also used as a backend development language.

      Native Javascript extensions can be used for applications that embed a web-browser view or that embed a Javascript engine (such as node.js). Extending a general purpose web-browser is not possible as this would be a severe security issue.

      -

      SWIG Javascript currently supports JavascriptCore, the Javascript engine used by Safari/Webkit, and v8, which is used by Chromium and node.js.

      -

      WebKit is a modern browser implementation available as open-source which can be embedded into an application. +

      SWIG Javascript currently supports JavascriptCore, the Javascript engine used by Safari/Webkit, and v8, which is used by Chromium and node.js.

      +

      WebKit is a modern browser implementation available as open-source which can be embedded into an application. With node-webkit there is a platform which uses Google's Chromium as Web-Browser widget and node.js for javascript extensions.

      @@ -289,7 +289,7 @@ extern bool example_initialize(JSGlobalContextRef context, JSObjectRef* exports)

      27.3.2.2 GTK

      -

      There is general information about programming GTK at GTK documentation and in the GTK tutorial, and for Webkit there is a Webkit GTK+ API Reference.

      +

      There is general information about programming GTK at GTK documentation and in the GTK tutorial, and for Webkit there is a Webkit GTK+ API Reference.

      An integration of a native extension 'example' would look like this:

      @@ -604,7 +604,7 @@ at ReadStream.EventEmitter.emit (events.js:98:17)
       at emitKey (readline.js:1095:12)

      -Note: In ECMAScript 5 there is no concept for classes. Instead each function can be used as a constructor function which is executed by the 'new' operator. Furthermore, during construction the key property prototype of the constructor function is used to attach a prototype instance to the created object. A prototype is essentially an object itself that is the first-class delegate of a class used whenever the access to a property of an object fails. The very same prototype instance is shared among all instances of one type. Prototypal inheritance is explained in more detail on in Inheritance and the prototype chain, for instance. +Note: In ECMAScript 5 there is no concept for classes. Instead each function can be used as a constructor function which is executed by the 'new' operator. Furthermore, during construction the key property prototype of the constructor function is used to attach a prototype instance to the created object. A prototype is essentially an object itself that is the first-class delegate of a class used whenever the access to a property of an object fails. The very same prototype instance is shared among all instances of one type. Prototypal inheritance is explained in more detail on in Inheritance and the prototype chain, for instance.

      27.5 Implementation

      diff --git a/Doc/Manual/Mzscheme.html b/Doc/Manual/Mzscheme.html index 860a5c412..aae181ee9 100644 --- a/Doc/Manual/Mzscheme.html +++ b/Doc/Manual/Mzscheme.html @@ -170,7 +170,7 @@ Some points of interest:

      -See the C API for more description of using the mechanism for adding extensions. The main documentation is here. +See the C API for more description of using the mechanism for adding extensions. The main documentation is here.

      diff --git a/Doc/Manual/Php.html b/Doc/Manual/Php.html index 1b8b2d468..d80731c5c 100644 --- a/Doc/Manual/Php.html +++ b/Doc/Manual/Php.html @@ -153,7 +153,7 @@ If the module is in PHP's default extension directory, you can omit the path.

      For some SAPIs (for example, the CLI SAPI) you can instead use the -dl() function to load +dl() function to load an extension at run time, by adding a line like this to the start of each PHP script which uses your extension:

      diff --git a/Doc/Manual/Python.html b/Doc/Manual/Python.html index 2554e9da3..5a3947d4d 100644 --- a/Doc/Manual/Python.html +++ b/Doc/Manual/Python.html @@ -301,7 +301,7 @@ how you might go about compiling and using the generated files.

      The preferred approach to building an extension module for Python is to compile it with distutils, which comes with all recent versions of Python -(Distutils Docs). +(Distutils Docs).

      @@ -2355,7 +2355,7 @@ wrapped class is turned into a new Python built-in type which inherits from from the wrapped methods. For more information about Python built-in extensions, please refer to the Python documentation:

      -

      http://docs.python.org/extending/newtypes.html

      +

      https://docs.python.org/3/extending/newtypes.html

      32.4.2.1 Limitations

      @@ -2574,7 +2574,7 @@ automatically converted to Python slot operators, refer to the file

      Read about all of the available Python slots here: -http://docs.python.org/c-api/typeobj.html

      +https://docs.python.org/3/c-api/typeobj.html

      There are two ways to define a Python slot function: dispatch to a diff --git a/Doc/Manual/Scilab.html b/Doc/Manual/Scilab.html index 29c4eacf0..88ab8043e 100644 --- a/Doc/Manual/Scilab.html +++ b/Doc/Manual/Scilab.html @@ -973,7 +973,7 @@ ans =

      -Note: the pointer to the struct works as described in Pointers. For example, the type of the struct pointer can be get with typeof, as following: +Note: the pointer to the struct works as described in Pointers. For example, the type of the struct pointer can be get with typeof, as following:

      @@ -1037,7 +1037,7 @@ ans  =
       

      -Note: like structs, class pointers are mapped as described in Pointers. Let's give an example which shows that each class pointer type is a new type in Scilab that can be used for example (through overloading) to implement a custom print for the Point class: +Note: like structs, class pointers are mapped as described in Pointers. Let's give an example which shows that each class pointer type is a new type in Scilab that can be used for example (through overloading) to implement a custom print for the Point class:

      diff --git a/Doc/Manual/Typemaps.html b/Doc/Manual/Typemaps.html
      index d34bb2801..8a31dbf10 100644
      --- a/Doc/Manual/Typemaps.html
      +++ b/Doc/Manual/Typemaps.html
      @@ -672,8 +672,8 @@ void wrap_foo(char *s, int x) {
       
       
       

      -SWIG has parallels to Aspect Oriented Software Development (AOP). -The AOP terminology with respect to SWIG typemaps can be viewed as follows: +SWIG has parallels to Aspect Oriented Software Development (AOP). +The AOP terminology with respect to SWIG typemaps can be viewed as follows:

      • Cross-cutting concerns: The cross-cutting concerns are the modularization of the functionality that the typemaps implement, which is primarily marshalling of types from/to the target language and C/C++. diff --git a/Doc/Manual/Windows.html b/Doc/Manual/Windows.html index 01caf6c7f..faea8b4e7 100644 --- a/Doc/Manual/Windows.html +++ b/Doc/Manual/Windows.html @@ -249,7 +249,7 @@ Execute the steps in the order shown and don't use spaces in path names. In fact
        1. Download the following packages from the MinGW download page - or MinGW SourceForge download page. + or MinGW SourceForge download page. Note that at the time of writing, the majority of these are in the Current release list and some are in the Snapshot or Previous release list.
            From 6791f8b769fd5a82392a3bd2b9d14daa78577a79 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 15 Apr 2019 19:31:32 +0100 Subject: [PATCH 089/134] Add linkchecker3 make target to check internal links Make sure all internal links use # anchors which are needed for wkhtmltopdf --- Doc/Manual/Javascript.html | 2 +- Doc/Manual/Makefile | 6 ++++++ Doc/Manual/SWIG.html | 2 +- Doc/Manual/SWIGPlus.html | 6 +++--- 4 files changed, 11 insertions(+), 5 deletions(-) diff --git a/Doc/Manual/Javascript.html b/Doc/Manual/Javascript.html index 021d4e380..417ee4585 100644 --- a/Doc/Manual/Javascript.html +++ b/Doc/Manual/Javascript.html @@ -1,7 +1,7 @@ - + diff --git a/Doc/Manual/Makefile b/Doc/Manual/Makefile index ee9a0af34..9505adb91 100644 --- a/Doc/Manual/Makefile +++ b/Doc/Manual/Makefile @@ -89,3 +89,9 @@ linkchecker2: cp *.png linkchecker-tmp (cd linkchecker-tmp && linkchecker --config=../linkchecker.config -F text --no-warnings SWIGDocumentation.html) +# Simple check for relative links (there shouldn't be any), they don't translate properly creating the .pdf doc +# with wkhtmltopdf. For example, href="SWIG.html" needs to be href="SWIG.html#SWIG" +linkchecker3: + @echo "The following list should just contain SWIGDocumentation.html and SWIGDocumentation.pdf," + @echo "as all links should have an anchor (with a #) or be a full url beginning http." + grep 'href="' *.html | sed -e 's/.*href="\(.*\)">.*$$/\1/' | grep -v "#" | grep -v "^http" | grep -v "^style.css" diff --git a/Doc/Manual/SWIG.html b/Doc/Manual/SWIG.html index 79d52ef56..64db9c6c6 100644 --- a/Doc/Manual/SWIG.html +++ b/Doc/Manual/SWIG.html @@ -1826,7 +1826,7 @@ When wrapping C code, simple use of identifiers/symbols with %rename us When wrapping C++ code, simple use of simple identifiers/symbols with %rename might be too limiting when using C++ features such as function overloading, default arguments, namespaces, template specialization etc. If you are using the %rename directive and C++, make sure you read the -SWIG and C++ chapter and in particular the section on +SWIG and C++ chapter and in particular the section on Renaming and ambiguity resolution for method overloading and default arguments.

            diff --git a/Doc/Manual/SWIGPlus.html b/Doc/Manual/SWIGPlus.html index 8ad9daedf..3a50cf8ce 100644 --- a/Doc/Manual/SWIGPlus.html +++ b/Doc/Manual/SWIGPlus.html @@ -88,9 +88,9 @@ This chapter describes SWIG's support for wrapping C++. It is mostly concerned about C++ as defined by the C++ 98 and 03 standards. For additions to the original C++ standard, please read the -SWIG and C++11, -SWIG and C++14 and -SWIG and C++17 chapters. +SWIG and C++11, +SWIG and C++14 and +SWIG and C++17 chapters. As a prerequisite, you should first read the chapter SWIG Basics to see how SWIG wraps ANSI C. Support for C++ builds upon ANSI C From 4e5d1891e6d5ce58d61a70a0c2be1305ce213e00 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 15 Apr 2019 22:55:56 +0100 Subject: [PATCH 090/134] testcase fixes for gcc-9 --- Examples/test-suite/cpp11_lambda_functions.i | 13 ++++++++----- Examples/test-suite/java/rename1_runme.java | 4 ---- Examples/test-suite/java/rename2_runme.java | 4 ---- Examples/test-suite/java/rename3_runme.java | 4 ---- Examples/test-suite/java/rename4_runme.java | 4 ---- Examples/test-suite/javascript/rename1_runme.js | 4 ---- Examples/test-suite/javascript/rename2_runme.js | 4 ---- Examples/test-suite/javascript/rename3_runme.js | 4 ---- Examples/test-suite/javascript/rename4_runme.js | 4 ---- Examples/test-suite/rename.h | 6 +----- Examples/test-suite/rename1.i | 7 +------ Examples/test-suite/rename2.i | 2 +- Examples/test-suite/rename3.i | 2 +- Examples/test-suite/rename4.i | 12 ++---------- 14 files changed, 14 insertions(+), 60 deletions(-) diff --git a/Examples/test-suite/cpp11_lambda_functions.i b/Examples/test-suite/cpp11_lambda_functions.i index fc02aadb2..3d7d76d60 100644 --- a/Examples/test-suite/cpp11_lambda_functions.i +++ b/Examples/test-suite/cpp11_lambda_functions.i @@ -43,14 +43,17 @@ auto lambda1 = [](int x, int y) -> int { return x+y; }; single statement "return expr;". */ auto lambda2 = [](int x, int y) { return x+y; }; -auto lambda3 = [&](int x, int y) { return x+y; }; -auto lambda4 = [=](int x, int y) { return x+y; }; int thing = 0; #ifdef SWIG -// Not strictly correct as captured variables should have non-automatic storage duration, ie shouldn't capture globals. gcc-4.7 warns about this, but we check that SWIG can parse this anyway. +// This is not strictly legal: non-local lambda expression cannot have a capture-default +// gcc-4.7 warns about this and gcc-9 gives an error, but we check that SWIG can parse this anyway. +auto lambda3 = [&](int x, int y) { return x+y; }; +auto lambda4 = [=](int x, int y) { return x+y; }; auto lambda5 = [=,&thing]() { return thing; }; #else -auto lambda5 = [=]() { return thing; }; +auto lambda3 = [](int x, int y) { return x+y; }; +auto lambda4 = [](int x, int y) { return x+y; }; +auto lambda5 = []() { return thing; }; #endif void fn() { @@ -115,6 +118,6 @@ int runLambdaInline() { // TODO int(*lambda101notauto)(int, int) = [] (int a, int b) { return a + b; }; int lambda102 = [] (int a, int b) mutable { return a + b; }(1, 2); -void lambda_init(int = ([=]{ return 0; })()); +void lambda_init(int = ([]{ return 0; })()); %} diff --git a/Examples/test-suite/java/rename1_runme.java b/Examples/test-suite/java/rename1_runme.java index 058de41fd..c04baf81f 100644 --- a/Examples/test-suite/java/rename1_runme.java +++ b/Examples/test-suite/java/rename1_runme.java @@ -24,7 +24,6 @@ public class rename1_runme { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } { XYZDouble xyz = new XYZDouble(); @@ -36,7 +35,6 @@ public class rename1_runme { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } { XYZKlass xyz = new XYZKlass(); @@ -48,7 +46,6 @@ public class rename1_runme { xyz.tMethod3(new Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } { XYZEnu xyz = new XYZEnu(); @@ -60,7 +57,6 @@ public class rename1_runme { xyz.tMethod4(Enu.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } { ABC abc = new ABC(); diff --git a/Examples/test-suite/java/rename2_runme.java b/Examples/test-suite/java/rename2_runme.java index b6a62dd1e..b97cc59ed 100644 --- a/Examples/test-suite/java/rename2_runme.java +++ b/Examples/test-suite/java/rename2_runme.java @@ -24,7 +24,6 @@ public class rename2_runme { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } { XYZDouble xyz = new XYZDouble(); @@ -36,7 +35,6 @@ public class rename2_runme { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } { XYZKlass xyz = new XYZKlass(); @@ -48,7 +46,6 @@ public class rename2_runme { xyz.tMethod3(new Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } { XYZEnu xyz = new XYZEnu(); @@ -60,7 +57,6 @@ public class rename2_runme { xyz.tMethod4(Enu.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } { ABC abc = new ABC(); diff --git a/Examples/test-suite/java/rename3_runme.java b/Examples/test-suite/java/rename3_runme.java index e1b090af8..222d54899 100644 --- a/Examples/test-suite/java/rename3_runme.java +++ b/Examples/test-suite/java/rename3_runme.java @@ -24,7 +24,6 @@ public class rename3_runme { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } { XYZDouble xyz = new XYZDouble(); @@ -36,7 +35,6 @@ public class rename3_runme { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } { XYZKlass xyz = new XYZKlass(); @@ -48,7 +46,6 @@ public class rename3_runme { xyz.tMethod3(new Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } { XYZEnu xyz = new XYZEnu(); @@ -60,7 +57,6 @@ public class rename3_runme { xyz.tMethod4(Enu.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } { ABC abc = new ABC(); diff --git a/Examples/test-suite/java/rename4_runme.java b/Examples/test-suite/java/rename4_runme.java index 69f909e9e..ef92dd300 100644 --- a/Examples/test-suite/java/rename4_runme.java +++ b/Examples/test-suite/java/rename4_runme.java @@ -24,7 +24,6 @@ public class rename4_runme { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } { XYZDouble xyz = new XYZDouble(); @@ -36,7 +35,6 @@ public class rename4_runme { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } { XYZKlass xyz = new XYZKlass(); @@ -48,7 +46,6 @@ public class rename4_runme { xyz.tMethod3(new Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } { XYZEnu xyz = new XYZEnu(); @@ -60,7 +57,6 @@ public class rename4_runme { xyz.tMethod4(Enu.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } { ABC abc = new ABC(); diff --git a/Examples/test-suite/javascript/rename1_runme.js b/Examples/test-suite/javascript/rename1_runme.js index 68ecc11b6..7b2ac37b6 100644 --- a/Examples/test-suite/javascript/rename1_runme.js +++ b/Examples/test-suite/javascript/rename1_runme.js @@ -10,7 +10,6 @@ function part1() { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } function part2() { @@ -23,7 +22,6 @@ function part2() { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } function part3(){ @@ -36,7 +34,6 @@ function part3(){ xyz.tMethod3(new rename.Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } function part4() { @@ -49,7 +46,6 @@ function part4() { xyz.tMethod4(rename.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } function part5() { diff --git a/Examples/test-suite/javascript/rename2_runme.js b/Examples/test-suite/javascript/rename2_runme.js index 99f478596..040c798bb 100644 --- a/Examples/test-suite/javascript/rename2_runme.js +++ b/Examples/test-suite/javascript/rename2_runme.js @@ -10,7 +10,6 @@ function part1() { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } function part2() { @@ -23,7 +22,6 @@ function part2() { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } function part3(){ @@ -36,7 +34,6 @@ function part3(){ xyz.tMethod3(new rename.Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } function part4() { @@ -49,7 +46,6 @@ function part4() { xyz.tMethod4(rename.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } function part5() { diff --git a/Examples/test-suite/javascript/rename3_runme.js b/Examples/test-suite/javascript/rename3_runme.js index 237029fbb..fb9393b03 100644 --- a/Examples/test-suite/javascript/rename3_runme.js +++ b/Examples/test-suite/javascript/rename3_runme.js @@ -10,7 +10,6 @@ function part1() { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } function part2() { @@ -23,7 +22,6 @@ function part2() { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } function part3(){ @@ -36,7 +34,6 @@ function part3(){ xyz.tMethod3(new rename.Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } function part4() { @@ -49,7 +46,6 @@ function part4() { xyz.tMethod4(rename.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } function part5() { diff --git a/Examples/test-suite/javascript/rename4_runme.js b/Examples/test-suite/javascript/rename4_runme.js index fed50dceb..1c3d8e77f 100644 --- a/Examples/test-suite/javascript/rename4_runme.js +++ b/Examples/test-suite/javascript/rename4_runme.js @@ -10,7 +10,6 @@ function part1() { xyz.tMethod2(0); xyz.tMethodNotXYZ2(notxyz); xyz.opNotXYZ2(); - xyz.opXYZ2(); } function part2() { @@ -23,7 +22,6 @@ function part2() { xyz.tMethod1(0); xyz.tMethodNotXYZ1(notxyz); xyz.opNotXYZ1(); - xyz.opXYZ1(); } function part3(){ @@ -36,7 +34,6 @@ function part3(){ xyz.tMethod3(new rename.Klass()); xyz.tMethodNotXYZ3(notxyz); xyz.opNotXYZ3(); - xyz.opXYZ3(); } function part4() { @@ -49,7 +46,6 @@ function part4() { xyz.tMethod4(rename.En1); xyz.tMethodNotXYZ4(notxyz); xyz.opNotXYZ4(); - xyz.opXYZ4(); } function part5() { diff --git a/Examples/test-suite/rename.h b/Examples/test-suite/rename.h index c8199eeeb..3f10c5856 100644 --- a/Examples/test-suite/rename.h +++ b/Examples/test-suite/rename.h @@ -27,7 +27,6 @@ namespace Space { void templateXYZ(XYZ i) {} operator T() { return m_t; } operator NotXYZ() const { return m_notxyz; } - operator XYZ() const { XYZ xyz = XYZ(); return xyz; } }; } @@ -48,10 +47,7 @@ class ABC { public: void method(ABC a) const {} void method(Klass k) const {} -#if !defined(__clang__) - // Workaround for: warning: conversion function converting 'Space::ABC' to itself will never be used - operator ABC() const { ABC a; return a; } -#endif + operator ABC*() const { return new ABC(); } operator Klass() const { Klass k; return k; } }; } diff --git a/Examples/test-suite/rename1.i b/Examples/test-suite/rename1.i index 38af2b3bd..92e6b3494 100644 --- a/Examples/test-suite/rename1.i +++ b/Examples/test-suite/rename1.i @@ -35,14 +35,9 @@ %rename(opNotXYZ3) Space::XYZ::operator NotXYZ() const; %rename(opNotXYZ4) Space::XYZ::operator NotXYZ() const; -%rename(opXYZ1) Space::XYZ::operator XYZ() const; -%rename(opXYZ2) Space::XYZ::operator XYZ() const; -%rename(opXYZ3) Space::XYZ::operator XYZ() const; -%rename(opXYZ4) Space::XYZ::operator XYZ() const; - %rename(methodABC) Space::ABC::method(ABC a) const; -%rename(opABC) Space::ABC::operator ABC() const; +%rename(opABC) Space::ABC::operator ABC*() const; %rename(methodKlass) Space::ABC::method(Klass k) const; %rename(opKlass) Space::ABC::operator Klass() const; diff --git a/Examples/test-suite/rename2.i b/Examples/test-suite/rename2.i index 6a9c22ecf..93b82ddc6 100644 --- a/Examples/test-suite/rename2.i +++ b/Examples/test-suite/rename2.i @@ -43,7 +43,7 @@ namespace Space { %rename(methodABC) ABC::method(ABC a) const; -%rename(opABC) ABC::operator ABC() const; +%rename(opABC) ABC::operator ABC*() const; %rename(methodKlass) ABC::method(Klass k) const; %rename(opKlass) ABC::operator Klass() const; } diff --git a/Examples/test-suite/rename3.i b/Examples/test-suite/rename3.i index b39979fdd..5b613d769 100644 --- a/Examples/test-suite/rename3.i +++ b/Examples/test-suite/rename3.i @@ -52,7 +52,7 @@ namespace Space { %extend ABC { %rename(methodABC) method(ABC a) const; - %rename(opABC) operator ABC() const; + %rename(opABC) operator ABC*() const; %rename(methodKlass) method(Klass k) const; %rename(opKlass) operator Klass() const; } diff --git a/Examples/test-suite/rename4.i b/Examples/test-suite/rename4.i index 9ddff362f..75f01ca5b 100644 --- a/Examples/test-suite/rename4.i +++ b/Examples/test-suite/rename4.i @@ -29,21 +29,18 @@ namespace Space { %rename(tMethodXYZ2) templateXYZ(XYZ); %rename(opT2) operator int(); %rename(opNotXYZ2) operator NotXYZ() const; -%rename(opXYZ2) operator XYZ() const; %rename(tMethod3) templateT(Space::Klass i); %rename(tMethodNotXYZ3) templateNotXYZ(NotXYZ); %rename(tMethodXYZ3) templateXYZ(XYZ); %rename(opT3) operator Space::Klass(); %rename(opNotXYZ3) operator NotXYZ() const; -%rename(opXYZ3) operator XYZ() const; %rename(tMethod4) templateT(Space::Enu i); %rename(tMethodNotXYZ4) templateNotXYZ(NotXYZ); %rename(tMethodXYZ4) templateXYZ(XYZ); %rename(opT4) operator Space::Enu(); %rename(opNotXYZ4) operator NotXYZ() const; -%rename(opXYZ4) operator XYZ() const; namespace Space { using namespace AnotherSpace; @@ -60,7 +57,6 @@ namespace Space { %rename(tMethodXYZ1) templateXYZ(XYZ); %rename(opT1) operator T(); %rename(opNotXYZ1) operator NotXYZ() const; - %rename(opXYZ1) operator XYZ() const; NotXYZ *m_int; T m_t; @@ -74,7 +70,6 @@ namespace Space { void templateXYZ(XYZ i) {} operator T() { return m_t; } operator NotXYZ() const { return m_notxyz; } - operator XYZ() const { XYZ xyz; return xyz; } }; } @@ -93,16 +88,13 @@ class ABC { public: %rename(methodABC) method(ABC a) const; - %rename(opABC) operator ABC() const; + %rename(opABC) operator ABC*() const; %rename(methodKlass) method(Klass k) const; %rename(opKlass) operator Klass() const; void method(ABC a) const {} void method(Klass k) const {} -#if !defined(__clang__) - // Workaround for: warning: conversion function converting 'Space::ABC' to itself will never be used - operator ABC() const { ABC a; return a; } -#endif + operator ABC*() const { return new ABC(); } operator Klass() const { Klass k; return k; } }; } From 31b3b782a15bd4752b93193019dde85528443db5 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 15 Apr 2019 23:28:25 +0100 Subject: [PATCH 091/134] Possible fix for MinGW MSYS configure script error from ax_boost_base.m4 Issue #1435 --- Tools/config/ax_boost_base.m4 | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/Tools/config/ax_boost_base.m4 b/Tools/config/ax_boost_base.m4 index d54039576..f5a935cd6 100644 --- a/Tools/config/ax_boost_base.m4 +++ b/Tools/config/ax_boost_base.m4 @@ -181,8 +181,7 @@ AC_DEFUN([_AX_BOOST_BASE_RUNDETECT],[ AC_MSG_RESULT(yes) succeeded=yes found_system=yes - ],[ - ]) + ],[]) AC_LANG_POP([C++]) @@ -276,8 +275,7 @@ AC_DEFUN([_AX_BOOST_BASE_RUNDETECT],[ AC_MSG_RESULT(yes) succeeded=yes found_system=yes - ],[ - ]) + ],[]) AC_LANG_POP([C++]) fi From 12a245183ffd9748a3111cfdd0d80a8c6797a520 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 18 Apr 2019 20:04:20 +0100 Subject: [PATCH 092/134] Clear up some confusion over ANSI vs ISO C/C++ support Issue #890 --- Doc/Manual/Introduction.html | 8 ++++---- Doc/Manual/Library.html | 2 +- Doc/Manual/Lua.html | 2 +- Doc/Manual/Preprocessor.html | 6 +++--- Doc/Manual/SWIG.html | 12 ++++++------ Doc/Manual/SWIGPlus.html | 4 ++-- Doc/Manual/Windows.html | 2 +- 7 files changed, 18 insertions(+), 18 deletions(-) diff --git a/Doc/Manual/Introduction.html b/Doc/Manual/Introduction.html index 149e86877..8d161b73d 100644 --- a/Doc/Manual/Introduction.html +++ b/Doc/Manual/Introduction.html @@ -163,7 +163,7 @@ This ability to interface C/C++ to many different target languages is one of SWI

            SWIG is very broadly composed of two components. -A core component creates a parse tree from the input C/C++ and SWIG directives (extensions to C/C++). +A core component creates a parse tree from the input ISO C/C++ and SWIG directives (extensions to the C/C++ standards). The parse tree is then passed to a second component, one of the target language modules for generating code specific to a higher level language. SWIG supports many different target languages. These target languages are given a status of either Supported or Experimental. @@ -273,7 +273,7 @@ extern int my_mod(int n, int m);

      -The interface file contains ANSI C function prototypes and variable +The interface file contains ISO C function prototypes and variable declarations. The %module directive defines the name of the module that will be created by SWIG. The %{ %} block provides a location for inserting additional code, such as C header @@ -400,7 +400,7 @@ major features include:

      • Full C99 preprocessing. -
      • All ANSI C and C++ datatypes. +
      • All ISO C and C++ datatypes.
      • Functions, variables, and constants.
      • Classes.
      • Single and multiple inheritance. @@ -531,7 +531,7 @@ to work with complicated and unusual C/C++ applications. Ironically, the freedom that SWIG provides is countered by an extremely conservative approach to code generation. At its core, SWIG tries to distill even the most advanced C++ code down to a small -well-defined set of interface building techniques based on ANSI C +well-defined set of interface building techniques based on ISO C programming. Because of this, you will find that SWIG interfaces can be easily compiled by virtually every C/C++ compiler and that they can be used on any platform. Again, this is an important part of staying out diff --git a/Doc/Manual/Library.html b/Doc/Manual/Library.html index 4ef6aeb83..eeb2e5a57 100644 --- a/Doc/Manual/Library.html +++ b/Doc/Manual/Library.html @@ -1365,7 +1365,7 @@ to accomplish this in SWIG. This library provides support for a few common tech
      • If used in C++, this library uses new and delete [] for memory -allocation. If using ANSI C, the library uses malloc() and free(). +allocation. If using C, the library uses malloc() and free().
      • Rather than manipulating char * directly, you might consider using a special string diff --git a/Doc/Manual/Lua.html b/Doc/Manual/Lua.html index 0fa1ecb13..6633eaa38 100644 --- a/Doc/Manual/Lua.html +++ b/Doc/Manual/Lua.html @@ -77,7 +77,7 @@

        -Lua is an extension programming language designed to support general procedural programming with data description facilities. It also offers good support for object-oriented programming, functional programming, and data-driven programming. Lua is intended to be used as a powerful, light-weight configuration language for any program that needs one. Lua is implemented as a library, written in clean C (that is, in the common subset of ANSI C and C++). It's also a really tiny language, less than 6000 lines of code, which compiles to <100 kilobytes of binary code. It can be found at http://www.lua.org +Lua is an extension programming language designed to support general procedural programming with data description facilities. It also offers good support for object-oriented programming, functional programming, and data-driven programming. Lua is intended to be used as a powerful, light-weight configuration language for any program that needs one. Lua is implemented as a library, written in clean C (that is, in the common subset of ISO C and C++). It's also a really tiny language, less than 6000 lines of code, which compiles to <100 kilobytes of binary code. It can be found at http://www.lua.org

        eLua stands for Embedded Lua (can be thought of as a flavor of Lua) and offers the full implementation of the Lua programming language to the embedded world, extending it with specific features for efficient and portable software embedded development. eLua runs on smaller devices like microcontrollers and provides the full features of the regular Lua desktop version. More information on eLua can be found here: http://www.eluaproject.net diff --git a/Doc/Manual/Preprocessor.html b/Doc/Manual/Preprocessor.html index 1bf59e238..f28f7b2be 100644 --- a/Doc/Manual/Preprocessor.html +++ b/Doc/Manual/Preprocessor.html @@ -138,7 +138,7 @@ In addition, SWIG defines the following set of standard C/C++ macros:

         __LINE__                        Current line number
         __FILE__                        Current file name
        -__STDC__                        Defined to indicate ANSI C
        +__STDC__                        Defined to indicate ISO C
         __cplusplus                     Defined when -c++ option used
         
        @@ -180,9 +180,9 @@ More complex macros can be defined in the standard way. For example:
         #define EXTERN extern
         #ifdef __STDC__
        -#define _ANSI(args)   (args)
        +#define ISOC_(args)   (args)
         #else
        -#define _ANSI(args) ()
        +#define ISOC_(args) ()
         #endif
         
        diff --git a/Doc/Manual/SWIG.html b/Doc/Manual/SWIG.html index 64db9c6c6..d1492d30a 100644 --- a/Doc/Manual/SWIG.html +++ b/Doc/Manual/SWIG.html @@ -88,7 +88,7 @@

        This chapter describes the basic operation of SWIG, the structure of its -input files, and how it handles standard ANSI C declarations. C++ support is +input files, and how it handles standard ISO C declarations. C++ support is described in the next chapter. However, C++ programmers should still read this chapter to understand the basics. Specific details about each target language are described in later @@ -252,7 +252,7 @@ recursively.

        -As input, SWIG expects a file containing ANSI C/C++ declarations and +As input, SWIG expects a file containing ISO C/C++ declarations and special SWIG directives. More often than not, this is a special SWIG interface file which is usually denoted with a special .i or .swg suffix. In certain cases, SWIG can be used directly on @@ -270,7 +270,7 @@ The most common format of a SWIG interface is as follows: %{ #include "myheader.h" %} -// Now list ANSI C/C++ declarations +// Now list ISO C/C++ declarations int foo; int bar(int x); ... @@ -2242,7 +2242,7 @@ used in Tcl as follows :

        -Although the ANSI C standard does not allow default arguments, default +Although the ISO C standard does not allow default arguments, default arguments specified in a SWIG interface work with both C and C++.

        @@ -2415,7 +2415,7 @@ see Callbacks to the

        -This section describes the behavior of SWIG when processing ANSI C structures and union declarations. Extensions to +This section describes the behavior of SWIG when processing ISO C structures and union declarations. Extensions to handle C++ are described in the next section.

        @@ -3469,7 +3469,7 @@ interface to your program. SWIG's %include directive to process an entire C source/header file. -
      • Make sure everything in the interface file uses ANSI C/C++ syntax. +
      • Make sure everything in the interface file uses ISO C/C++ syntax.
      • Make sure all necessary `typedef' declarations and type-information is available in the interface file. diff --git a/Doc/Manual/SWIGPlus.html b/Doc/Manual/SWIGPlus.html index 3a50cf8ce..dc9ae0f7e 100644 --- a/Doc/Manual/SWIGPlus.html +++ b/Doc/Manual/SWIGPlus.html @@ -93,7 +93,7 @@ For additions to the original C++ standard, please read the SWIG and C++17 chapters. As a prerequisite, you should first read the chapter SWIG Basics to see -how SWIG wraps ANSI C. Support for C++ builds upon ANSI C +how SWIG wraps ISO C. Support for C++ builds upon ISO C wrapping and that material will be useful in understanding this chapter.

        @@ -144,7 +144,7 @@ yourself in the foot. You will just have to be careful.

        To wrap C++, SWIG uses a layered approach to code generation. -At the lowest level, SWIG generates a collection of procedural ANSI-C style +At the lowest level, SWIG generates a collection of procedural ISO C style wrappers. These wrappers take care of basic type conversion, type checking, error handling, and other low-level details of the C++ binding. These wrappers are also sufficient to bind C++ into any target language diff --git a/Doc/Manual/Windows.html b/Doc/Manual/Windows.html index faea8b4e7..301974b64 100644 --- a/Doc/Manual/Windows.html +++ b/Doc/Manual/Windows.html @@ -211,7 +211,7 @@ If you do not have access to Visual C++ you will have to set up project files /

        -SWIG can also be compiled and run using Cygwin or MinGW which provides a Unix like front end to Windows and comes free with gcc, an ANSI C/C++ compiler. However, this is not a recommended approach as the prebuilt executable is supplied. +SWIG can also be compiled and run using Cygwin or MinGW which provides a Unix like front end to Windows and comes free with gcc, an ISO C/C++ compiler. However, this is not a recommended approach as the prebuilt executable is supplied.

        3.3.1 Building swig.exe on Windows

        From 65a7fafd844b03f2d2fd719b996a1f4c0eae2b4d Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 18 Apr 2019 20:27:14 +0100 Subject: [PATCH 093/134] Fix minor whitespace regression in Java generated code --- Source/Modules/java.cxx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Source/Modules/java.cxx b/Source/Modules/java.cxx index 94087369a..cb41781dd 100644 --- a/Source/Modules/java.cxx +++ b/Source/Modules/java.cxx @@ -2078,7 +2078,7 @@ public: Printv(proxy_class_def, methodmods, NIL); else Printv(proxy_class_def, destruct_methodmodifiers, NIL); - Printv(proxy_class_def, " void ", destruct_methodname, "(", destruct_parameters, ") ", destructor_throws_clause, " ", destruct, "\n", NIL); + Printv(proxy_class_def, " void ", destruct_methodname, "(", destruct_parameters, ")", destructor_throws_clause, " ", destruct, "\n", NIL); } } if (*Char(interface_upcasts)) From b6a675cf1d471a2341258f9f56c783cf8e3b4768 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 18 Apr 2019 23:22:01 +0100 Subject: [PATCH 094/134] Add potential incompatibility info for Java std::vector wrappers --- CHANGES.current | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 3c819bd88..9633d07e7 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -1390,6 +1390,35 @@ Version 4.0.0 (in progress) 2017-05-26: Volker Diels-Grabsch, vadz [Java] #842 Extend from java.util.AbstractList<> and implement java.util.RandomAccess for std::vector wrappers. This notably allows to iterate over wrapped vectors in a natural way. + Note that boxed types are now used in the Java layer when wrapping vector of C primitive + types, for example. This may introduce some subtle incompatibilities due to some + differences in how Java converts boxed types and unboxed types. For example, + + int i=0; + double d1 = i; // ok + Double d2 = i; // error: incompatible types: int cannot be converted to Double + + This can be a problem when calling the add and set functions. A suggested backwards + compatible workaround is to use something like (shown for std::vector: + + #if defined(SWIGJAVA) + // Add in old api that uses non-boxed types + %extend std::vector { + %proxycode %{ + public void add(double x) { + add(Double.valueOf(x)); + } + public void set(int i, double val) { + set(i, Double.valueOf(val)); + } + %} + } + #endif + + %include "std_vector.i" + %template(VectorDouble) std::vector; + + *** POTENTIAL INCOMPATIBILITY *** 2017-05-30: davidcl [Scilab] #994 Undefined symbol error when loading in Scilab 6 From 05c8c972cc32c11bc4adbbfd45e73cd7bf97495f Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 18 Apr 2019 23:24:43 +0100 Subject: [PATCH 095/134] Improve backwards compatibility in Java std::vector wrappers For users who have typemaps for the parameters in the add and set methods (now called doAdd and doSet). Also for users who have typemaps for the get method - revert the return type for get (now called doGet) back to the same return type as std::vector::at. Correct definitions of const_reference to match the those in the (C++11) standard. --- Lib/java/std_vector.i | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/Lib/java/std_vector.i b/Lib/java/std_vector.i index 88de46f46..e33270238 100644 --- a/Lib/java/std_vector.i +++ b/Lib/java/std_vector.i @@ -105,14 +105,14 @@ SWIGINTERN jint SWIG_VectorSize(size_t size) { return SWIG_VectorSize(self->size()); } - void doAdd(const value_type& value) { - self->push_back(value); + void doAdd(const value_type& x) { + self->push_back(x); } - void doAdd(jint index, const value_type& value) throw (std::out_of_range) { + void doAdd(jint index, const value_type& x) throw (std::out_of_range) { jint size = static_cast(self->size()); if (0 <= index && index <= size) { - self->insert(self->begin() + index, value); + self->insert(self->begin() + index, x); } else { throw std::out_of_range("vector index out of range"); } @@ -129,7 +129,7 @@ SWIGINTERN jint SWIG_VectorSize(size_t size) { } } - CONST_REFERENCE doGet(jint index) throw (std::out_of_range) { + const_reference doGet(jint index) throw (std::out_of_range) { jint size = static_cast(self->size()); if (index >= 0 && index < size) return (*self)[index]; @@ -137,11 +137,11 @@ SWIGINTERN jint SWIG_VectorSize(size_t size) { throw std::out_of_range("vector index out of range"); } - value_type doSet(jint index, const value_type& value) throw (std::out_of_range) { + value_type doSet(jint index, const value_type& val) throw (std::out_of_range) { jint size = static_cast(self->size()); if (index >= 0 && index < size) { CTYPE const old_value = (*self)[index]; - (*self)[index] = value; + (*self)[index] = val; return old_value; } else @@ -169,7 +169,7 @@ SWIGINTERN jint SWIG_VectorSize(size_t size) { namespace std { template class vector { - SWIG_STD_VECTOR_MINIMUM_INTERNAL(T, const T&) + SWIG_STD_VECTOR_MINIMUM_INTERNAL(T, const value_type&) }; // bool specialization From c79cf790853d6e6d65aa7379ccb2e472b704e456 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 19 Apr 2019 00:11:22 +0100 Subject: [PATCH 096/134] Improve backwards compatibility in C# std::vector wrappers For users who have typemaps for the parameters in the setitem method. Correct definitions of const_reference to match the those in the (C++11) standard. --- Lib/csharp/std_vector.i | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/Lib/csharp/std_vector.i b/Lib/csharp/std_vector.i index e8eeb8411..1e2603782 100644 --- a/Lib/csharp/std_vector.i +++ b/Lib/csharp/std_vector.i @@ -233,15 +233,15 @@ else throw std::out_of_range("index"); } - CONST_REFERENCE getitem(int index) throw (std::out_of_range) { + const_reference getitem(int index) throw (std::out_of_range) { if (index>=0 && index<(int)$self->size()) return (*$self)[index]; else throw std::out_of_range("index"); } - void setitem(int index, CTYPE const& value) throw (std::out_of_range) { + void setitem(int index, CTYPE const& val) throw (std::out_of_range) { if (index>=0 && index<(int)$self->size()) - (*$self)[index] = value; + (*$self)[index] = val; else throw std::out_of_range("index"); } @@ -351,7 +351,7 @@ %define SWIG_STD_VECTOR_ENHANCED(CTYPE...) namespace std { template<> class vector< CTYPE > { - SWIG_STD_VECTOR_MINIMUM_INTERNAL(IList, %arg(CTYPE const&), %arg(CTYPE)) + SWIG_STD_VECTOR_MINIMUM_INTERNAL(IList, const value_type&, %arg(CTYPE)) SWIG_STD_VECTOR_EXTRA_OP_EQUALS_EQUALS(CTYPE) }; } @@ -384,11 +384,11 @@ namespace std { // primary (unspecialized) class template for std::vector // does not require operator== to be defined template class vector { - SWIG_STD_VECTOR_MINIMUM_INTERNAL(IEnumerable, T const&, T) + SWIG_STD_VECTOR_MINIMUM_INTERNAL(IEnumerable, const value_type&, T) }; // specialization for pointers template class vector { - SWIG_STD_VECTOR_MINIMUM_INTERNAL(IList, T *const&, T *) + SWIG_STD_VECTOR_MINIMUM_INTERNAL(IList, const value_type&, T *) SWIG_STD_VECTOR_EXTRA_OP_EQUALS_EQUALS(T *) }; // bool is specialized in the C++ standard - const_reference in particular From 592b97a8cd8b6e535011a2e611b64c1af8d2bfe0 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 19 Apr 2019 00:22:53 +0100 Subject: [PATCH 097/134] Improve backwards compatibility in D std::vector wrappers For users who have typemaps for the parameters in the setElement method. Correct definitions of const_reference to match the those in the (C++11) standard. --- Lib/d/std_vector.i | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/Lib/d/std_vector.i b/Lib/d/std_vector.i index 9dcb184c6..fb8f7d2e0 100644 --- a/Lib/d/std_vector.i +++ b/Lib/d/std_vector.i @@ -135,7 +135,7 @@ public void capacity(size_t value) { return $self->capacity() - $self->size(); } - CONST_REFERENCE remove() throw (std::out_of_range) { + const_reference remove() throw (std::out_of_range) { if ($self->empty()) { throw std::out_of_range("Tried to remove last element from empty vector."); } @@ -145,7 +145,7 @@ public void capacity(size_t value) { return value; } - CONST_REFERENCE remove(size_type index) throw (std::out_of_range) { + const_reference remove(size_type index) throw (std::out_of_range) { if (index >= $self->size()) { throw std::out_of_range("Tried to remove element with invalid index."); } @@ -160,7 +160,7 @@ public void capacity(size_t value) { // Wrappers for setting/getting items with the possibly thrown exception // specified (important for SWIG wrapper generation). %extend { - CONST_REFERENCE getElement(size_type index) throw (std::out_of_range) { + const_reference getElement(size_type index) throw (std::out_of_range) { if ((index < 0) || ($self->size() <= index)) { throw std::out_of_range("Tried to get value of element with invalid index."); } @@ -172,11 +172,11 @@ public void capacity(size_t value) { // generation issue when using const pointers as vector elements (like // std::vector< const int* >). %extend { - void setElement(size_type index, CTYPE const& value) throw (std::out_of_range) { + void setElement(size_type index, CTYPE const& val) throw (std::out_of_range) { if ((index < 0) || ($self->size() <= index)) { throw std::out_of_range("Tried to set value of element with invalid index."); } - (*$self)[index] = value; + (*$self)[index] = val; } } @@ -478,7 +478,7 @@ int opApply(int delegate(ref size_t index, ref $typemap(dtype, CTYPE) value) dg) return pv; } - CONST_REFERENCE remove() throw (std::out_of_range) { + const_reference remove() throw (std::out_of_range) { if ($self->empty()) { throw std::out_of_range("Tried to remove last element from empty vector."); } @@ -488,7 +488,7 @@ int opApply(int delegate(ref size_t index, ref $typemap(dtype, CTYPE) value) dg) return value; } - CONST_REFERENCE remove(size_type index) throw (std::out_of_range) { + const_reference remove(size_type index) throw (std::out_of_range) { if (index >= $self->size()) { throw std::out_of_range("Tried to remove element with invalid index."); } @@ -520,7 +520,7 @@ int opApply(int delegate(ref size_t index, ref $typemap(dtype, CTYPE) value) dg) // Wrappers for setting/getting items with the possibly thrown exception // specified (important for SWIG wrapper generation). %extend { - CONST_REFERENCE getElement(size_type index) throw (std::out_of_range) { + const_reference getElement(size_type index) throw (std::out_of_range) { if ((index < 0) || ($self->size() <= index)) { throw std::out_of_range("Tried to get value of element with invalid index."); } @@ -531,11 +531,11 @@ int opApply(int delegate(ref size_t index, ref $typemap(dtype, CTYPE) value) dg) // generation issue when using const pointers as vector elements (like // std::vector< const int* >). %extend { - void setElement(size_type index, CTYPE const& value) throw (std::out_of_range) { + void setElement(size_type index, CTYPE const& val) throw (std::out_of_range) { if ((index < 0) || ($self->size() <= index)) { throw std::out_of_range("Tried to set value of element with invalid index."); } - (*$self)[index] = value; + (*$self)[index] = val; } } @@ -558,7 +558,7 @@ int opApply(int delegate(ref size_t index, ref $typemap(dtype, CTYPE) value) dg) %define SWIG_STD_VECTOR_ENHANCED(CTYPE...) namespace std { template<> class vector { - SWIG_STD_VECTOR_MINIMUM_INTERNAL(%arg(CTYPE const&), %arg(CTYPE)) + SWIG_STD_VECTOR_MINIMUM_INTERNAL(const value_type&, %arg(CTYPE)) SWIG_STD_VECTOR_EXTRA_OP_EQUALS_EQUALS(CTYPE) }; } @@ -573,11 +573,11 @@ namespace std { // primary (unspecialized) class template for std::vector // does not require operator== to be defined template class vector { - SWIG_STD_VECTOR_MINIMUM_INTERNAL(T const&, T) + SWIG_STD_VECTOR_MINIMUM_INTERNAL(const value_type&, T) }; // specializations for pointers template class vector { - SWIG_STD_VECTOR_MINIMUM_INTERNAL(T *const&, T *) + SWIG_STD_VECTOR_MINIMUM_INTERNAL(const value_type&, T *) SWIG_STD_VECTOR_EXTRA_OP_EQUALS_EQUALS(T *) }; // bool is a bit different in the C++ standard - const_reference in particular From f87182ad98de90f46d986617c1c942be8bdc9002 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 19 Apr 2019 11:06:24 +0100 Subject: [PATCH 098/134] Improve backwards compatibility in C#/Java std::array wrappers For users who have typemaps for the parameters in the setitem or set methods. --- Lib/csharp/std_array.i | 4 ++-- Lib/java/std_array.i | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Lib/csharp/std_array.i b/Lib/csharp/std_array.i index e7d392b85..a4f0f9640 100644 --- a/Lib/csharp/std_array.i +++ b/Lib/csharp/std_array.i @@ -192,9 +192,9 @@ else throw std::out_of_range("index"); } - void setitem(int index, const_reference value) throw (std::out_of_range) { + void setitem(int index, const_reference val) throw (std::out_of_range) { if (index>=0 && index<(int)$self->size()) - (*$self)[index] = value; + (*$self)[index] = val; else throw std::out_of_range("index"); } diff --git a/Lib/java/std_array.i b/Lib/java/std_array.i index f67b18d9b..d3436cc66 100644 --- a/Lib/java/std_array.i +++ b/Lib/java/std_array.i @@ -31,10 +31,10 @@ namespace std { else throw std::out_of_range("array index out of range"); } - void set(int i, const value_type& value) throw (std::out_of_range) { + void set(int i, const value_type& val) throw (std::out_of_range) { int size = int(self->size()); if (i>=0 && i Date: Fri, 19 Apr 2019 11:33:02 +0100 Subject: [PATCH 099/134] Fix Visual Studio 2015 and later compilation errors due to snprintf macro definition. Closes #1508 --- CHANGES.current | 4 ++++ Lib/chicken/chickenrun.swg | 2 +- Lib/swigfragments.swg | 2 +- 3 files changed, 6 insertions(+), 2 deletions(-) diff --git a/CHANGES.current b/CHANGES.current index 9633d07e7..d36f43c41 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,10 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-04-19: pbecherer + [Tcl] Fix Visual Studio 2015 and later compilation errors due to snprintf macro + definition. + 2019-04-09: wsfulton [C#] Fix FxCop warning CA2002 in SWIGPendingException - a lock on a reference of type 'Type'. diff --git a/Lib/chicken/chickenrun.swg b/Lib/chicken/chickenrun.swg index d4255c365..bb14b4bc9 100644 --- a/Lib/chicken/chickenrun.swg +++ b/Lib/chicken/chickenrun.swg @@ -7,7 +7,7 @@ #include #include #include -#if defined(_MSC_VER) || defined(__BORLANDC__) || defined(_WATCOM) +#if (defined(_MSC_VER) && (_MSC_VER < 1900)) || defined(__BORLANDC__) || defined(_WATCOM) # ifndef snprintf # define snprintf _snprintf # endif diff --git a/Lib/swigfragments.swg b/Lib/swigfragments.swg index 63bb6c8f4..2cbef7cce 100644 --- a/Lib/swigfragments.swg +++ b/Lib/swigfragments.swg @@ -35,7 +35,7 @@ %fragment("", "header") %{ #include -#if defined(_MSC_VER) || defined(__BORLANDC__) || defined(_WATCOM) +#if (defined(_MSC_VER) && (_MSC_VER < 1900)) || defined(__BORLANDC__) || defined(_WATCOM) # ifndef snprintf # define snprintf _snprintf # endif From 77f075b6e8196ea26aa32855a5ae1ada124a02b8 Mon Sep 17 00:00:00 2001 From: Ian Lance Taylor Date: Fri, 19 Apr 2019 12:49:56 -0700 Subject: [PATCH 100/134] When generating Go code, make -cgo the default. Add new -no-cgo option to disable the default. Keep -cgo as a no-op for existing users. --- Doc/Manual/Go.html | 53 +++++++++++++++++++++++-------------------- Examples/Makefile.in | 8 +++---- Source/Modules/go.cxx | 6 ++++- 3 files changed, 38 insertions(+), 29 deletions(-) diff --git a/Doc/Manual/Go.html b/Doc/Manual/Go.html index b16c764fb..dbea7de96 100644 --- a/Doc/Manual/Go.html +++ b/Doc/Manual/Go.html @@ -125,16 +125,15 @@ Go distribution. To generate code for gccgo, you should also use the

        -When using the -cgo option, SWIG will generate files that can be used -directly by go build. Starting with the Go 1.5 distribution the --cgo option has to be given. Put your SWIG interface file in a -directory under GOPATH/src, and give it a name that does not end in the -.swig or .swigcxx extension. Typically the SWIG interface file extension is .i -in this case. +By default SWIG will generate files that can be used directly +by go build. This requires Go 1.2 or later. Put your SWIG +interface file in a directory under GOPATH/src, and give it a name +that does not end in the .swig or .swigcxx extension. +Typically the SWIG interface file extension is .i in this case.

        -% swig -go -cgo example.i
        +% swig -go example.i
         % go install
         
        @@ -144,15 +143,16 @@ usual.

        -To use SWIG without the -cgo option, more steps are required. Recall -that this only works with Go versions before 1.5. When using Go version 1.2 or -later, or when using gccgo, the code generated by SWIG can be linked directly -into the Go program. A typical command sequence when using the Go compiler of -the Go distribution would look like this: +SWIG can be used without cgo, via the -no-cgo option, but +more steps are required. This only works with Go versions before 1.5. +When using Go version 1.2 or later, or when using gccgo, the code +generated by SWIG can be linked directly into the Go program. A +typical command sequence when using the Go compiler of the Go +distribution would look like this:

        -% swig -go example.i
        +% swig -go -no-cgo example.i
         % gcc -c code.c    # The C library being wrapped.
         % gcc -c example_wrap.c
         % go tool 6g example.go
        @@ -169,7 +169,7 @@ sequence for this approach would look like this:
         

        -% swig -go -use-shlib example.i
        +% swig -go -no-cgo -use-shlib example.i
         % gcc -c -fpic example.c
         % gcc -c -fpic example_wrap.c
         % gcc -shared example.o example_wrap.o -o example.so
        @@ -200,10 +200,15 @@ swig -go -help
         
         
         -cgo
        -Generate files to be used as input for the Go cgo tool.  This
        -  option is required for Go 1.5 and later, and works for Go 1.2 and
        -  later.  In the future this option will likely become the
        -  default.
        +Generate files to be used as input for the Go cgo tool.  This is
        +  the default.
        +
        +
        +
        +-no-cgo
        +Generate files that can be used directly, rather than via the Go
        +  cgo tool.  This option does not work with Go 1.5 or later.  It is
        +  required for versions of Go before 1.2.
         
         
         
        @@ -268,11 +273,11 @@ swig -go -help
         
         
         

        There are two different approaches to generating wrapper files, - controlled by SWIG's -cgo option. The -cgo option - works with Go version 1.2 or later. It is required when using Go - version 1.5 or later.

        + controlled by SWIG's -no-cgo option. The -no-cgo + option only works with version of Go before 1.5. It is required + when using versions of Go before 1.2.

        -

        With or without the -cgo option, SWIG will generate the +

        With or without the -no-cgo option, SWIG will generate the following files when generating wrapper code:

          @@ -296,8 +301,8 @@ or C++ compiler.
        -

        When neither the -cgo nor the -gccgo option is - used, SWIG will also generate an additional file:

        +

        When the -no-cgo option is used, and the -gccgo + option is not used, SWIG will also generate an additional file:

        • diff --git a/Examples/Makefile.in b/Examples/Makefile.in index b2cbb65da..d7b71af2f 100644 --- a/Examples/Makefile.in +++ b/Examples/Makefile.in @@ -1468,7 +1468,7 @@ GOGCCOBJS = $(GOSRCS:.go=.@OBJEXT@) # ---------------------------------------------------------------- go_nocgo: $(SRCDIR_SRCS) - $(SWIG) -go $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) + $(SWIG) -go -no-cgo $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) if $(GO12) || $(GO13) || $(GO15) || $(GOGCC); then \ $(CC) -g -c $(CPPFLAGS) $(CFLAGS) $(SRCDIR_SRCS) $(ISRCS) $(INCLUDES); \ else \ @@ -1504,7 +1504,7 @@ go_nocgo: $(SRCDIR_SRCS) fi go: $(SRCDIR_SRCS) - $(SWIG) -go -cgo $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) + $(SWIG) -go $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) @mkdir gopath 2>/dev/null || true @mkdir gopath/src 2>/dev/null || true @mkdir gopath/src/$(INTERFACE:.i=) 2>/dev/null || true @@ -1548,7 +1548,7 @@ go: $(SRCDIR_SRCS) # ---------------------------------------------------------------- go_cpp_nocgo: $(SRCDIR_SRCS) - $(SWIG) -go -c++ $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) + $(SWIG) -go -c++ -no-cgo $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) if $(GO12) || $(GO13) || $(GO15) || $(GOGCC); then \ if test -n "$(SRCDIR_CXXSRCS)$(SRCDIR_SRCS)"; then \ $(CXX) -g -c $(CPPFLAGS) $(CXXFLAGS) $(SRCDIR_CXXSRCS) $(SRCDIR_SRCS) $(INCLUDES); \ @@ -1596,7 +1596,7 @@ go_cpp_nocgo: $(SRCDIR_SRCS) fi go_cpp: $(SRCDIR_SRCS) - $(SWIG) -go -c++ -cgo $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) + $(SWIG) -go -c++ $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) @mkdir gopath 2>/dev/null || true @mkdir gopath/src 2>/dev/null || true @mkdir gopath/src/$(INTERFACE:.i=) 2>/dev/null || true diff --git a/Source/Modules/go.cxx b/Source/Modules/go.cxx index 41e8f7d0a..9e8162b5d 100644 --- a/Source/Modules/go.cxx +++ b/Source/Modules/go.cxx @@ -199,7 +199,7 @@ class GO:public Language { public: GO():package(NULL), module(NULL), - cgo_flag(false), + cgo_flag(true), gccgo_flag(false), go_prefix(NULL), prefix_option(NULL), @@ -269,6 +269,9 @@ private: } else if (strcmp(argv[i], "-cgo") == 0) { Swig_mark_arg(i); cgo_flag = true; + } else if (strcmp(argv[i], "-no-cgo") == 0) { + Swig_mark_arg(i); + cgo_flag = false; } else if (strcmp(argv[i], "-gccgo") == 0) { Swig_mark_arg(i); gccgo_flag = true; @@ -6979,6 +6982,7 @@ extern "C" Language *swig_go(void) { const char * const GO::usage = "\ Go Options (available with -go)\n\ -cgo - Generate cgo input files\n\ + -no-cgo - Do not generate cgo input files\n\ -gccgo - Generate code for gccgo rather than 6g/8g\n\ -go-pkgpath

          - Like gccgo -fgo-pkgpath option\n\ -go-prefix

          - Like gccgo -fgo-prefix option\n\ From d67c133c4a85c72f77bce245b7db4ae047202396 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 20 Apr 2019 11:20:24 +0100 Subject: [PATCH 101/134] Java/C# std::vector workarounds for clang Workaround clang++ 9.1.0 error not knowing std::vector::const_reference is actually typedef to bool: li_std_vector_wrap.cxx:1838:40: error: no matching constructor for initialization of 'std::vector::const_reference' Workaround is use const value_type& getitem(int index) throw (std::out_of_range) { ... // bool specialization: bool getitem(int index) throw (std::out_of_range) { ... instead of const_reference_type getitem(int index) throw (std::out_of_range) { ... Although the following would be better, it would require a more complicated implementation: const_reference_type getitem(int index) throw (std::out_of_range) { ... // bool specialization: bool getitem(int index) throw (std::out_of_range) { ... --- Lib/csharp/std_vector.i | 2 +- Lib/java/std_vector.i | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Lib/csharp/std_vector.i b/Lib/csharp/std_vector.i index 1e2603782..e2811290c 100644 --- a/Lib/csharp/std_vector.i +++ b/Lib/csharp/std_vector.i @@ -233,7 +233,7 @@ else throw std::out_of_range("index"); } - const_reference getitem(int index) throw (std::out_of_range) { + CONST_REFERENCE getitem(int index) throw (std::out_of_range) { if (index>=0 && index<(int)$self->size()) return (*$self)[index]; else diff --git a/Lib/java/std_vector.i b/Lib/java/std_vector.i index e33270238..955e20cac 100644 --- a/Lib/java/std_vector.i +++ b/Lib/java/std_vector.i @@ -129,7 +129,7 @@ SWIGINTERN jint SWIG_VectorSize(size_t size) { } } - const_reference doGet(jint index) throw (std::out_of_range) { + CONST_REFERENCE doGet(jint index) throw (std::out_of_range) { jint size = static_cast(self->size()); if (index >= 0 && index < size) return (*self)[index]; From 01a2cd27e7bd64f2788885eaa1d8f39310631f5f Mon Sep 17 00:00:00 2001 From: Vadim Zeitlin Date: Fri, 19 Apr 2019 18:48:35 +0200 Subject: [PATCH 102/134] Don't crash if type is not available in Python Doxygen code Fix crash if "@return" Doxygen tag was used on a node without any return type (such as a class, for example). Ignoring it might not be the best thing to do, but it's definitely better than crashing and it's not really clear what else could be done anyhow. Closes #1516. --- Examples/test-suite/doxygen_misc_constructs.i | 3 +++ .../test-suite/java/doxygen_misc_constructs_runme.java | 3 +++ Source/Doxygen/pydoc.cxx | 7 ++++++- 3 files changed, 12 insertions(+), 1 deletion(-) diff --git a/Examples/test-suite/doxygen_misc_constructs.i b/Examples/test-suite/doxygen_misc_constructs.i index c95e85683..c1b3eea31 100644 --- a/Examples/test-suite/doxygen_misc_constructs.i +++ b/Examples/test-suite/doxygen_misc_constructs.i @@ -104,6 +104,9 @@ }; + /// @return This is a bad place for this tag, but it should be ignored. + struct StructWithReturnComment {}; + /** An example of a list in a documentation comment. diff --git a/Examples/test-suite/java/doxygen_misc_constructs_runme.java b/Examples/test-suite/java/doxygen_misc_constructs_runme.java index 6d018b9d2..5d95bd565 100644 --- a/Examples/test-suite/java/doxygen_misc_constructs_runme.java +++ b/Examples/test-suite/java/doxygen_misc_constructs_runme.java @@ -117,6 +117,9 @@ public class doxygen_misc_constructs_runme { wantedComments.put("doxygen_misc_constructs.ClassWithNestedEnum.ENested.THREE", " desc of three\n"); + wantedComments.put("doxygen_misc_constructs.StructWithReturnComment", + " @return This is a bad place for this tag, but it should be ignored."); + wantedComments.put("doxygen_misc_constructs.doxygen_misc_constructs.showList()", " An example of a list in a documentation comment.
          \n" + "
          \n" + diff --git a/Source/Doxygen/pydoc.cxx b/Source/Doxygen/pydoc.cxx index 8c3090035..fc3b0ea09 100644 --- a/Source/Doxygen/pydoc.cxx +++ b/Source/Doxygen/pydoc.cxx @@ -336,8 +336,13 @@ static std::string getPyDocType(Node *n, const_String_or_char_ptr lname = "") { std::string type; String *s = Swig_typemap_lookup("doctype", n, lname, 0); + if (!s) { + if (String *t = Getattr(n, "type")) + s = SwigType_str(t, ""); + } + if (!s) - s = SwigType_str(Getattr(n, "type"), ""); + return type; if (Language::classLookup(s)) { // In Python C++ namespaces are flattened, so remove all but last component From 74adaa5738368ce473870451422f4a7175b6a736 Mon Sep 17 00:00:00 2001 From: Vadim Zeitlin Date: Thu, 18 Apr 2019 17:46:13 +0200 Subject: [PATCH 103/134] Fix parsing of enums with trailing comma with -doxygen To correctly parse Doxygen post-comments after the trailing comma, switch to right recursion in "enumlist" production rule definition: this does consume more stack space when parsing, but makes the rules much easier to write and to understand and hopefully shouldn't result in any problems with real code (which shouldn't have thousands of enums items in it). Closes #1514. --- Examples/test-suite/doxygen_parsing_enums.i | 5 ++ .../doxygen_parsing_enums_proper_runme.java | 4 ++ .../doxygen_parsing_enums_simple_runme.java | 4 ++ .../doxygen_parsing_enums_typesafe_runme.java | 4 ++ ...oxygen_parsing_enums_typeunsafe_runme.java | 4 ++ Source/CParse/parser.y | 58 +++++++------------ 6 files changed, 43 insertions(+), 36 deletions(-) diff --git a/Examples/test-suite/doxygen_parsing_enums.i b/Examples/test-suite/doxygen_parsing_enums.i index 5c48f4801..b7a39871f 100644 --- a/Examples/test-suite/doxygen_parsing_enums.i +++ b/Examples/test-suite/doxygen_parsing_enums.i @@ -32,4 +32,9 @@ SOME_ITEM_30 ///< Post comment for the third item }; + enum SomeEnumWithTrailingComma + { + SOME_ITEM_100, ///< Post comment after comma. + SOME_ITEM_200, ///< Post comment after last comma. + }; %} diff --git a/Examples/test-suite/java/doxygen_parsing_enums_proper_runme.java b/Examples/test-suite/java/doxygen_parsing_enums_proper_runme.java index a8527e364..ef1f06af5 100644 --- a/Examples/test-suite/java/doxygen_parsing_enums_proper_runme.java +++ b/Examples/test-suite/java/doxygen_parsing_enums_proper_runme.java @@ -55,6 +55,10 @@ public class doxygen_parsing_enums_proper_runme { wantedComments.put("doxygen_parsing_enums_proper.SomeAnotherEnum2.SOME_ITEM_20", "Post comment for the second item \n" + ""); + wantedComments.put("doxygen_parsing_enums_proper.SomeEnumWithTrailingComma.SOME_ITEM_100", + "Post comment after comma."); + wantedComments.put("doxygen_parsing_enums_proper.SomeEnumWithTrailingComma.SOME_ITEM_200", + "Post comment after last comma."); // and ask the parser to check comments for us System.exit(parser.check(wantedComments)); diff --git a/Examples/test-suite/java/doxygen_parsing_enums_simple_runme.java b/Examples/test-suite/java/doxygen_parsing_enums_simple_runme.java index f68fff151..85ec0cb55 100644 --- a/Examples/test-suite/java/doxygen_parsing_enums_simple_runme.java +++ b/Examples/test-suite/java/doxygen_parsing_enums_simple_runme.java @@ -47,6 +47,10 @@ public class doxygen_parsing_enums_simple_runme { " The comment for the first item \n" + " \n" + ""); + wantedComments.put("doxygen_parsing_enums_simple.doxygen_parsing_enums_simpleConstants.SOME_ITEM_100", + "Post comment after comma."); + wantedComments.put("doxygen_parsing_enums_simple.doxygen_parsing_enums_simpleConstants.SOME_ITEM_200", + "Post comment after last comma."); // and ask the parser to check comments for us System.exit(parser.check(wantedComments)); diff --git a/Examples/test-suite/java/doxygen_parsing_enums_typesafe_runme.java b/Examples/test-suite/java/doxygen_parsing_enums_typesafe_runme.java index 7c7f05ccc..4e5f4b489 100644 --- a/Examples/test-suite/java/doxygen_parsing_enums_typesafe_runme.java +++ b/Examples/test-suite/java/doxygen_parsing_enums_typesafe_runme.java @@ -55,6 +55,10 @@ public class doxygen_parsing_enums_typesafe_runme { wantedComments.put("doxygen_parsing_enums_typesafe.SomeAnotherEnum2.SOME_ITEM_30", "Post comment for the third item \n" + ""); + wantedComments.put("doxygen_parsing_enums_typesafe.SomeEnumWithTrailingComma.SOME_ITEM_100", + "Post comment after comma."); + wantedComments.put("doxygen_parsing_enums_typesafe.SomeEnumWithTrailingComma.SOME_ITEM_200", + "Post comment after last comma."); // and ask the parser to check comments for us diff --git a/Examples/test-suite/java/doxygen_parsing_enums_typeunsafe_runme.java b/Examples/test-suite/java/doxygen_parsing_enums_typeunsafe_runme.java index 8c7dfeda0..428649196 100644 --- a/Examples/test-suite/java/doxygen_parsing_enums_typeunsafe_runme.java +++ b/Examples/test-suite/java/doxygen_parsing_enums_typeunsafe_runme.java @@ -55,6 +55,10 @@ public class doxygen_parsing_enums_typeunsafe_runme { wantedComments.put("doxygen_parsing_enums_typeunsafe.SomeAnotherEnum2.SOME_ITEM_10", "Post comment for the first item \n" + ""); + wantedComments.put("doxygen_parsing_enums_typeunsafe.SomeEnumWithTrailingComma.SOME_ITEM_100", + "Post comment after comma."); + wantedComments.put("doxygen_parsing_enums_typeunsafe.SomeEnumWithTrailingComma.SOME_ITEM_200", + "Post comment after last comma."); // and ask the parser to check comments for us System.exit(parser.check(wantedComments)); diff --git a/Source/CParse/parser.y b/Source/CParse/parser.y index 4046e480e..b526da907 100644 --- a/Source/CParse/parser.y +++ b/Source/CParse/parser.y @@ -1650,7 +1650,7 @@ static String *add_qualifier_to_declarator(SwigType *type, SwigType *qualifier) /* C declarations */ %type c_declaration c_decl c_decl_tail c_enum_key c_enum_inherit c_enum_decl c_enum_forward_decl c_constructor_decl; -%type enumlist enumlist_tail enumlist_item edecl_with_dox edecl; +%type enumlist enumlist_item edecl_with_dox edecl; /* C++ declarations */ %type cpp_declaration cpp_class_decl cpp_forward_class_decl cpp_template_decl cpp_alternate_rettype; @@ -6374,21 +6374,31 @@ optional_ignored_defines | empty ; -optional_ignored_define_after_comma - : empty - | COMMA - | COMMA constant_directive - ; - /* Enum lists - any #define macros (constant directives) within the enum list are ignored. Trailing commas accepted. */ -enumlist : enumlist_item optional_ignored_define_after_comma { +enumlist : enumlist_item { Setattr($1,"_last",$1); $$ = $1; } - | enumlist_item enumlist_tail optional_ignored_define_after_comma { - set_nextSibling($1, $2); - Setattr($1,"_last",Getattr($2,"_last")); - Setattr($2,"_last",NULL); + | enumlist_item DOXYGENPOSTSTRING { + Setattr($1,"_last",$1); + set_comment($1, $2); + $$ = $1; + } + | enumlist_item COMMA enumlist { + if ($3) { + set_nextSibling($1, $3); + Setattr($1,"_last",Getattr($3,"_last")); + Setattr($3,"_last",NULL); + } + $$ = $1; + } + | enumlist_item COMMA DOXYGENPOSTSTRING enumlist { + if ($4) { + set_nextSibling($1, $4); + Setattr($1,"_last",Getattr($4,"_last")); + Setattr($4,"_last",NULL); + } + set_comment($1, $3); $$ = $1; } | optional_ignored_defines { @@ -6396,17 +6406,6 @@ enumlist : enumlist_item optional_ignored_define_after_comma { } ; -enumlist_tail : COMMA enumlist_item { - Setattr($2,"_last",$2); - $$ = $2; - } - | enumlist_tail COMMA enumlist_item { - set_nextSibling(Getattr($1,"_last"), $3); - Setattr($1,"_last",$3); - $$ = $1; - } - ; - enumlist_item : optional_ignored_defines edecl_with_dox optional_ignored_defines { $$ = $2; } @@ -6419,19 +6418,6 @@ edecl_with_dox : edecl { $$ = $2; set_comment($2, $1); } - | edecl DOXYGENPOSTSTRING { - $$ = $1; - set_comment($1, $2); - } - | DOXYGENPOSTSTRING edecl { - $$ = $2; - set_comment(previousNode, $1); - } - | DOXYGENPOSTSTRING edecl DOXYGENPOSTSTRING { - $$ = $2; - set_comment(previousNode, $1); - set_comment($2, $3); - } ; edecl : identifier { From c3a2b7524e3c43e8be31e0ab100b5b00dd1fed71 Mon Sep 17 00:00:00 2001 From: Marko Klopcic Date: Tue, 23 Apr 2019 10:07:42 +0200 Subject: [PATCH 104/134] added section 'troubleshooting' --- Doc/Manual/Doxygen.html | 141 ++++++++++++++++++++++++++++++++++------ 1 file changed, 122 insertions(+), 19 deletions(-) diff --git a/Doc/Manual/Doxygen.html b/Doc/Manual/Doxygen.html index 8a847bb7e..75809e311 100644 --- a/Doc/Manual/Doxygen.html +++ b/Doc/Manual/Doxygen.html @@ -23,6 +23,7 @@

      • Additional command line options
      +
    • Troubleshooting
    • Doxygen to Javadoc
      • Basic example @@ -70,7 +71,7 @@ and Pydoc for the SWIG Java and Python modules. Other extensions could be added at a later date. The Doxygen Translation module originally started as a Google Summer of -Code proposal from Summer 2008. +Code proposal from Summer 2008.

        17.2 Preparations

        @@ -165,7 +166,7 @@ and in some special cases, like function parameter comments:
         void someFunction(
        -         int a ///< Some parameter 
        +         int a ///< Some parameter
              );
         
        @@ -442,6 +443,108 @@ This is only applicable to Java at the moment. ALSO TO BE ADDED (Javadoc auto brief?)

        + +

        17.3 Troubleshooting

        + + +

        +When running SWIG with command line switch -doxygen, it may happen +that SWIG will fail to parse the code, which is valid C++ code and +is parsed without problems without the switch. The problem is, +that Doxygen comments are not tokens (C/C++ compiler actually never +sees them) and that they can appear anywhere in the code. That's why it is +practically impossible to handle all corner cases with parser. +However, these problems can usually be avoided by minor changes in the +code or comment. Known problems and solutions are shown in this section. +

        + + +

        +Recommended approach is to first run SWIG without command line +switch -doxygen. When it successfully processes the code, +include the switch and fix problems with Doxygen comments. +

        + +

        17.3.1 Enums

        + + +

        +In C/C++ the comma after the last enum item is optional, but when +-doxygen switch is used the comma must not be present +if followed by Doxygen post-comment. For example, this snippet will +cause Error: Syntax error in input(3).: +

        + +
        +/**
        + * Comments after enum items.
        + */
        +enum SomeEnum
        +{
        +  SOME_ITEM_100, ///< Post comment for the first item
        +  SOME_ITEM_200, ///< Comma after enum item causes error.
        +};
        +
        + + +

        +Solution: remove the comma after the last enum item: +

        + +
        +/**
        + * Comments after enum items.
        + */
        +enum SomeEnum
        +{
        +  SOME_ITEM_100, ///< Post comment for the first item
        +  SOME_ITEM_200  ///< OK.
        +};
        +
        + + + + +

        17.3.2 Conditional compilation

        + + +

        + Inserting of conditional compilation preprocessor directive between + Doxygen comment and commented item may also break parsing: +

        + + +
        +class A {
        +  /**
        +   * Some func.
        +   */
        +  #ifndef SWIG
        +  void myfunc()
        +  {
        +  }
        +  #endif
        +};
        +
        + +

        + Solution is to move the directive above comment: +

        + +
        +class A {
        +  #ifndef SWIG
        +  /**
        +   * Some func.
        +   */
        +  void myfunc()
        +  {
        +  }
        +  #endif
        +};
        +
        + +

        17.3 Doxygen to Javadoc

        @@ -485,9 +588,9 @@ Simply running SWIG should result in the following code being present in Shapes.
         
         /**
        - * This is describing class Shape 
        - * @author Bob 
        - * 
        + * This is describing class Shape
        + * @author Bob
        + *
          */
         
         public class Shape {
        @@ -495,35 +598,35 @@ public class Shape {
         ...
         
         /**
        - * Important Variables 
        + * Important Variables
          */
           public void setX(double value) {
             ShapesJNI.Shape_x_set(swigCPtr, this, value);
           }
         
         /**
        - * Important Variables 
        + * Important Variables
          */
           public double getX() {
             return ShapesJNI.Shape_x_get(swigCPtr, this);
           }
         
         /**
        - * Moves the Shape 
        + * Moves the Shape
          */
           public void move(double dx, double dy) {
             ShapesJNI.Shape_move(swigCPtr, this, dx, dy);
           }
         
         /**
        - * @return the area 
        + * @return the area
          */
           public double area() {
             return ShapesJNI.Shape_area(swigCPtr, this);
           }
         
         /**
        - * @return the perimeter 
        + * @return the perimeter
          */
           public double perimeter() {
             return ShapesJNI.Shape_perimeter(swigCPtr, this);
        @@ -545,7 +648,7 @@ The Javadoc translator will handle most of the tags conversions (see the
         table below). It will also automatically translate link-objects
         params, in \see and \link...\endlink commands. For example,
         'someFunction(std::string)' will be converted to
        -'someFunction(String)'.  If 
        +'someFunction(String)'.  If
         you don't want such behaviour, you could turn this off by using the
         'doxygen:nolinktranslate' feature. Also all '\param' and '\tparam'
         commands are stripped out, if the specified parameter is not present in
        @@ -1103,31 +1206,31 @@ Simply running SWIG should result in the following code being present in Shapes.
         
         class Shape(_object):
             """
        -    This is describing class Shape 
        +    This is describing class Shape
             Authors:
        -    Bob 
        +    Bob
         
             """
        -    
        +
             ...
        -    
        +
             def move(self, *args):
                 """
        -        Moves the Shape 
        +        Moves the Shape
                 """
                 return _Shapes.Shape_move(self, *args)
         
             def area(self):
                 """
                 Return:
        -        the area 
        +        the area
                 """
                 return _Shapes.Shape_area(self)
         
             def perimeter(self):
                 """
                 Return:
        -        the perimeter 
        +        the perimeter
                 """
                 return _Shapes.Shape_perimeter(self)
         
        @@ -1712,7 +1815,7 @@ tool, for example: Examples/test-suite/java $ kdiff3 expected.txt got.txt - +

        Runtime tests in Java are implemented using Javadoc doclets. To make that work, you should have tools.jar from the JDK in your classpath. Or you should have JAVA_HOME From 4c6f33b1c985a70b15121056e099a47a67888b04 Mon Sep 17 00:00:00 2001 From: Marko Klopcic Date: Tue, 23 Apr 2019 10:25:35 +0200 Subject: [PATCH 105/134] improved section 'troubleshooting', moved before 'Developr info' --- Doc/Manual/Doxygen.html | 165 +++++++++++++++------------------------- 1 file changed, 63 insertions(+), 102 deletions(-) diff --git a/Doc/Manual/Doxygen.html b/Doc/Manual/Doxygen.html index 75809e311..4e4ed421c 100644 --- a/Doc/Manual/Doxygen.html +++ b/Doc/Manual/Doxygen.html @@ -23,7 +23,6 @@

    • Additional command line options
    -
  • Troubleshooting
  • Doxygen to Javadoc +
  • Troubleshooting
  • Developer information
    • Doxygen translator design @@ -444,107 +444,6 @@ ALSO TO BE ADDED (Javadoc auto brief?)

      -

      17.3 Troubleshooting

      - - -

      -When running SWIG with command line switch -doxygen, it may happen -that SWIG will fail to parse the code, which is valid C++ code and -is parsed without problems without the switch. The problem is, -that Doxygen comments are not tokens (C/C++ compiler actually never -sees them) and that they can appear anywhere in the code. That's why it is -practically impossible to handle all corner cases with parser. -However, these problems can usually be avoided by minor changes in the -code or comment. Known problems and solutions are shown in this section. -

      - - -

      -Recommended approach is to first run SWIG without command line -switch -doxygen. When it successfully processes the code, -include the switch and fix problems with Doxygen comments. -

      - -

      17.3.1 Enums

      - - -

      -In C/C++ the comma after the last enum item is optional, but when --doxygen switch is used the comma must not be present -if followed by Doxygen post-comment. For example, this snippet will -cause Error: Syntax error in input(3).: -

      - -
      -/**
      - * Comments after enum items.
      - */
      -enum SomeEnum
      -{
      -  SOME_ITEM_100, ///< Post comment for the first item
      -  SOME_ITEM_200, ///< Comma after enum item causes error.
      -};
      -
      - - -

      -Solution: remove the comma after the last enum item: -

      - -
      -/**
      - * Comments after enum items.
      - */
      -enum SomeEnum
      -{
      -  SOME_ITEM_100, ///< Post comment for the first item
      -  SOME_ITEM_200  ///< OK.
      -};
      -
      - - - - -

      17.3.2 Conditional compilation

      - - -

      - Inserting of conditional compilation preprocessor directive between - Doxygen comment and commented item may also break parsing: -

      - - -
      -class A {
      -  /**
      -   * Some func.
      -   */
      -  #ifndef SWIG
      -  void myfunc()
      -  {
      -  }
      -  #endif
      -};
      -
      - -

      - Solution is to move the directive above comment: -

      - -
      -class A {
      -  #ifndef SWIG
      -  /**
      -   * Some func.
      -   */
      -  void myfunc()
      -  {
      -  }
      -  #endif
      -};
      -
      - -

      17.3 Doxygen to Javadoc

      @@ -1737,6 +1636,68 @@ Here is the list of these tags: TO BE ADDED.

      +

      17.4 Troubleshooting

      + + +

      +When running SWIG with command line switch -doxygen, it may happen +that SWIG will fail to parse the code, which is valid C++ code and +is parsed without problems without the switch. The problem is, +that Doxygen comments are not tokens (C/C++ compiler actually never +sees them) and that they can appear anywhere in the code. That's why it is +practically impossible to handle all corner cases with parser. +However, these problems can usually be avoided by minor changes in the +code or comment. Known problems and solutions are shown in this section. +

      + + +

      +Recommended approach is to first run SWIG without command line +switch -doxygen. When it successfully processes the code, +include the switch and fix problems with Doxygen comments. +

      + + +

      17.3.1 Problem with conditional compilation

      + + +

      + Inserting conditional compilation preprocessor directive between + Doxygen comment and commented item may break parsing: +

      + + +
      +class A {
      +  /**
      +   * Some func.
      +   */
      +  #ifndef SWIG
      +  void myfunc()
      +  {
      +  }
      +  #endif
      +};
      +
      + +

      + Solution is to move the directive above comment: +

      + +
      +class A {
      +  #ifndef SWIG
      +  /**
      +   * Some func.
      +   */
      +  void myfunc()
      +  {
      +  }
      +  #endif
      +};
      +
      + +

      17.5 Developer information

      From 57965e29f6bcafeefbb80cf600692accaeb112d3 Mon Sep 17 00:00:00 2001 From: Marko Klopcic Date: Tue, 23 Apr 2019 11:34:25 +0200 Subject: [PATCH 106/134] updated troubleshooting section --- Doc/Manual/Doxygen.html | 39 +++++++++++++++++++-------------------- 1 file changed, 19 insertions(+), 20 deletions(-) diff --git a/Doc/Manual/Doxygen.html b/Doc/Manual/Doxygen.html index 4e4ed421c..67fe340d7 100644 --- a/Doc/Manual/Doxygen.html +++ b/Doc/Manual/Doxygen.html @@ -71,7 +71,7 @@ and Pydoc for the SWIG Java and Python modules. Other extensions could be added at a later date. The Doxygen Translation module originally started as a Google Summer of -Code proposal from Summer 2008. +Code proposal from Summer 2008.

      17.2 Preparations

      @@ -166,7 +166,7 @@ and in some special cases, like function parameter comments:
       void someFunction(
      -         int a ///< Some parameter
      +         int a ///< Some parameter 
            );
       
      @@ -443,7 +443,6 @@ This is only applicable to Java at the moment. ALSO TO BE ADDED (Javadoc auto brief?)

      -

      17.3 Doxygen to Javadoc

      @@ -487,9 +486,9 @@ Simply running SWIG should result in the following code being present in Shapes.
       
       /**
      - * This is describing class Shape
      - * @author Bob
      - *
      + * This is describing class Shape 
      + * @author Bob 
      + * 
        */
       
       public class Shape {
      @@ -497,35 +496,35 @@ public class Shape {
       ...
       
       /**
      - * Important Variables
      + * Important Variables 
        */
         public void setX(double value) {
           ShapesJNI.Shape_x_set(swigCPtr, this, value);
         }
       
       /**
      - * Important Variables
      + * Important Variables 
        */
         public double getX() {
           return ShapesJNI.Shape_x_get(swigCPtr, this);
         }
       
       /**
      - * Moves the Shape
      + * Moves the Shape 
        */
         public void move(double dx, double dy) {
           ShapesJNI.Shape_move(swigCPtr, this, dx, dy);
         }
       
       /**
      - * @return the area
      + * @return the area 
        */
         public double area() {
           return ShapesJNI.Shape_area(swigCPtr, this);
         }
       
       /**
      - * @return the perimeter
      + * @return the perimeter 
        */
         public double perimeter() {
           return ShapesJNI.Shape_perimeter(swigCPtr, this);
      @@ -547,7 +546,7 @@ The Javadoc translator will handle most of the tags conversions (see the
       table below). It will also automatically translate link-objects
       params, in \see and \link...\endlink commands. For example,
       'someFunction(std::string)' will be converted to
      -'someFunction(String)'.  If
      +'someFunction(String)'.  If 
       you don't want such behaviour, you could turn this off by using the
       'doxygen:nolinktranslate' feature. Also all '\param' and '\tparam'
       commands are stripped out, if the specified parameter is not present in
      @@ -1105,31 +1104,31 @@ Simply running SWIG should result in the following code being present in Shapes.
       
       class Shape(_object):
           """
      -    This is describing class Shape
      +    This is describing class Shape 
           Authors:
      -    Bob
      +    Bob 
       
           """
      -
      +    
           ...
      -
      +    
           def move(self, *args):
               """
      -        Moves the Shape
      +        Moves the Shape 
               """
               return _Shapes.Shape_move(self, *args)
       
           def area(self):
               """
               Return:
      -        the area
      +        the area 
               """
               return _Shapes.Shape_area(self)
       
           def perimeter(self):
               """
               Return:
      -        the perimeter
      +        the perimeter 
               """
               return _Shapes.Shape_perimeter(self)
       
      @@ -1776,7 +1775,7 @@ tool, for example: Examples/test-suite/java $ kdiff3 expected.txt got.txt - +

      Runtime tests in Java are implemented using Javadoc doclets. To make that work, you should have tools.jar from the JDK in your classpath. Or you should have JAVA_HOME From 453fe4cda84e99bb109c4a666c9ef2dd939ee371 Mon Sep 17 00:00:00 2001 From: Marko Klopcic Date: Tue, 23 Apr 2019 12:24:12 +0200 Subject: [PATCH 107/134] markok314: fixed section numbering because of inserted Doxygen troubleshooting section --- Doc/Manual/Doxygen.html | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/Doc/Manual/Doxygen.html b/Doc/Manual/Doxygen.html index 67fe340d7..3863aaa92 100644 --- a/Doc/Manual/Doxygen.html +++ b/Doc/Manual/Doxygen.html @@ -1635,7 +1635,7 @@ Here is the list of these tags: TO BE ADDED.

      -

      17.4 Troubleshooting

      +

      17.5 Troubleshooting

      @@ -1657,7 +1657,7 @@ include the switch and fix problems with Doxygen comments.

      -

      17.3.1 Problem with conditional compilation

      +

      17.5.1 Problem with conditional compilation

      @@ -1697,14 +1697,14 @@ class A { -

      17.5 Developer information

      +

      17.6 Developer information

      This section contains information for developers enhancing the Doxygen translator.

      -

      17.5.1 Doxygen translator design

      +

      17.6.1 Doxygen translator design

      @@ -1730,7 +1730,7 @@ class for translation into the target documentation language. For example, JavaDocConverter is the Javadoc module class.

      -

      17.5.2 Debugging the Doxygen parser and translator

      +

      17.6.2 Debugging the Doxygen parser and translator

      @@ -1743,7 +1743,7 @@ detailed debug information printing. -debug-doxygen-translator - Display Doxygen translator module debugging information -

      17.5.3 Tests

      +

      17.6.3 Tests

      @@ -1795,7 +1795,7 @@ Runtime tests in Python are just plain string comparisons of the __doc__ properties.

      -

      17.6 Extending to other languages

      +

      17.7 Extending to other languages

      From 8212473b935b2e982a81028d40c3d1b83e8b3e8a Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 19 Apr 2019 11:34:48 +0100 Subject: [PATCH 108/134] Add missing issue number --- CHANGES.current | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGES.current b/CHANGES.current index d36f43c41..5a86aea34 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -8,7 +8,7 @@ Version 4.0.0 (in progress) =========================== 2019-04-19: pbecherer - [Tcl] Fix Visual Studio 2015 and later compilation errors due to snprintf macro + [Tcl] #1508 Fix Visual Studio 2015 and later compilation errors due to snprintf macro definition. 2019-04-09: wsfulton From 03030e98a176e14e622bffd5d9542a64b05e1f9a Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Wed, 24 Apr 2019 07:32:50 +0100 Subject: [PATCH 109/134] Add -cgo as default to changes file --- CHANGES.current | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 5a86aea34..594bf7480 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,10 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-04-19: ianlancetaylor + [Go] #1055 When generating Go code, make -cgo the default. Add new -no-cgo option + to disable the default. + 2019-04-19: pbecherer [Tcl] #1508 Fix Visual Studio 2015 and later compilation errors due to snprintf macro definition. From fb0adb14c3be367fbb2ae69a1da644ec9d038b33 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Wed, 24 Apr 2019 08:04:15 +0100 Subject: [PATCH 110/134] Documentation: terminology consistency for command line options plus Doxygen tweaks. --- Doc/Manual/D.html | 8 ++++---- Doc/Manual/Doxygen.html | 22 +++++++++++----------- Doc/Manual/Java.html | 4 ++-- Doc/Manual/Preprocessor.html | 2 +- 4 files changed, 18 insertions(+), 18 deletions(-) diff --git a/Doc/Manual/D.html b/Doc/Manual/D.html index f1b3404a6..d97267a5b 100644 --- a/Doc/Manual/D.html +++ b/Doc/Manual/D.html @@ -56,7 +56,7 @@

      23.2 Command line invocation

      -

      To activate the D module, pass the -d option to SWIG at the command line. The same standard command line switches as with any other language module are available, plus the following D specific ones:

      +

      To activate the D module, pass the -d option to SWIG at the command line. The same standard command line options as with any other language module are available, plus the following D specific ones:

      -d2
      @@ -66,8 +66,8 @@
      -splitproxy
      -

      By default, SWIG generates two D modules: the proxy module, named like the source module (either specified via the %module directive or via the module command line switch), which contains all the proxy classes, functions, enums, etc., and the intermediary module (named like the proxy module, but suffixed with _im), which contains all the extern(C) function declarations and other private parts only used internally by the proxy module.

      -

      If the split proxy mode is enabled by passing this switch at the command line, all proxy classes and enums are emitted to their own D module instead. The main proxy module only contains free functions and constants in this case.

      +

      By default, SWIG generates two D modules: the proxy module, named like the source module (either specified via the %module directive or via the module command line option), which contains all the proxy classes, functions, enums, etc., and the intermediary module (named like the proxy module, but suffixed with _im), which contains all the extern(C) function declarations and other private parts only used internally by the proxy module.

      +

      If the split proxy mode is enabled by passing this option at the command line, all proxy classes and enums are emitted to their own D module instead. The main proxy module only contains free functions and constants in this case.

      -package <pkg>
      @@ -77,7 +77,7 @@
      -wrapperlibrary <wl>
      -

      The code SWIG generates to dynamically load the C/C++ wrapper layer looks for a library called $module_wrap by default. With this switch, you can override the name of the file the wrapper code loads at runtime (the lib prefix and the suffix for shared libraries are appended automatically, depending on the OS).

      +

      The code SWIG generates to dynamically load the C/C++ wrapper layer looks for a library called $module_wrap by default. With this option, you can override the name of the file the wrapper code loads at runtime (the lib prefix and the suffix for shared libraries are appended automatically, depending on the OS).

      This might especially be useful if you want to invoke SWIG several times on separate modules, but compile the resulting code into a single shared library.

      diff --git a/Doc/Manual/Doxygen.html b/Doc/Manual/Doxygen.html index 3863aaa92..100d95ba4 100644 --- a/Doc/Manual/Doxygen.html +++ b/Doc/Manual/Doxygen.html @@ -195,7 +195,7 @@ These structural commands are stripped out by SWIG and are not assigned to anyth

      Doxygen comments translation is disabled by default and needs to be explicitly -enabled using the command line -doxygen switch for the languages that +enabled using the command line -doxygen option for the languages that do support it (currently Java and Python).

      @@ -1639,12 +1639,12 @@ TO BE ADDED.

      -When running SWIG with command line switch -doxygen, it may happen +When running SWIG with command line option -doxygen, it may happen that SWIG will fail to parse the code, which is valid C++ code and -is parsed without problems without the switch. The problem is, -that Doxygen comments are not tokens (C/C++ compiler actually never +is parsed without problems without the option. The problem is, +that Doxygen comments are not tokens (the C/C++ compiler actually never sees them) and that they can appear anywhere in the code. That's why it is -practically impossible to handle all corner cases with parser. +practically impossible to handle all corner cases with the parser. However, these problems can usually be avoided by minor changes in the code or comment. Known problems and solutions are shown in this section.

      @@ -1652,8 +1652,8 @@ code or comment. Known problems and solutions are shown in this section.

      Recommended approach is to first run SWIG without command line -switch -doxygen. When it successfully processes the code, -include the switch and fix problems with Doxygen comments. +option -doxygen. When it successfully processes the code, +include the option and fix problems with Doxygen comments.

      @@ -1661,8 +1661,8 @@ include the switch and fix problems with Doxygen comments.

      - Inserting conditional compilation preprocessor directive between - Doxygen comment and commented item may break parsing: + Inserting a conditional compilation preprocessor directive between a + Doxygen comment and a commented item may break parsing:

      @@ -1680,7 +1680,7 @@ class A {

      - Solution is to move the directive above comment: + The solution is to move the directive above the comment:

      @@ -1734,7 +1734,7 @@ example, JavaDocConverter is the Javadoc module class.
       
       
       

      -There are two handy command line switches, that enable lots of +There are two handy command line options, that enable lots of detailed debug information printing.

      diff --git a/Doc/Manual/Java.html b/Doc/Manual/Java.html index e0c6aed03..db5f041e4 100644 --- a/Doc/Manual/Java.html +++ b/Doc/Manual/Java.html @@ -477,7 +477,7 @@ Exception in thread "main" java.lang.UnsatisfiedLinkError: exampleJNI.gcd(II)I

      where gcd is the missing JNI function that SWIG generated into the wrapper file. Also make sure you pass all of the required libraries to the linker. -The java -verbose:jni commandline switch is also a great way to get more information on unresolved symbols. +The java -verbose:jni commandline option is also a great way to get more information on unresolved symbols. One last piece of advice is to beware of the common faux pas of having more than one native library version in your path.

      @@ -645,7 +645,7 @@ java::

      To build the DLL and compile the java code, run NMAKE (you may need to run vcvars32 first). This is a pretty simplistic Makefile, but hopefully its enough to get you started. -Of course you may want to make changes for it to work for C++ by adding in the -c++ command line switch for swig and replacing .c with .cxx. +Of course you may want to make changes for it to work for C++ by adding in the -c++ command line option for swig and replacing .c with .cxx.

      diff --git a/Doc/Manual/Preprocessor.html b/Doc/Manual/Preprocessor.html index f28f7b2be..3d1bb453e 100644 --- a/Doc/Manual/Preprocessor.html +++ b/Doc/Manual/Preprocessor.html @@ -458,7 +458,7 @@ would generate

      Like many compilers, SWIG supports a -E command line option to display the output from the preprocessor. -When the -E switch is used, SWIG will not generate any wrappers. +When the -E option is used, SWIG will not generate any wrappers. Instead the results after the preprocessor has run are displayed. This might be useful as an aid to debugging and viewing the results of macro expansions.

      From 8df627eab87efebbe0ee555d379e62dce2e00725 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Wed, 24 Apr 2019 08:06:10 +0100 Subject: [PATCH 111/134] HTML section numbering update --- Doc/Manual/Contents.html | 4 ++++ Doc/Manual/Doxygen.html | 3 +++ 2 files changed, 7 insertions(+) diff --git a/Doc/Manual/Contents.html b/Doc/Manual/Contents.html index fa1ef9b5c..57aef5b8a 100644 --- a/Doc/Manual/Contents.html +++ b/Doc/Manual/Contents.html @@ -647,6 +647,10 @@
    • Unsupported tags
    • Further details
    +
  • Troubleshooting +
  • Developer information
    • Doxygen translator design diff --git a/Doc/Manual/Doxygen.html b/Doc/Manual/Doxygen.html index 100d95ba4..ff025c047 100644 --- a/Doc/Manual/Doxygen.html +++ b/Doc/Manual/Doxygen.html @@ -38,6 +38,9 @@
    • Further details
  • Troubleshooting +
  • Developer information
    • Doxygen translator design From b04cc850ab86091dae6923ca128a2ea491c6b2c0 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Wed, 24 Apr 2019 08:13:19 +0100 Subject: [PATCH 112/134] Add recent doxygen fixes to changes file --- CHANGES.current | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/CHANGES.current b/CHANGES.current index 594bf7480..fa13e9e48 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -7,6 +7,12 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/ Version 4.0.0 (in progress) =========================== +2019-04-24: vadz + #1517 Fix crash if "@return" Doxygen tag was used on a node without any return type. + +2019-04-24: vadz + #1515 Fix parsing of enums with trailing comma when using -doxygen. + 2019-04-19: ianlancetaylor [Go] #1055 When generating Go code, make -cgo the default. Add new -no-cgo option to disable the default. From 8a1c09e280e323ba48407a9a9ae86f19d1c7abbe Mon Sep 17 00:00:00 2001 From: Ian Lance Taylor Date: Wed, 24 Apr 2019 21:43:38 -0700 Subject: [PATCH 113/134] Fix Go tests to run in module mode Stop using relative imports and add a go.mod file. Tested against Go 1.6 through Go pre-1.13, and gccgo. --- Doc/Manual/Go.html | 7 ++ Examples/Makefile.in | 57 ++++++++------ Examples/go/callback/runme.go | 3 +- Examples/go/class/runme.go | 3 +- Examples/go/constants/runme.go | 3 +- Examples/go/director/runme.go | 3 +- Examples/go/enum/runme.go | 3 +- Examples/go/extend/runme.go | 3 +- Examples/go/funcptr/runme.go | 3 +- Examples/go/multimap/runme.go | 3 +- Examples/go/pointer/runme.go | 3 +- Examples/go/reference/runme.go | 3 +- Examples/go/simple/runme.go | 3 +- Examples/go/template/runme.go | 3 +- Examples/go/variables/runme.go | 3 +- Examples/test-suite/go/Makefile.in | 78 ++++++++++++------- .../test-suite/go/abstract_access_runme.go | 2 +- .../test-suite/go/abstract_typedef2_runme.go | 2 +- .../test-suite/go/abstract_typedef_runme.go | 2 +- .../test-suite/go/abstract_virtual_runme.go | 2 +- Examples/test-suite/go/argout_runme.go | 2 +- Examples/test-suite/go/array_member_runme.go | 2 +- Examples/test-suite/go/arrays_global_runme.go | 2 +- Examples/test-suite/go/char_binary_runme.go | 2 +- Examples/test-suite/go/class_ignore_runme.go | 2 +- .../test-suite/go/class_scope_weird_runme.go | 2 +- .../test-suite/go/compactdefaultargs_runme.go | 2 +- Examples/test-suite/go/constover_runme.go | 3 +- .../test-suite/go/constructor_copy_runme.go | 2 +- Examples/test-suite/go/contract_runme.go | 2 +- ...cpp11_strongly_typed_enumerations_runme.go | 2 +- Examples/test-suite/go/cpp_enum_runme.go | 2 +- Examples/test-suite/go/cpp_namespace_runme.go | 2 +- Examples/test-suite/go/cpp_static_runme.go | 2 +- Examples/test-suite/go/default_args_runme.go | 2 +- .../go/default_constructor_runme.go | 2 +- .../go/director_alternating_runme.go | 2 +- .../test-suite/go/director_basic_runme.go | 2 +- .../test-suite/go/director_classic_runme.go | 2 +- .../test-suite/go/director_default_runme.go | 2 +- .../test-suite/go/director_detect_runme.go | 2 +- Examples/test-suite/go/director_enum_runme.go | 2 +- .../test-suite/go/director_exception_runme.go | 2 +- .../test-suite/go/director_extend_runme.go | 2 +- .../test-suite/go/director_finalizer_runme.go | 2 +- Examples/test-suite/go/director_frob_runme.go | 2 +- .../test-suite/go/director_nested_runme.go | 2 +- .../test-suite/go/director_profile_runme.go | 2 +- .../test-suite/go/director_protected_runme.go | 2 +- .../test-suite/go/director_string_runme.go | 2 +- .../test-suite/go/director_unroll_runme.go | 2 +- Examples/test-suite/go/disown_runme.go | 2 +- Examples/test-suite/go/dynamic_cast_runme.go | 2 +- Examples/test-suite/go/empty_c_runme.go | 2 +- Examples/test-suite/go/empty_runme.go | 2 +- Examples/test-suite/go/enum_template_runme.go | 2 +- Examples/test-suite/go/enums_runme.go | 2 +- .../test-suite/go/exception_order_runme.go | 2 +- .../test-suite/go/extend_placement_runme.go | 2 +- .../test-suite/go/extend_template_ns_runme.go | 2 +- .../test-suite/go/extend_template_runme.go | 2 +- .../test-suite/go/extend_variable_runme.go | 2 +- Examples/test-suite/go/extern_c_runme.go | 2 +- Examples/test-suite/go/friends_runme.go | 2 +- Examples/test-suite/go/fvirtual_runme.go | 2 +- Examples/test-suite/go/global_ns_arg_runme.go | 2 +- .../test-suite/go/go_director_inout_runme.go | 2 +- Examples/test-suite/go/go_inout_runme.go | 2 +- .../test-suite/go/go_subdir_import_runme.go | 6 +- Examples/test-suite/go/grouping_runme.go | 2 +- .../test-suite/go/import_nomodule_runme.go | 2 +- Examples/test-suite/go/imports_runme.go | 4 +- Examples/test-suite/go/inctest_runme.go | 2 +- .../test-suite/go/inherit_member_runme.go | 2 +- .../test-suite/go/inherit_missing_runme.go | 2 +- Examples/test-suite/go/input_runme.go | 2 +- .../test-suite/go/keyword_rename_c_runme.go | 2 +- .../test-suite/go/keyword_rename_runme.go | 2 +- Examples/test-suite/go/li_attribute_runme.go | 2 +- .../test-suite/go/li_carrays_cpp_runme.go | 2 +- Examples/test-suite/go/li_carrays_runme.go | 2 +- Examples/test-suite/go/li_cdata_cpp_runme.go | 2 +- Examples/test-suite/go/li_cdata_runme.go | 2 +- Examples/test-suite/go/li_cmalloc_runme.go | 2 +- .../test-suite/go/li_cpointer_cpp_runme.go | 2 +- Examples/test-suite/go/li_cpointer_runme.go | 2 +- Examples/test-suite/go/li_std_map_runme.go | 2 +- .../test-suite/go/li_std_vector_ptr_runme.go | 2 +- .../test-suite/go/member_pointer_runme.go | 2 +- .../test-suite/go/memberin_extend_c_runme.go | 2 +- Examples/test-suite/go/minherit_runme.go | 2 +- Examples/test-suite/go/mod_runme.go | 4 +- Examples/test-suite/go/multi_import_runme.go | 4 +- .../test-suite/go/namespace_class_runme.go | 2 +- .../test-suite/go/namespace_typemap_runme.go | 2 +- .../go/namespace_virtual_method_runme.go | 2 +- Examples/test-suite/go/naturalvar_runme.go | 2 +- .../test-suite/go/nested_workaround_runme.go | 2 +- .../go/overload_complicated_runme.go | 2 +- Examples/test-suite/go/overload_copy_runme.go | 2 +- .../test-suite/go/overload_extend2_runme.go | 2 +- .../test-suite/go/overload_extend_c_runme.go | 2 +- .../test-suite/go/overload_extend_runme.go | 2 +- .../go/overload_polymorphic_runme.go | 2 +- .../test-suite/go/overload_rename_runme.go | 2 +- .../test-suite/go/overload_simple_runme.go | 2 +- .../test-suite/go/overload_subtype_runme.go | 2 +- .../go/overload_template_fast_runme.go | 2 +- .../test-suite/go/overload_template_runme.go | 2 +- Examples/test-suite/go/preproc_runme.go | 2 +- Examples/test-suite/go/primitive_ref_runme.go | 2 +- Examples/test-suite/go/profiletest_runme.go | 2 +- Examples/test-suite/go/refcount_runme.go | 2 +- .../go/reference_global_vars_runme.go | 2 +- Examples/test-suite/go/rename_scope_runme.go | 2 +- Examples/test-suite/go/rename_simple_runme.go | 2 +- .../go/rename_strip_encoder_runme.go | 2 +- Examples/test-suite/go/ret_by_value_runme.go | 2 +- .../test-suite/go/return_const_value_runme.go | 2 +- .../go/smart_pointer_extend_runme.go | 2 +- .../go/smart_pointer_member_runme.go | 2 +- .../go/smart_pointer_multi_runme.go | 2 +- .../go/smart_pointer_multi_typedef_runme.go | 2 +- .../go/smart_pointer_overload_runme.go | 2 +- .../go/smart_pointer_rename_runme.go | 2 +- .../go/smart_pointer_simple_runme.go | 2 +- .../smart_pointer_templatevariables_runme.go | 2 +- .../go/smart_pointer_typedef_runme.go | 2 +- Examples/test-suite/go/sneaky1_runme.go | 2 +- .../go/special_variable_macros_runme.go | 2 +- .../go/static_const_member_2_runme.go | 2 +- .../go/struct_initialization_runme.go | 2 +- Examples/test-suite/go/struct_rename_runme.go | 2 +- Examples/test-suite/go/struct_value_runme.go | 2 +- .../go/template_default_arg_runme.go | 2 +- .../test-suite/go/template_extend1_runme.go | 2 +- .../test-suite/go/template_extend2_runme.go | 2 +- .../test-suite/go/template_inherit_runme.go | 2 +- Examples/test-suite/go/template_ns4_runme.go | 2 +- Examples/test-suite/go/template_ns_runme.go | 2 +- .../test-suite/go/template_opaque_runme.go | 2 +- .../test-suite/go/template_ref_type_runme.go | 2 +- .../test-suite/go/template_rename_runme.go | 2 +- .../test-suite/go/template_static_runme.go | 2 +- .../go/template_tbase_template_runme.go | 2 +- .../go/template_type_namespace_runme.go | 2 +- .../go/template_typedef_cplx3_runme.go | 2 +- .../go/template_typedef_cplx4_runme.go | 2 +- .../test-suite/go/threads_exception_runme.go | 2 +- Examples/test-suite/go/typedef_class_runme.go | 2 +- .../test-suite/go/typedef_funcptr_runme.go | 2 +- .../test-suite/go/typedef_inherit_runme.go | 2 +- Examples/test-suite/go/typedef_scope_runme.go | 2 +- .../test-suite/go/typemap_namespace_runme.go | 2 +- .../test-suite/go/typemap_ns_using_runme.go | 2 +- .../go/typemap_out_optimal_runme.go | 2 +- Examples/test-suite/go/typename_runme.go | 2 +- Examples/test-suite/go/unions_runme.go | 2 +- Examples/test-suite/go/using1_runme.go | 2 +- Examples/test-suite/go/using2_runme.go | 2 +- .../test-suite/go/using_composition_runme.go | 2 +- Examples/test-suite/go/using_extend_runme.go | 2 +- Examples/test-suite/go/using_inherit_runme.go | 2 +- Examples/test-suite/go/using_private_runme.go | 2 +- .../test-suite/go/using_protected_runme.go | 2 +- .../test-suite/go/varargs_overload_runme.go | 2 +- Examples/test-suite/go/varargs_runme.go | 2 +- .../test-suite/go/virtual_derivation_runme.go | 2 +- Examples/test-suite/go/virtual_poly_runme.go | 2 +- Examples/test-suite/go/voidtest_runme.go | 2 +- Examples/test-suite/go/wrapmacro_runme.go | 2 +- Examples/test-suite/go_subdir_import.list | 2 +- Source/Modules/go.cxx | 21 ++++- 173 files changed, 298 insertions(+), 227 deletions(-) diff --git a/Doc/Manual/Go.html b/Doc/Manual/Go.html index dbea7de96..cfa56dbcf 100644 --- a/Doc/Manual/Go.html +++ b/Doc/Manual/Go.html @@ -266,6 +266,13 @@ swig -go -help ignored. + +-import-prefix <prefix> +A prefix to add when turning a %import prefix in the SWIG + interface file into an import statement in the Go file. For + example, with -import-prefix mymodule, a SWIG + interface file %import mypackage will become a Go + import statement import "mymodule/mypackage". diff --git a/Examples/Makefile.in b/Examples/Makefile.in index d7b71af2f..98be7873f 100644 --- a/Examples/Makefile.in +++ b/Examples/Makefile.in @@ -1457,7 +1457,8 @@ GOPACK = `if $(GO1) ; then echo go tool pack; else echo gopack; fi` GOPACKAGE = $(notdir $(INTERFACE:.i=.a)) -GOPATHDIR = gopath/src/$(INTERFACE:.i=) +GOPATHPARENTDIR = gopath/$(GOMOD)/src +GOPATHDIR = $(GOPATHPARENTDIR)/$(INTERFACE:.i=) GOOBJEXT = `if $(GO15); then echo o; else echo $(GOC:c=); fi` GOGCOBJS = $(GOSRCS:.go=.$(GOOBJEXT)) @@ -1467,6 +1468,16 @@ GOGCCOBJS = $(GOSRCS:.go=.@OBJEXT@) # Build a Go module (C) # ---------------------------------------------------------------- +$(GOPATHPARENTDIR)/go.mod: + @mkdir gopath 2>/dev/null || true + @mkdir gopath/$(GOMOD) 2>/dev/null || true + @mkdir gopath/$(GOMOD)/src 2>/dev/null || true + @mkdir $(GOPATHDIR) 2>/dev/null || true + echo "module swigtests" > $(GOPATHDIR)/go.mod + echo "" >> $(GOPATHDIR)/go.mod + echo "go 1.12" >> $(GOPATHDIR)/go.mod + mv -f $(GOPATHDIR)/go.mod $(GOPATHPARENTDIR)/go.mod + go_nocgo: $(SRCDIR_SRCS) $(SWIG) -go -no-cgo $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) if $(GO12) || $(GO13) || $(GO15) || $(GOGCC); then \ @@ -1503,11 +1514,12 @@ go_nocgo: $(SRCDIR_SRCS) fi; \ fi -go: $(SRCDIR_SRCS) - $(SWIG) -go $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) +go: $(SRCDIR_SRCS) $(GOPATHPARENTDIR)/go.mod + $(SWIG) -go -import-prefix swigtests $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ISRCS) $(INTERFACEPATH) @mkdir gopath 2>/dev/null || true - @mkdir gopath/src 2>/dev/null || true - @mkdir gopath/src/$(INTERFACE:.i=) 2>/dev/null || true + @mkdir gopath/$(GOMOD) 2>/dev/null || true + @mkdir gopath/$(GOMOD)/src 2>/dev/null || true + @mkdir $(GOPATHDIR) 2>/dev/null || true rm -f $(GOPATHDIR)/* cp $(ISRCS) $(GOPATHDIR)/ if test -f $(IWRAP:.i=.h); then \ @@ -1517,7 +1529,7 @@ go: $(SRCDIR_SRCS) cp $(SRCDIR_SRCS) $(GOPATHDIR)/; \ fi cp $(GOSRCS) $(GOPATHDIR)/ - GOPATH=`pwd`/gopath; \ + GOPATH=`pwd`/gopath/$(GOMOD); \ export GOPATH; \ CGO_CPPFLAGS="$(CPPFLAGS) $(INCLUDES) -I `cd $(SRCDIR) && pwd` -I `pwd`"; \ export CGO_CPPFLAGS; \ @@ -1526,17 +1538,16 @@ go: $(SRCDIR_SRCS) CGO_LDFLAGS="$(LDFLAGS) -lm"; \ export CGO_LDFLAGS; \ (cd $(GOPATHDIR)/ && $(COMPILETOOL) $(GO) build `if $(GOGCC); then echo -compiler=gccgo; fi` -o $(GOPACKAGE)) - cp $(GOPATHDIR)/$(GOPACKAGE) $(dir $(INTERFACE))/$(GOPACKAGE) if $(GOGCC); then \ - cp $(dir $(INTERFACE))/$(GOPACKAGE) $(dir $(INTERFACE))/$(GOPACKAGE:.a=.gox); \ + cp $(GOPATHDIR)/$(GOPACKAGE) $(GOPATHDIR)/$(GOPACKAGE:.a=.gox); \ fi if test -f $(SRCDIR)$(RUNME).go; then \ if $(GOGCC) ; then \ - $(COMPILETOOL) $(GCCGO) -c -g $(SRCDIR)$(RUNME).go; \ - $(COMPILETOOL) $(GCCGO) -o $(RUNME) $(RUNME).@OBJEXT@ $(dir $(INTERFACE))/$(GOPACKAGE); \ + $(COMPILETOOL) $(GCCGO) -c -g -I $(GOPATHDIR) $(SRCDIR)$(RUNME).go; \ + $(COMPILETOOL) $(GCCGO) -o $(RUNME) $(RUNME).@OBJEXT@ $(GOPATHDIR)/$(GOPACKAGE); \ elif $(GO12) || $(GO13) || $(GO15); then \ - $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -o $(RUNME).$(GOOBJEXT) $(SRCDIR)$(RUNME).go; \ - $(COMPILETOOL) $(GOTOOL) $(GOLD) -linkmode external -extld "$(CC)" -extldflags "$(CFLAGS) $(LDFLAGS)" -o $(RUNME) $(RUNME).$(GOOBJEXT); \ + $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I $(GOPATHDIR) -o $(RUNME).$(GOOBJEXT) $(SRCDIR)$(RUNME).go; \ + $(COMPILETOOL) $(GOTOOL) $(GOLD) -L $(GOPATHDIR) -linkmode external -extld "$(CC)" -extldflags "$(CFLAGS) $(LDFLAGS)" -o $(RUNME) $(RUNME).$(GOOBJEXT); \ else \ $(COMPILETOOL) $(GO) $(GOCOMPILEARG) $(SRCDIR)$(RUNME).go; \ $(COMPILETOOL) $(GOTOOL) $(GOLD) -r $${GOROOT:-`go env GOROOT`}/pkg/$${GOOS:-`go env GOOS`}_$${GOARCH:-`go env GOARCH`}:. -o $(RUNME) $(RUNME).$(GOOBJEXT); \ @@ -1595,11 +1606,12 @@ go_cpp_nocgo: $(SRCDIR_SRCS) fi; \ fi -go_cpp: $(SRCDIR_SRCS) - $(SWIG) -go -c++ $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) +go_cpp: $(SRCDIR_SRCS) $(GOPATHPARENTDIR)/go.mod + $(SWIG) -go -c++ -import-prefix swigtests $(GOOPT) $(GOSWIGARG) $(SWIGOPT) -o $(ICXXSRCS) $(INTERFACEPATH) @mkdir gopath 2>/dev/null || true - @mkdir gopath/src 2>/dev/null || true - @mkdir gopath/src/$(INTERFACE:.i=) 2>/dev/null || true + @mkdir gopath/$(GOMOD) 2>/dev/null || true + @mkdir gopath/$(GOMOD)/src 2>/dev/null || true + @mkdir $(GOPATHDIR) 2>/dev/null || true rm -f $(GOPATHDIR)/* cp $(ICXXSRCS) $(GOPATHDIR)/ if test -f $(IWRAP:.i=.h); then \ @@ -1612,7 +1624,7 @@ go_cpp: $(SRCDIR_SRCS) cp $(SRCDIR_SRCS) $(GOPATHDIR)/; \ fi cp $(GOSRCS) $(GOPATHDIR)/ - GOPATH=`pwd`/gopath; \ + GOPATH=`pwd`/gopath/$(GOMOD); \ export GOPATH; \ CGO_CPPFLAGS="$(CPPFLAGS) $(INCLUDES) -I `cd $(SRCDIR) && pwd` -I `pwd`"; \ export CGO_CPPFLAGS; \ @@ -1623,17 +1635,16 @@ go_cpp: $(SRCDIR_SRCS) CGO_LDFLAGS="$(LDFLAGS) -lm"; \ export CGO_LDFLAGS; \ (cd $(GOPATHDIR) && $(COMPILETOOL) $(GO) build `if $(GOGCC); then echo -compiler=gccgo; fi` -o $(GOPACKAGE)) - cp $(GOPATHDIR)/$(GOPACKAGE) $(dir $(INTERFACE))/$(GOPACKAGE) if $(GOGCC); then \ - cp $(dir $(INTERFACE))/$(GOPACKAGE) $(dir $(INTERFACE))/$(GOPACKAGE:.a=.gox); \ + cp $(GOPATHDIR)/$(GOPACKAGE) $(GOPATHDIR)/$(GOPACKAGE:.a=.gox); \ fi if test -f $(SRCDIR)$(RUNME).go; then \ if $(GOGCC) ; then \ - $(COMPILETOOL) $(GCCGO) -g -c $(SRCDIR)$(RUNME).go; \ - $(COMPILETOOL) $(GCCGO) -o $(RUNME) $(RUNME).@OBJEXT@ $(dir $(INTERFACE))/$(GOPACKAGE) -lstdc++; \ + $(COMPILETOOL) $(GCCGO) -g -c -I $(GOPATHDIR) $(SRCDIR)$(RUNME).go; \ + $(COMPILETOOL) $(GCCGO) -o $(RUNME) $(RUNME).@OBJEXT@ $(GOPATHDIR)/$(GOPACKAGE) -lstdc++; \ elif $(GO12) || $(GO13) || $(GO15); then \ - $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -o $(RUNME).$(GOOBJEXT) $(SRCDIR)$(RUNME).go; \ - $(COMPILETOOL) $(GOTOOL) $(GOLD) -linkmode external -extld "$(CXX)" -extldflags "$(CXXFLAGS) $(LDFLAGS)" -o $(RUNME) $(RUNME).$(GOOBJEXT); \ + $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I $(GOPATHDIR) -o $(RUNME).$(GOOBJEXT) $(SRCDIR)$(RUNME).go; \ + $(COMPILETOOL) $(GOTOOL) $(GOLD) -L $(GOPATHDIR) -linkmode external -extld "$(CXX)" -extldflags "$(CXXFLAGS) $(LDFLAGS)" -o $(RUNME) $(RUNME).$(GOOBJEXT); \ else \ $(COMPILETOOL) $(GO) $(GOCOMPILEARG) $(SRCDIR)$(RUNME).go; \ $(COMPILETOOL) $(GOTOOL) $(GOLD) -r $${GOROOT:-`go env GOROOT`}/pkg/$${GOOS:-`go env GOOS`}_$${GOARCH:-`go env GOARCH`}:. -o $(RUNME) $(RUNME).$(GOOBJEXT); \ diff --git a/Examples/go/callback/runme.go b/Examples/go/callback/runme.go index 03ab0c5e2..2c1d81343 100644 --- a/Examples/go/callback/runme.go +++ b/Examples/go/callback/runme.go @@ -1,8 +1,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/class/runme.go b/Examples/go/class/runme.go index 8d68afb61..d2f292ed4 100644 --- a/Examples/go/class/runme.go +++ b/Examples/go/class/runme.go @@ -3,8 +3,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/constants/runme.go b/Examples/go/constants/runme.go index 1427997a0..d56fd62c8 100644 --- a/Examples/go/constants/runme.go +++ b/Examples/go/constants/runme.go @@ -1,8 +1,9 @@ package main import ( - "./example" "fmt" + + "example" ) func main() { diff --git a/Examples/go/director/runme.go b/Examples/go/director/runme.go index 0d839bc88..0e0da07bd 100644 --- a/Examples/go/director/runme.go +++ b/Examples/go/director/runme.go @@ -1,9 +1,10 @@ package main import ( - "./example" "fmt" "os" + + "example" ) func Compare(name string, got string, exp string) error { diff --git a/Examples/go/enum/runme.go b/Examples/go/enum/runme.go index 99d2651f4..50887056e 100644 --- a/Examples/go/enum/runme.go +++ b/Examples/go/enum/runme.go @@ -1,8 +1,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/extend/runme.go b/Examples/go/extend/runme.go index a56968937..af64a6e5d 100644 --- a/Examples/go/extend/runme.go +++ b/Examples/go/extend/runme.go @@ -3,8 +3,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/funcptr/runme.go b/Examples/go/funcptr/runme.go index 44dae3c9e..4b20db4fb 100644 --- a/Examples/go/funcptr/runme.go +++ b/Examples/go/funcptr/runme.go @@ -1,8 +1,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/multimap/runme.go b/Examples/go/multimap/runme.go index 390205a80..571fac7c2 100644 --- a/Examples/go/multimap/runme.go +++ b/Examples/go/multimap/runme.go @@ -1,8 +1,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/pointer/runme.go b/Examples/go/pointer/runme.go index 1414d341e..0cf340f51 100644 --- a/Examples/go/pointer/runme.go +++ b/Examples/go/pointer/runme.go @@ -1,8 +1,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/reference/runme.go b/Examples/go/reference/runme.go index 004a04c2e..9999733b3 100644 --- a/Examples/go/reference/runme.go +++ b/Examples/go/reference/runme.go @@ -3,8 +3,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/simple/runme.go b/Examples/go/simple/runme.go index 9eb0ff454..0bd4657f9 100644 --- a/Examples/go/simple/runme.go +++ b/Examples/go/simple/runme.go @@ -1,8 +1,9 @@ package main import ( - "./example" "fmt" + + "example" ) func main() { diff --git a/Examples/go/template/runme.go b/Examples/go/template/runme.go index fca2f1b75..347795377 100644 --- a/Examples/go/template/runme.go +++ b/Examples/go/template/runme.go @@ -3,8 +3,9 @@ package main import ( - . "./example" "fmt" + + . "example" ) func main() { diff --git a/Examples/go/variables/runme.go b/Examples/go/variables/runme.go index 3d9737f5c..e2dd0c67f 100644 --- a/Examples/go/variables/runme.go +++ b/Examples/go/variables/runme.go @@ -3,8 +3,9 @@ package main import ( - "./example" "fmt" + + "example" ) func main() { diff --git a/Examples/test-suite/go/Makefile.in b/Examples/test-suite/go/Makefile.in index b7be554d7..d07a56bec 100644 --- a/Examples/test-suite/go/Makefile.in +++ b/Examples/test-suite/go/Makefile.in @@ -73,7 +73,18 @@ INCLUDES = -I$(abs_top_srcdir)/$(EXAMPLES)/$(TEST_SUITE) %.multicpptest: $(setup) - +$(swig_and_compile_multi_cpp) + mkdir -p gopath/$*/src 2>/dev/null || true + if ! test -d gopath/$*/src/swigtests; then \ + (cd gopath/$*/src && ln -s . swigtests); \ + fi + +for f in `cat $(top_srcdir)/$(EXAMPLES)/$(TEST_SUITE)/$*.list` ; do \ + $(MAKE) -f $(top_builddir)/$(EXAMPLES)/Makefile SRCDIR='$(SRCDIR)' CXXSRCS='$(CXXSRCS)' \ + SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ + LIBS='$(LIBS)' INCLUDES='$(INCLUDES)' SWIGOPT='$(SWIGOPT)' NOLINK=true \ + TARGET="$(TARGETPREFIX)$${f}$(TARGETSUFFIX)" INTERFACEDIR='$(INTERFACEDIR)' INTERFACE="$$f.i" \ + GOMOD="$*" \ + $(LANGUAGE)$(VARIANT)_cpp; \ + done $(run_multi_testcase) li_windows.cpptest: @@ -82,50 +93,55 @@ li_windows.cpptest: multi_import.multicpptest: $(setup) + mkdir -p gopath/multi_import/src 2>/dev/null || true + if ! test -d gopath/multi_import/src/swigtests; then \ + (cd gopath/multi_import/src && ln -s . swigtests); \ + fi for f in multi_import_b multi_import_a; do \ $(MAKE) -f $(top_builddir)/$(EXAMPLES)/Makefile SRCDIR='$(SRCDIR)' CXXSRCS='$(CXXSRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ LIBS='$(LIBS)' INCLUDES='$(INCLUDES)' SWIGOPT='$(SWIGOPT)' NOLINK=true \ TARGET="$(TARGETPREFIX)$${f}$(TARGETSUFFIX)" INTERFACEDIR='$(INTERFACEDIR)' INTERFACE="$$f.i" \ + GOMOD="multi_import" \ $(LANGUAGE)$(VARIANT)_cpp; \ done $(run_multi_testcase) go_subdir_import.multicpptest: $(setup) - mkdir -p testdir/go_subdir_import/ - mkdir -p gopath/src/testdir/go_subdir_import/ + mkdir -p gopath/go_subdir_import/src 2>/dev/null || true + if ! test -d gopath/go_subdir_import/src/swigtests; then \ + (cd gopath/go_subdir_import/src && ln -s . swigtests); \ + fi + mkdir -p testdir/go_subdir_import 2>/dev/null || true + mkdir -p gopath/go_subdir_import/src/testdir/go_subdir_import 2>/dev/null || true $(MAKE) -f $(top_builddir)/$(EXAMPLES)/Makefile SRCDIR='$(SRCDIR)' CXXSRCS='$(CXXSRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ LIBS='$(LIBS)' INTERFACEPATH='$(SRCDIR)$(INTERFACEDIR)go_subdir_import_b.i' \ INCLUDES='$(INCLUDES)' SWIGOPT='$(SWIGOPT) -outdir .' NOLINK=true \ TARGET='$(TARGETPREFIX)go_subdir_import_b$(TARGETSUFFIX)' INTERFACEDIR='$(INTERFACEDIR)' \ INTERFACE='testdir/go_subdir_import/go_subdir_import_b.i' \ + GOMOD="go_subdir_import" \ $(LANGUAGE)$(VARIANT)_cpp; for f in testdir/go_subdir_import/go_subdir_import_c go_subdir_import_a ; do \ $(MAKE) -f $(top_builddir)/$(EXAMPLES)/Makefile SRCDIR='$(SRCDIR)' CXXSRCS='$(CXXSRCS)' \ SWIG_LIB_DIR='$(SWIG_LIB_DIR)' SWIGEXE='$(SWIGEXE)' \ LIBS='$(LIBS)' INCLUDES='$(INCLUDES)' SWIGOPT='$(SWIGOPT)' NOLINK=true \ TARGET="$(TARGETPREFIX)$${f}$(TARGETSUFFIX)" INTERFACEDIR='$(INTERFACEDIR)' INTERFACE="$$f.i" \ + GOMOD="go_subdir_import" \ $(LANGUAGE)$(VARIANT)_cpp; \ done - if $(GOGCC); then \ - cp gopath/src/testdir/go_subdir_import/go_subdir_import_b/go_subdir_import_b.a gopath/src/testdir/go_subdir_import/go_subdir_import_b.gox; \ - cp gopath/src/testdir/go_subdir_import/go_subdir_import_b/go_subdir_import_b.a .; \ - cp gopath/src/testdir/go_subdir_import/go_subdir_import_c/go_subdir_import_c.a gopath/src/testdir/go_subdir_import/go_subdir_import_c.gox; \ - cp gopath/src/testdir/go_subdir_import/go_subdir_import_c/go_subdir_import_c.a testdir/go_subdir_import/; \ - fi $(run_multi_testcase) # Runs the testcase. run_testcase = \ if test -f $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX); then \ if $(GOGCC) ; then \ - $(COMPILETOOL) $(GCCGO) -c -g -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ - $(COMPILETOOL) $(GCCGO) -o $*_runme $(SCRIPTPREFIX)$*_runme.@OBJEXT@ $*.a; \ + $(COMPILETOOL) $(GCCGO) -c -g -I gopath/src/$* $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ + $(COMPILETOOL) $(GCCGO) -o $*_runme $(SCRIPTPREFIX)$*_runme.@OBJEXT@ gopath/src/$*/$*.a; \ elif $(GO12) || $(GO13) || $(GO15); then \ - $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ - $(COMPILETOOL) $(GOTOOL) $(GOLD) -linkmode external -extld $(CC) -extldflags "$(CFLAGS) $(OSXOLDGOLINKFLAGS)" -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ + $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I gopath/src/$* $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ + $(COMPILETOOL) $(GOTOOL) $(GOLD) -L gopath/src/$* -linkmode external -extld $(CC) -extldflags "$(CFLAGS) $(OSXOLDGOLINKFLAGS)" -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ else \ $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ $(COMPILETOOL) $(GOTOOL) $(GOLD) -L . -r $${GOROOT:-`go env GOROOT`}/pkg/$${GOOS:-`go env GOOS`}_$${GOARCH:-`go env GOARCH`}:. -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ @@ -136,11 +152,11 @@ run_testcase = \ run_testcase_cpp = \ if test -f $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX); then \ if $(GOGCC) ; then \ - $(COMPILETOOL) $(GCCGO) -c -g -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ - $(COMPILETOOL) $(GCCGO) -o $*_runme $(SCRIPTPREFIX)$*_runme.@OBJEXT@ $*.a -lstdc++; \ + $(COMPILETOOL) $(GCCGO) -c -g -I gopath/src/$* $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ + $(COMPILETOOL) $(GCCGO) -o $*_runme $(SCRIPTPREFIX)$*_runme.@OBJEXT@ gopath/src/$*/$*.a -lstdc++; \ elif $(GO12) || $(GO13) || $(GO15); then \ - $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ - $(COMPILETOOL) $(GOTOOL) $(GOLD) -linkmode external -extld $(CXX) -extldflags "$(CXXFLAGS) $(OSXOLDGOLINKFLAGS)" -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ + $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I gopath/src/$* $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ + $(COMPILETOOL) $(GOTOOL) $(GOLD) -L gopath/src/$* -linkmode external -extld $(CXX) -extldflags "$(CXXFLAGS) $(OSXOLDGOLINKFLAGS)" -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ else \ $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ $(COMPILETOOL) $(GOTOOL) $(GOLD) -L . -r $${GOROOT:-`go env GOROOT`}/pkg/$${GOOS:-`go env GOOS`}_$${GOARCH:-`go env GOARCH`}:. -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ @@ -150,18 +166,24 @@ run_testcase_cpp = \ run_multi_testcase = \ if test -f $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX); then \ - if $(GOGCC) ; then \ - $(COMPILETOOL) $(GCCGO) -c -g -I . -I gopath/src $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ + if $(GO15) || $(GOGCC); then \ files=`cat $(top_srcdir)/$(EXAMPLES)/$(TEST_SUITE)/$*.list`; \ - $(COMPILETOOL) $(GCCGO) -o $*_runme $(SCRIPTPREFIX)$*_runme.@OBJEXT@ `for f in $$files; do echo $$f.a; done` -lstdc++; \ - elif $(GO12) || $(GO13) || $(GO15); then \ - $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ - $(COMPILETOOL) $(GOTOOL) $(GOLD) -L . -linkmode external -extld $(CXX) -extldflags "$(CXXFLAGS) $(OSXOLDGOLINKFLAGS)" -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ - else \ - $(COMPILETOOL) $(GO) $(GOCOMPILEARG) -I . $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) && \ - $(COMPILETOOL) $(GOTOOL) $(GOLD) -L . -r $${GOROOT:-`go env GOROOT`}/pkg/$${GOOS:-`go env GOOS`}_$${GOARCH:-`go env GOARCH`}:. -o $*_runme $(SCRIPTPREFIX)$*_runme.$(GOOBJEXT); \ - fi && \ - env LD_LIBRARY_PATH=.:$$LD_LIBRARY_PATH $(RUNTOOL) ./$*_runme; \ + mkdir gopath/$*/src/$* 2>/dev/null || true; \ + cp $(SCRIPTDIR)/$(SCRIPTPREFIX)$*$(SCRIPTSUFFIX) gopath/$*/src/$*; \ + GOPATH="`pwd`/gopath/$*"; \ + export GOPATH; \ + CGO_CPPFLAGS="$(CPPFLAGS) $(INCLUDES) `for f in $$files; do echo -I ../$$f; done`"; \ + export CGO_CPPFLAGS; \ + CGO_CFLAGS="$(CFLAGS)"; \ + export CGO_CFLAGS; \ + CGO_CXXFLAGS="$(CXXFLAGS)"; \ + export CGO_CXXFLAGS; \ + CGO_LDFLAGS="$(LDFLAGS) -lm"; \ + export CGO_LDFLAGS; \ + (cd gopath/$*/src/$* && \ + $(GO) build `if $(GOGCC); then echo -compiler=gccgo; fi` -o ../../../../$*_runme) && \ + env LD_LIBRARY_PATH=.:$$LD_LIBRARY_PATH $(RUNTOOL) ./$*_runme; \ + fi; \ fi %.clean: diff --git a/Examples/test-suite/go/abstract_access_runme.go b/Examples/test-suite/go/abstract_access_runme.go index a2cfeda92..5102236f9 100644 --- a/Examples/test-suite/go/abstract_access_runme.go +++ b/Examples/test-suite/go/abstract_access_runme.go @@ -1,6 +1,6 @@ package main -import "./abstract_access" +import "abstract_access" func main() { d := abstract_access.NewD() diff --git a/Examples/test-suite/go/abstract_typedef2_runme.go b/Examples/test-suite/go/abstract_typedef2_runme.go index ef760e45d..76a5fc8de 100644 --- a/Examples/test-suite/go/abstract_typedef2_runme.go +++ b/Examples/test-suite/go/abstract_typedef2_runme.go @@ -1,6 +1,6 @@ package main -import "./abstract_typedef2" +import "abstract_typedef2" func main() { abstract_typedef2.NewA_UF() diff --git a/Examples/test-suite/go/abstract_typedef_runme.go b/Examples/test-suite/go/abstract_typedef_runme.go index 99ff94ded..56aaa613f 100644 --- a/Examples/test-suite/go/abstract_typedef_runme.go +++ b/Examples/test-suite/go/abstract_typedef_runme.go @@ -1,6 +1,6 @@ package main -import "./abstract_typedef" +import "abstract_typedef" func main() { e := abstract_typedef.NewEngine() diff --git a/Examples/test-suite/go/abstract_virtual_runme.go b/Examples/test-suite/go/abstract_virtual_runme.go index b87cf9b5c..e19eac27d 100644 --- a/Examples/test-suite/go/abstract_virtual_runme.go +++ b/Examples/test-suite/go/abstract_virtual_runme.go @@ -1,6 +1,6 @@ package main -import "./abstract_virtual" +import "abstract_virtual" func main() { abstract_virtual.NewD() diff --git a/Examples/test-suite/go/argout_runme.go b/Examples/test-suite/go/argout_runme.go index 5f7017e73..bb8ab9ed2 100644 --- a/Examples/test-suite/go/argout_runme.go +++ b/Examples/test-suite/go/argout_runme.go @@ -1,6 +1,6 @@ package main -import wrap "./argout" +import wrap "argout" func main() { ip := wrap.New_intp() diff --git a/Examples/test-suite/go/array_member_runme.go b/Examples/test-suite/go/array_member_runme.go index d8a8fac2b..4f029db98 100644 --- a/Examples/test-suite/go/array_member_runme.go +++ b/Examples/test-suite/go/array_member_runme.go @@ -1,6 +1,6 @@ package main -import . "./array_member" +import . "array_member" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/arrays_global_runme.go b/Examples/test-suite/go/arrays_global_runme.go index 0ff40090c..35b049d9a 100644 --- a/Examples/test-suite/go/arrays_global_runme.go +++ b/Examples/test-suite/go/arrays_global_runme.go @@ -1,6 +1,6 @@ package main -import . "./arrays_global" +import . "arrays_global" func main() { SetArray_i(GetArray_const_i()) diff --git a/Examples/test-suite/go/char_binary_runme.go b/Examples/test-suite/go/char_binary_runme.go index 50f2e121d..d47d616af 100644 --- a/Examples/test-suite/go/char_binary_runme.go +++ b/Examples/test-suite/go/char_binary_runme.go @@ -1,6 +1,6 @@ package main -import . "./char_binary" +import . "char_binary" func main() { t := NewTest() diff --git a/Examples/test-suite/go/class_ignore_runme.go b/Examples/test-suite/go/class_ignore_runme.go index 82e52eff5..24261c637 100644 --- a/Examples/test-suite/go/class_ignore_runme.go +++ b/Examples/test-suite/go/class_ignore_runme.go @@ -1,6 +1,6 @@ package main -import "./class_ignore" +import "class_ignore" func main() { a := class_ignore.NewBar() diff --git a/Examples/test-suite/go/class_scope_weird_runme.go b/Examples/test-suite/go/class_scope_weird_runme.go index 332586f31..a42bdad21 100644 --- a/Examples/test-suite/go/class_scope_weird_runme.go +++ b/Examples/test-suite/go/class_scope_weird_runme.go @@ -1,6 +1,6 @@ package main -import "./class_scope_weird" +import "class_scope_weird" func main() { f := class_scope_weird.NewFoo() diff --git a/Examples/test-suite/go/compactdefaultargs_runme.go b/Examples/test-suite/go/compactdefaultargs_runme.go index 46f3ff3f9..fe6224ca2 100644 --- a/Examples/test-suite/go/compactdefaultargs_runme.go +++ b/Examples/test-suite/go/compactdefaultargs_runme.go @@ -1,6 +1,6 @@ package main -import . "./compactdefaultargs" +import . "compactdefaultargs" func main() { defaults1 := NewDefaults1(1000) diff --git a/Examples/test-suite/go/constover_runme.go b/Examples/test-suite/go/constover_runme.go index f961e01b5..6c837095a 100644 --- a/Examples/test-suite/go/constover_runme.go +++ b/Examples/test-suite/go/constover_runme.go @@ -1,9 +1,10 @@ package main import ( - "./constover" "fmt" "os" + + "constover" ) func main() { diff --git a/Examples/test-suite/go/constructor_copy_runme.go b/Examples/test-suite/go/constructor_copy_runme.go index d9b77a9db..68c428853 100644 --- a/Examples/test-suite/go/constructor_copy_runme.go +++ b/Examples/test-suite/go/constructor_copy_runme.go @@ -1,6 +1,6 @@ package main -import . "./constructor_copy" +import . "constructor_copy" func main() { f1 := NewFoo1(3) diff --git a/Examples/test-suite/go/contract_runme.go b/Examples/test-suite/go/contract_runme.go index b20a1a64f..b028855c3 100644 --- a/Examples/test-suite/go/contract_runme.go +++ b/Examples/test-suite/go/contract_runme.go @@ -1,6 +1,6 @@ package main -import "./contract" +import "contract" func main() { contract.Test_preassert(1, 2) diff --git a/Examples/test-suite/go/cpp11_strongly_typed_enumerations_runme.go b/Examples/test-suite/go/cpp11_strongly_typed_enumerations_runme.go index f4b84b1ee..f9ca74a1e 100644 --- a/Examples/test-suite/go/cpp11_strongly_typed_enumerations_runme.go +++ b/Examples/test-suite/go/cpp11_strongly_typed_enumerations_runme.go @@ -1,7 +1,7 @@ package main import "fmt" -import . "./cpp11_strongly_typed_enumerations" +import . "cpp11_strongly_typed_enumerations" func enumCheck(actual int, expected int) int { if actual != expected { diff --git a/Examples/test-suite/go/cpp_enum_runme.go b/Examples/test-suite/go/cpp_enum_runme.go index 7d7db953d..8906dd4f1 100644 --- a/Examples/test-suite/go/cpp_enum_runme.go +++ b/Examples/test-suite/go/cpp_enum_runme.go @@ -1,6 +1,6 @@ package main -import "./cpp_enum" +import "cpp_enum" func main() { f := cpp_enum.NewFoo() diff --git a/Examples/test-suite/go/cpp_namespace_runme.go b/Examples/test-suite/go/cpp_namespace_runme.go index 8482b043f..aecdd9543 100644 --- a/Examples/test-suite/go/cpp_namespace_runme.go +++ b/Examples/test-suite/go/cpp_namespace_runme.go @@ -1,7 +1,7 @@ // Note: This example assumes that namespaces are flattened package main -import "./cpp_namespace" +import "cpp_namespace" func main() { n := cpp_namespace.Fact(4) diff --git a/Examples/test-suite/go/cpp_static_runme.go b/Examples/test-suite/go/cpp_static_runme.go index ead433466..1ad981a60 100644 --- a/Examples/test-suite/go/cpp_static_runme.go +++ b/Examples/test-suite/go/cpp_static_runme.go @@ -1,6 +1,6 @@ package main -import . "./cpp_static" +import . "cpp_static" func main() { StaticFunctionTestStatic_func() diff --git a/Examples/test-suite/go/default_args_runme.go b/Examples/test-suite/go/default_args_runme.go index 38243ac44..a39f95716 100644 --- a/Examples/test-suite/go/default_args_runme.go +++ b/Examples/test-suite/go/default_args_runme.go @@ -1,6 +1,6 @@ package main -import "./default_args" +import "default_args" func main() { if default_args.StaticsStaticmethod() != 60 { diff --git a/Examples/test-suite/go/default_constructor_runme.go b/Examples/test-suite/go/default_constructor_runme.go index 40a5a6e49..eeac7eaf8 100644 --- a/Examples/test-suite/go/default_constructor_runme.go +++ b/Examples/test-suite/go/default_constructor_runme.go @@ -1,6 +1,6 @@ package main -import dc "./default_constructor" +import dc "default_constructor" func main() { a := dc.NewA() diff --git a/Examples/test-suite/go/director_alternating_runme.go b/Examples/test-suite/go/director_alternating_runme.go index 10f6774a3..b4793aa8f 100644 --- a/Examples/test-suite/go/director_alternating_runme.go +++ b/Examples/test-suite/go/director_alternating_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_alternating" +import . "director_alternating" func main() { id := GetBar().Id() diff --git a/Examples/test-suite/go/director_basic_runme.go b/Examples/test-suite/go/director_basic_runme.go index 0ce780bbd..360424d9b 100644 --- a/Examples/test-suite/go/director_basic_runme.go +++ b/Examples/test-suite/go/director_basic_runme.go @@ -1,6 +1,6 @@ package main -import "./director_basic" +import "director_basic" type GoFoo struct{} diff --git a/Examples/test-suite/go/director_classic_runme.go b/Examples/test-suite/go/director_classic_runme.go index 45e89eac5..230c9638d 100644 --- a/Examples/test-suite/go/director_classic_runme.go +++ b/Examples/test-suite/go/director_classic_runme.go @@ -1,7 +1,7 @@ package main import "fmt" -import . "./director_classic" +import . "director_classic" type TargetLangPerson struct{} // From Person func (p *TargetLangPerson) Id() string { diff --git a/Examples/test-suite/go/director_default_runme.go b/Examples/test-suite/go/director_default_runme.go index 2f963b239..ac2aace1d 100644 --- a/Examples/test-suite/go/director_default_runme.go +++ b/Examples/test-suite/go/director_default_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_default" +import . "director_default" func main() { NewFoo() diff --git a/Examples/test-suite/go/director_detect_runme.go b/Examples/test-suite/go/director_detect_runme.go index 9f1ad94a9..0c3c95fdc 100644 --- a/Examples/test-suite/go/director_detect_runme.go +++ b/Examples/test-suite/go/director_detect_runme.go @@ -1,6 +1,6 @@ package main -import "./director_detect" +import "director_detect" type MyBar struct { val int diff --git a/Examples/test-suite/go/director_enum_runme.go b/Examples/test-suite/go/director_enum_runme.go index 5653fda40..002d425d2 100644 --- a/Examples/test-suite/go/director_enum_runme.go +++ b/Examples/test-suite/go/director_enum_runme.go @@ -1,6 +1,6 @@ package main -import "./director_enum" +import "director_enum" type MyFoo struct{} // From director_enum.Foo func (p *MyFoo) Say_hi(val director_enum.EnumDirectorHello) director_enum.EnumDirectorHello { diff --git a/Examples/test-suite/go/director_exception_runme.go b/Examples/test-suite/go/director_exception_runme.go index 29df3e40b..55231ff16 100644 --- a/Examples/test-suite/go/director_exception_runme.go +++ b/Examples/test-suite/go/director_exception_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_exception" +import . "director_exception" type Exception struct { msg string diff --git a/Examples/test-suite/go/director_extend_runme.go b/Examples/test-suite/go/director_extend_runme.go index 70e2ab41b..27e55b997 100644 --- a/Examples/test-suite/go/director_extend_runme.go +++ b/Examples/test-suite/go/director_extend_runme.go @@ -5,7 +5,7 @@ package main -import . "./director_extend" +import . "director_extend" func main() { m := NewSpObject() diff --git a/Examples/test-suite/go/director_finalizer_runme.go b/Examples/test-suite/go/director_finalizer_runme.go index 96fcf860e..d36a4ba33 100644 --- a/Examples/test-suite/go/director_finalizer_runme.go +++ b/Examples/test-suite/go/director_finalizer_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_finalizer" +import . "director_finalizer" type MyFoo struct{} // From Foo func DeleteMyFoo(p Foo) { diff --git a/Examples/test-suite/go/director_frob_runme.go b/Examples/test-suite/go/director_frob_runme.go index a6afedf69..3985eb14b 100644 --- a/Examples/test-suite/go/director_frob_runme.go +++ b/Examples/test-suite/go/director_frob_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_frob" +import . "director_frob" func main() { foo := NewBravo() diff --git a/Examples/test-suite/go/director_nested_runme.go b/Examples/test-suite/go/director_nested_runme.go index 2d3bc77e1..a1193ad59 100644 --- a/Examples/test-suite/go/director_nested_runme.go +++ b/Examples/test-suite/go/director_nested_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_nested" +import . "director_nested" type A struct{} // From FooBar_int func (p *A) Do_step() string { diff --git a/Examples/test-suite/go/director_profile_runme.go b/Examples/test-suite/go/director_profile_runme.go index 87edcbe26..a9bc7934b 100644 --- a/Examples/test-suite/go/director_profile_runme.go +++ b/Examples/test-suite/go/director_profile_runme.go @@ -1,7 +1,7 @@ package main import "fmt" -import "./director_profile" +import "director_profile" type MyB struct{} // From director_profile.B func (p *MyB) Vfi(a int) int { diff --git a/Examples/test-suite/go/director_protected_runme.go b/Examples/test-suite/go/director_protected_runme.go index 24adfe7bd..bfd50c6b2 100644 --- a/Examples/test-suite/go/director_protected_runme.go +++ b/Examples/test-suite/go/director_protected_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_protected" +import . "director_protected" type FooBar struct{} // From Bar func (p *FooBar) Ping() string { diff --git a/Examples/test-suite/go/director_string_runme.go b/Examples/test-suite/go/director_string_runme.go index c5201ab96..f4f9cc150 100644 --- a/Examples/test-suite/go/director_string_runme.go +++ b/Examples/test-suite/go/director_string_runme.go @@ -1,6 +1,6 @@ package main -import . "./director_string" +import . "director_string" type B struct { // From A abi A diff --git a/Examples/test-suite/go/director_unroll_runme.go b/Examples/test-suite/go/director_unroll_runme.go index 6d2894a72..6a919f656 100644 --- a/Examples/test-suite/go/director_unroll_runme.go +++ b/Examples/test-suite/go/director_unroll_runme.go @@ -1,6 +1,6 @@ package main -import "./director_unroll" +import "director_unroll" type MyFoo struct{} // From director_unroll.Foo func (p *MyFoo) Ping() string { diff --git a/Examples/test-suite/go/disown_runme.go b/Examples/test-suite/go/disown_runme.go index 3e853de59..4484515fd 100644 --- a/Examples/test-suite/go/disown_runme.go +++ b/Examples/test-suite/go/disown_runme.go @@ -1,6 +1,6 @@ package main -import . "./disown" +import . "disown" func main() { a := NewA() diff --git a/Examples/test-suite/go/dynamic_cast_runme.go b/Examples/test-suite/go/dynamic_cast_runme.go index 476734805..46ba23698 100644 --- a/Examples/test-suite/go/dynamic_cast_runme.go +++ b/Examples/test-suite/go/dynamic_cast_runme.go @@ -1,6 +1,6 @@ package main -import "./dynamic_cast" +import "dynamic_cast" func main() { f := dynamic_cast.NewFoo() diff --git a/Examples/test-suite/go/empty_c_runme.go b/Examples/test-suite/go/empty_c_runme.go index 831a56118..1a1bd9cc5 100644 --- a/Examples/test-suite/go/empty_c_runme.go +++ b/Examples/test-suite/go/empty_c_runme.go @@ -1,6 +1,6 @@ package main -import _ "./empty_c" +import _ "empty_c" func main() { } diff --git a/Examples/test-suite/go/empty_runme.go b/Examples/test-suite/go/empty_runme.go index f74285cb0..681a6f3ad 100644 --- a/Examples/test-suite/go/empty_runme.go +++ b/Examples/test-suite/go/empty_runme.go @@ -1,6 +1,6 @@ package main -import _ "./empty" +import _ "empty" func main() { } diff --git a/Examples/test-suite/go/enum_template_runme.go b/Examples/test-suite/go/enum_template_runme.go index 269fe7d5b..c60a452d7 100644 --- a/Examples/test-suite/go/enum_template_runme.go +++ b/Examples/test-suite/go/enum_template_runme.go @@ -1,6 +1,6 @@ package main -import "./enum_template" +import "enum_template" func main() { if enum_template.MakeETest() != 1 { diff --git a/Examples/test-suite/go/enums_runme.go b/Examples/test-suite/go/enums_runme.go index ab193f74b..7a528b3e2 100644 --- a/Examples/test-suite/go/enums_runme.go +++ b/Examples/test-suite/go/enums_runme.go @@ -1,6 +1,6 @@ package main -import "./enums" +import "enums" func main() { enums.Bar2(1) diff --git a/Examples/test-suite/go/exception_order_runme.go b/Examples/test-suite/go/exception_order_runme.go index 626a826f8..21dcff312 100644 --- a/Examples/test-suite/go/exception_order_runme.go +++ b/Examples/test-suite/go/exception_order_runme.go @@ -1,7 +1,7 @@ package main import "strings" -import . "./exception_order" +import . "exception_order" func main() { a := NewA() diff --git a/Examples/test-suite/go/extend_placement_runme.go b/Examples/test-suite/go/extend_placement_runme.go index efa776e31..253ec6618 100644 --- a/Examples/test-suite/go/extend_placement_runme.go +++ b/Examples/test-suite/go/extend_placement_runme.go @@ -1,6 +1,6 @@ package main -import "./extend_placement" +import "extend_placement" func main() { foo := extend_placement.NewFoo() diff --git a/Examples/test-suite/go/extend_template_ns_runme.go b/Examples/test-suite/go/extend_template_ns_runme.go index 164a31b26..d005172a4 100644 --- a/Examples/test-suite/go/extend_template_ns_runme.go +++ b/Examples/test-suite/go/extend_template_ns_runme.go @@ -1,6 +1,6 @@ package main -import . "./extend_template_ns" +import . "extend_template_ns" func main() { f := NewFoo_One() diff --git a/Examples/test-suite/go/extend_template_runme.go b/Examples/test-suite/go/extend_template_runme.go index 5adb4b3c2..a5c4da4e1 100644 --- a/Examples/test-suite/go/extend_template_runme.go +++ b/Examples/test-suite/go/extend_template_runme.go @@ -1,6 +1,6 @@ package main -import "./extend_template" +import "extend_template" func main() { f := extend_template.NewFoo_0() diff --git a/Examples/test-suite/go/extend_variable_runme.go b/Examples/test-suite/go/extend_variable_runme.go index c6428c467..9425aee4d 100644 --- a/Examples/test-suite/go/extend_variable_runme.go +++ b/Examples/test-suite/go/extend_variable_runme.go @@ -1,6 +1,6 @@ package main -import . "./extend_variable" +import . "extend_variable" func main() { if FooBar != 42 { diff --git a/Examples/test-suite/go/extern_c_runme.go b/Examples/test-suite/go/extern_c_runme.go index 0fb5b21cc..9bc2cd0cc 100644 --- a/Examples/test-suite/go/extern_c_runme.go +++ b/Examples/test-suite/go/extern_c_runme.go @@ -1,6 +1,6 @@ package main -import "./extern_c" +import "extern_c" func main() { extern_c.RealFunction(2) diff --git a/Examples/test-suite/go/friends_runme.go b/Examples/test-suite/go/friends_runme.go index 9f223fcac..2e34a4db0 100644 --- a/Examples/test-suite/go/friends_runme.go +++ b/Examples/test-suite/go/friends_runme.go @@ -1,6 +1,6 @@ package main -import "./friends" +import "friends" func main() { a := friends.NewA(2) diff --git a/Examples/test-suite/go/fvirtual_runme.go b/Examples/test-suite/go/fvirtual_runme.go index 8810d5cbb..86ef90f18 100644 --- a/Examples/test-suite/go/fvirtual_runme.go +++ b/Examples/test-suite/go/fvirtual_runme.go @@ -1,6 +1,6 @@ package main -import . "./fvirtual" +import . "fvirtual" func main() { sw := NewNodeSwitch() diff --git a/Examples/test-suite/go/global_ns_arg_runme.go b/Examples/test-suite/go/global_ns_arg_runme.go index ece779c9c..e86aa6747 100644 --- a/Examples/test-suite/go/global_ns_arg_runme.go +++ b/Examples/test-suite/go/global_ns_arg_runme.go @@ -1,6 +1,6 @@ package main -import . "./global_ns_arg" +import . "global_ns_arg" func main() { Foo(1) diff --git a/Examples/test-suite/go/go_director_inout_runme.go b/Examples/test-suite/go/go_director_inout_runme.go index 9b9df318e..e6768a465 100644 --- a/Examples/test-suite/go/go_director_inout_runme.go +++ b/Examples/test-suite/go/go_director_inout_runme.go @@ -1,7 +1,7 @@ package main import ( - wrap "./go_director_inout" + wrap "go_director_inout" ) type GoMyClass struct {} diff --git a/Examples/test-suite/go/go_inout_runme.go b/Examples/test-suite/go/go_inout_runme.go index 9aa0cd0c5..4599aa104 100644 --- a/Examples/test-suite/go/go_inout_runme.go +++ b/Examples/test-suite/go/go_inout_runme.go @@ -5,7 +5,7 @@ import ( "fmt" "reflect" - "./go_inout" + "go_inout" ) type S struct { diff --git a/Examples/test-suite/go/go_subdir_import_runme.go b/Examples/test-suite/go/go_subdir_import_runme.go index f90a6eb54..a040c993f 100644 --- a/Examples/test-suite/go/go_subdir_import_runme.go +++ b/Examples/test-suite/go/go_subdir_import_runme.go @@ -1,9 +1,9 @@ package main import ( - "go_subdir_import_a" - "testdir/go_subdir_import/go_subdir_import_b" - "testdir/go_subdir_import/go_subdir_import_c" + "swigtests/go_subdir_import_a" + "swigtests/testdir/go_subdir_import/go_subdir_import_b" + "swigtests/testdir/go_subdir_import/go_subdir_import_c" ) func main() { diff --git a/Examples/test-suite/go/grouping_runme.go b/Examples/test-suite/go/grouping_runme.go index c63d6fb12..f808e1286 100644 --- a/Examples/test-suite/go/grouping_runme.go +++ b/Examples/test-suite/go/grouping_runme.go @@ -1,6 +1,6 @@ package main -import "./grouping" +import "grouping" func main() { x := grouping.Test1(42) diff --git a/Examples/test-suite/go/import_nomodule_runme.go b/Examples/test-suite/go/import_nomodule_runme.go index a6bbd7de5..48592df25 100644 --- a/Examples/test-suite/go/import_nomodule_runme.go +++ b/Examples/test-suite/go/import_nomodule_runme.go @@ -1,6 +1,6 @@ package main -import . "./import_nomodule" +import . "import_nomodule" func main() { f := Create_Foo() diff --git a/Examples/test-suite/go/imports_runme.go b/Examples/test-suite/go/imports_runme.go index 896036cbf..a67ae407b 100644 --- a/Examples/test-suite/go/imports_runme.go +++ b/Examples/test-suite/go/imports_runme.go @@ -2,8 +2,8 @@ package main -import "imports_b" -import "imports_a" +import "swigtests/imports_b" +import "swigtests/imports_a" func main() { x := imports_b.NewB() diff --git a/Examples/test-suite/go/inctest_runme.go b/Examples/test-suite/go/inctest_runme.go index f8a2c116c..3148abcd2 100644 --- a/Examples/test-suite/go/inctest_runme.go +++ b/Examples/test-suite/go/inctest_runme.go @@ -1,6 +1,6 @@ package main -import "./inctest" +import "inctest" func main() { inctest.NewA() diff --git a/Examples/test-suite/go/inherit_member_runme.go b/Examples/test-suite/go/inherit_member_runme.go index 599a0eb56..6fd70cf80 100644 --- a/Examples/test-suite/go/inherit_member_runme.go +++ b/Examples/test-suite/go/inherit_member_runme.go @@ -1,6 +1,6 @@ package main -import wrap "./inherit_member" +import wrap "inherit_member" func main() { s := wrap.NewChild() diff --git a/Examples/test-suite/go/inherit_missing_runme.go b/Examples/test-suite/go/inherit_missing_runme.go index ba9a2a516..c70c48306 100644 --- a/Examples/test-suite/go/inherit_missing_runme.go +++ b/Examples/test-suite/go/inherit_missing_runme.go @@ -1,6 +1,6 @@ package main -import "./inherit_missing" +import "inherit_missing" func main() { a := inherit_missing.New_Foo() diff --git a/Examples/test-suite/go/input_runme.go b/Examples/test-suite/go/input_runme.go index 207bdaa28..ddc2992fe 100644 --- a/Examples/test-suite/go/input_runme.go +++ b/Examples/test-suite/go/input_runme.go @@ -1,6 +1,6 @@ package main -import . "./input" +import . "input" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/keyword_rename_c_runme.go b/Examples/test-suite/go/keyword_rename_c_runme.go index 425e38a26..26f2ea42b 100644 --- a/Examples/test-suite/go/keyword_rename_c_runme.go +++ b/Examples/test-suite/go/keyword_rename_c_runme.go @@ -1,6 +1,6 @@ package main -import "./keyword_rename_c" +import "keyword_rename_c" func main() { keyword_rename_c.Xgo(1) diff --git a/Examples/test-suite/go/keyword_rename_runme.go b/Examples/test-suite/go/keyword_rename_runme.go index e36bc5968..7a40ff83d 100644 --- a/Examples/test-suite/go/keyword_rename_runme.go +++ b/Examples/test-suite/go/keyword_rename_runme.go @@ -1,6 +1,6 @@ package main -import "./keyword_rename" +import "keyword_rename" func main() { keyword_rename.Xgo(1) diff --git a/Examples/test-suite/go/li_attribute_runme.go b/Examples/test-suite/go/li_attribute_runme.go index 5d2c3d0c3..b502b8cea 100644 --- a/Examples/test-suite/go/li_attribute_runme.go +++ b/Examples/test-suite/go/li_attribute_runme.go @@ -1,6 +1,6 @@ package main -import "./li_attribute" +import "li_attribute" func main() { aa := li_attribute.NewA(1, 2, 3) diff --git a/Examples/test-suite/go/li_carrays_cpp_runme.go b/Examples/test-suite/go/li_carrays_cpp_runme.go index 7ee0a4103..cfc171284 100644 --- a/Examples/test-suite/go/li_carrays_cpp_runme.go +++ b/Examples/test-suite/go/li_carrays_cpp_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_carrays_cpp" +import . "li_carrays_cpp" func main() { d := NewDoubleArray(10) diff --git a/Examples/test-suite/go/li_carrays_runme.go b/Examples/test-suite/go/li_carrays_runme.go index 0cbe92cd8..9128bbfd1 100644 --- a/Examples/test-suite/go/li_carrays_runme.go +++ b/Examples/test-suite/go/li_carrays_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_carrays" +import . "li_carrays" func main() { d := NewDoubleArray(10) diff --git a/Examples/test-suite/go/li_cdata_cpp_runme.go b/Examples/test-suite/go/li_cdata_cpp_runme.go index 42a0ebd08..daa5384f7 100644 --- a/Examples/test-suite/go/li_cdata_cpp_runme.go +++ b/Examples/test-suite/go/li_cdata_cpp_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_cdata_cpp" +import . "li_cdata_cpp" func main() { s := "ABC abc" diff --git a/Examples/test-suite/go/li_cdata_runme.go b/Examples/test-suite/go/li_cdata_runme.go index f71a3a2c3..9458dab43 100644 --- a/Examples/test-suite/go/li_cdata_runme.go +++ b/Examples/test-suite/go/li_cdata_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_cdata" +import . "li_cdata" func main() { s := "ABC abc" diff --git a/Examples/test-suite/go/li_cmalloc_runme.go b/Examples/test-suite/go/li_cmalloc_runme.go index 45f47b45f..5b9f9704a 100644 --- a/Examples/test-suite/go/li_cmalloc_runme.go +++ b/Examples/test-suite/go/li_cmalloc_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_cmalloc" +import . "li_cmalloc" func main() { p := Malloc_int() diff --git a/Examples/test-suite/go/li_cpointer_cpp_runme.go b/Examples/test-suite/go/li_cpointer_cpp_runme.go index e2f5a59d1..0de57c624 100644 --- a/Examples/test-suite/go/li_cpointer_cpp_runme.go +++ b/Examples/test-suite/go/li_cpointer_cpp_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_cpointer_cpp" +import . "li_cpointer_cpp" func main() { p := New_intp() diff --git a/Examples/test-suite/go/li_cpointer_runme.go b/Examples/test-suite/go/li_cpointer_runme.go index 57493b122..0fe29e77d 100644 --- a/Examples/test-suite/go/li_cpointer_runme.go +++ b/Examples/test-suite/go/li_cpointer_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_cpointer" +import . "li_cpointer" func main() { p := New_intp() diff --git a/Examples/test-suite/go/li_std_map_runme.go b/Examples/test-suite/go/li_std_map_runme.go index 66e74dd60..5c5cc2e4c 100644 --- a/Examples/test-suite/go/li_std_map_runme.go +++ b/Examples/test-suite/go/li_std_map_runme.go @@ -1,6 +1,6 @@ package main -import "./li_std_map" +import "li_std_map" func main() { a1 := li_std_map.NewA(3) diff --git a/Examples/test-suite/go/li_std_vector_ptr_runme.go b/Examples/test-suite/go/li_std_vector_ptr_runme.go index a9f7fe91c..d66ff19c6 100644 --- a/Examples/test-suite/go/li_std_vector_ptr_runme.go +++ b/Examples/test-suite/go/li_std_vector_ptr_runme.go @@ -1,6 +1,6 @@ package main -import . "./li_std_vector_ptr" +import . "li_std_vector_ptr" import "fmt" func check(val1 int, val2 int) { diff --git a/Examples/test-suite/go/member_pointer_runme.go b/Examples/test-suite/go/member_pointer_runme.go index 9a55bc4b9..731526b75 100644 --- a/Examples/test-suite/go/member_pointer_runme.go +++ b/Examples/test-suite/go/member_pointer_runme.go @@ -3,7 +3,7 @@ package main import "fmt" -import . "./member_pointer" +import . "member_pointer" func check(what string, expected float64, actual float64) { if expected != actual { diff --git a/Examples/test-suite/go/memberin_extend_c_runme.go b/Examples/test-suite/go/memberin_extend_c_runme.go index ec8b11e60..0551acc90 100644 --- a/Examples/test-suite/go/memberin_extend_c_runme.go +++ b/Examples/test-suite/go/memberin_extend_c_runme.go @@ -1,6 +1,6 @@ package main -import "./memberin_extend_c" +import "memberin_extend_c" func main() { t := memberin_extend_c.NewPerson() diff --git a/Examples/test-suite/go/minherit_runme.go b/Examples/test-suite/go/minherit_runme.go index c69fe92c1..9b7873cb0 100644 --- a/Examples/test-suite/go/minherit_runme.go +++ b/Examples/test-suite/go/minherit_runme.go @@ -1,7 +1,7 @@ package main import "fmt" -import "./minherit" +import "minherit" func main() { a := minherit.NewFoo() diff --git a/Examples/test-suite/go/mod_runme.go b/Examples/test-suite/go/mod_runme.go index 581c83918..8d894db8d 100644 --- a/Examples/test-suite/go/mod_runme.go +++ b/Examples/test-suite/go/mod_runme.go @@ -1,7 +1,7 @@ package main -import "mod_a" -import "mod_b" +import "swigtests/mod_a" +import "swigtests/mod_b" func main() { c := mod_b.NewC() diff --git a/Examples/test-suite/go/multi_import_runme.go b/Examples/test-suite/go/multi_import_runme.go index 973af1e7b..f30913c6d 100644 --- a/Examples/test-suite/go/multi_import_runme.go +++ b/Examples/test-suite/go/multi_import_runme.go @@ -1,7 +1,7 @@ package main -import "multi_import_a" -import "multi_import_b" +import "swigtests/multi_import_a" +import "swigtests/multi_import_b" func main() { x := multi_import_b.NewXXX() diff --git a/Examples/test-suite/go/namespace_class_runme.go b/Examples/test-suite/go/namespace_class_runme.go index 2ed5567f7..4c240b6a4 100644 --- a/Examples/test-suite/go/namespace_class_runme.go +++ b/Examples/test-suite/go/namespace_class_runme.go @@ -1,6 +1,6 @@ package main -import . "./namespace_class" +import . "namespace_class" func main() { EulerT3DToFrame(1, 1, 1) diff --git a/Examples/test-suite/go/namespace_typemap_runme.go b/Examples/test-suite/go/namespace_typemap_runme.go index 056da1567..47e2b64f1 100644 --- a/Examples/test-suite/go/namespace_typemap_runme.go +++ b/Examples/test-suite/go/namespace_typemap_runme.go @@ -1,6 +1,6 @@ package main -import . "./namespace_typemap" +import . "namespace_typemap" func main() { if Stest1("hello") != "hello" { diff --git a/Examples/test-suite/go/namespace_virtual_method_runme.go b/Examples/test-suite/go/namespace_virtual_method_runme.go index 3f8e774c6..a8cb38bad 100644 --- a/Examples/test-suite/go/namespace_virtual_method_runme.go +++ b/Examples/test-suite/go/namespace_virtual_method_runme.go @@ -1,6 +1,6 @@ package main -import "./namespace_virtual_method" +import "namespace_virtual_method" func main() { _ = namespace_virtual_method.NewSpam() diff --git a/Examples/test-suite/go/naturalvar_runme.go b/Examples/test-suite/go/naturalvar_runme.go index e3723e6ab..ed47e9d2d 100644 --- a/Examples/test-suite/go/naturalvar_runme.go +++ b/Examples/test-suite/go/naturalvar_runme.go @@ -1,6 +1,6 @@ package main -import . "./naturalvar" +import . "naturalvar" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/nested_workaround_runme.go b/Examples/test-suite/go/nested_workaround_runme.go index 5737aaaf7..8b31a7f4b 100644 --- a/Examples/test-suite/go/nested_workaround_runme.go +++ b/Examples/test-suite/go/nested_workaround_runme.go @@ -1,6 +1,6 @@ package main -import . "./nested_workaround" +import . "nested_workaround" func main() { inner := NewInner(5) diff --git a/Examples/test-suite/go/overload_complicated_runme.go b/Examples/test-suite/go/overload_complicated_runme.go index e3911c218..ce9d124c8 100644 --- a/Examples/test-suite/go/overload_complicated_runme.go +++ b/Examples/test-suite/go/overload_complicated_runme.go @@ -1,6 +1,6 @@ package main -import . "./overload_complicated" +import . "overload_complicated" func main() { var pInt *int diff --git a/Examples/test-suite/go/overload_copy_runme.go b/Examples/test-suite/go/overload_copy_runme.go index d35ff70b1..55ec4a333 100644 --- a/Examples/test-suite/go/overload_copy_runme.go +++ b/Examples/test-suite/go/overload_copy_runme.go @@ -1,6 +1,6 @@ package main -import . "./overload_copy" +import . "overload_copy" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/overload_extend2_runme.go b/Examples/test-suite/go/overload_extend2_runme.go index 121506734..db790989c 100644 --- a/Examples/test-suite/go/overload_extend2_runme.go +++ b/Examples/test-suite/go/overload_extend2_runme.go @@ -1,6 +1,6 @@ package main -import "./overload_extend2" +import "overload_extend2" func main() { f := overload_extend2.NewFoo() diff --git a/Examples/test-suite/go/overload_extend_c_runme.go b/Examples/test-suite/go/overload_extend_c_runme.go index e00f0b945..4d3b2b6e1 100644 --- a/Examples/test-suite/go/overload_extend_c_runme.go +++ b/Examples/test-suite/go/overload_extend_c_runme.go @@ -1,6 +1,6 @@ package main -import "./overload_extend_c" +import "overload_extend_c" func main() { f := overload_extend_c.NewFoo() diff --git a/Examples/test-suite/go/overload_extend_runme.go b/Examples/test-suite/go/overload_extend_runme.go index 1ba541f13..d73d6cf3c 100644 --- a/Examples/test-suite/go/overload_extend_runme.go +++ b/Examples/test-suite/go/overload_extend_runme.go @@ -1,6 +1,6 @@ package main -import "./overload_extend" +import "overload_extend" func main() { f := overload_extend.NewFoo() diff --git a/Examples/test-suite/go/overload_polymorphic_runme.go b/Examples/test-suite/go/overload_polymorphic_runme.go index 46f837f49..12b9777e6 100644 --- a/Examples/test-suite/go/overload_polymorphic_runme.go +++ b/Examples/test-suite/go/overload_polymorphic_runme.go @@ -1,6 +1,6 @@ package main -import "./overload_polymorphic" +import "overload_polymorphic" func main(){ t := overload_polymorphic.NewDerived() diff --git a/Examples/test-suite/go/overload_rename_runme.go b/Examples/test-suite/go/overload_rename_runme.go index dca5843c3..3bd4a69c5 100644 --- a/Examples/test-suite/go/overload_rename_runme.go +++ b/Examples/test-suite/go/overload_rename_runme.go @@ -1,6 +1,6 @@ package main -import "./overload_rename" +import "overload_rename" func main() { _ = overload_rename.NewFoo(float32(1)) diff --git a/Examples/test-suite/go/overload_simple_runme.go b/Examples/test-suite/go/overload_simple_runme.go index 5f6d0558b..3eb859bac 100644 --- a/Examples/test-suite/go/overload_simple_runme.go +++ b/Examples/test-suite/go/overload_simple_runme.go @@ -1,6 +1,6 @@ package main -import . "./overload_simple" +import . "overload_simple" func main() { if Foo(3) != "foo:int" { diff --git a/Examples/test-suite/go/overload_subtype_runme.go b/Examples/test-suite/go/overload_subtype_runme.go index dc56d1ca7..45d5a025f 100644 --- a/Examples/test-suite/go/overload_subtype_runme.go +++ b/Examples/test-suite/go/overload_subtype_runme.go @@ -1,6 +1,6 @@ package main -import . "./overload_subtype" +import . "overload_subtype" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/overload_template_fast_runme.go b/Examples/test-suite/go/overload_template_fast_runme.go index b80cb7dd4..63809c0ff 100644 --- a/Examples/test-suite/go/overload_template_fast_runme.go +++ b/Examples/test-suite/go/overload_template_fast_runme.go @@ -1,6 +1,6 @@ package main -import . "./overload_template_fast" +import . "overload_template_fast" func main() { _ = Foo() diff --git a/Examples/test-suite/go/overload_template_runme.go b/Examples/test-suite/go/overload_template_runme.go index 53e1def1b..f3a08ecd6 100644 --- a/Examples/test-suite/go/overload_template_runme.go +++ b/Examples/test-suite/go/overload_template_runme.go @@ -1,6 +1,6 @@ package main -import . "./overload_template" +import . "overload_template" func main() { _ = Foo() diff --git a/Examples/test-suite/go/preproc_runme.go b/Examples/test-suite/go/preproc_runme.go index a15062241..3c55aae72 100644 --- a/Examples/test-suite/go/preproc_runme.go +++ b/Examples/test-suite/go/preproc_runme.go @@ -1,6 +1,6 @@ package main -import "./preproc" +import "preproc" func main() { if preproc.GetEndif() != 1 { diff --git a/Examples/test-suite/go/primitive_ref_runme.go b/Examples/test-suite/go/primitive_ref_runme.go index 973806955..a1de2f8a5 100644 --- a/Examples/test-suite/go/primitive_ref_runme.go +++ b/Examples/test-suite/go/primitive_ref_runme.go @@ -1,6 +1,6 @@ package main -import . "./primitive_ref" +import . "primitive_ref" func main() { if Ref_int(3) != 3 { diff --git a/Examples/test-suite/go/profiletest_runme.go b/Examples/test-suite/go/profiletest_runme.go index 30b6cee69..c2b922ba3 100644 --- a/Examples/test-suite/go/profiletest_runme.go +++ b/Examples/test-suite/go/profiletest_runme.go @@ -1,7 +1,7 @@ package main import "fmt" -import "./profiletest" +import "profiletest" func main() { a := profiletest.NewA() diff --git a/Examples/test-suite/go/refcount_runme.go b/Examples/test-suite/go/refcount_runme.go index fdb271cc6..07d407273 100644 --- a/Examples/test-suite/go/refcount_runme.go +++ b/Examples/test-suite/go/refcount_runme.go @@ -1,6 +1,6 @@ package main -import . "./refcount" +import . "refcount" // very innocent example diff --git a/Examples/test-suite/go/reference_global_vars_runme.go b/Examples/test-suite/go/reference_global_vars_runme.go index b8cbb304a..908358f95 100644 --- a/Examples/test-suite/go/reference_global_vars_runme.go +++ b/Examples/test-suite/go/reference_global_vars_runme.go @@ -1,6 +1,6 @@ package main -import . "./reference_global_vars" +import . "reference_global_vars" func main() { // const class reference variable diff --git a/Examples/test-suite/go/rename_scope_runme.go b/Examples/test-suite/go/rename_scope_runme.go index 995f8c64d..13bd3f178 100644 --- a/Examples/test-suite/go/rename_scope_runme.go +++ b/Examples/test-suite/go/rename_scope_runme.go @@ -1,6 +1,6 @@ package main -import . "./rename_scope" +import . "rename_scope" func main() { a := NewNatural_UP() diff --git a/Examples/test-suite/go/rename_simple_runme.go b/Examples/test-suite/go/rename_simple_runme.go index a63023bd1..bd559ef27 100644 --- a/Examples/test-suite/go/rename_simple_runme.go +++ b/Examples/test-suite/go/rename_simple_runme.go @@ -1,7 +1,7 @@ package main import "fmt" -import . "./rename_simple" +import . "rename_simple" func main() { s := NewNewStruct() diff --git a/Examples/test-suite/go/rename_strip_encoder_runme.go b/Examples/test-suite/go/rename_strip_encoder_runme.go index 1d0bcb660..ae670600c 100644 --- a/Examples/test-suite/go/rename_strip_encoder_runme.go +++ b/Examples/test-suite/go/rename_strip_encoder_runme.go @@ -1,6 +1,6 @@ package main -import . "./rename_strip_encoder" +import . "rename_strip_encoder" func main() { _ = NewSomeWidget() diff --git a/Examples/test-suite/go/ret_by_value_runme.go b/Examples/test-suite/go/ret_by_value_runme.go index 44743d2b7..9659d21e9 100644 --- a/Examples/test-suite/go/ret_by_value_runme.go +++ b/Examples/test-suite/go/ret_by_value_runme.go @@ -1,6 +1,6 @@ package main -import "./ret_by_value" +import "ret_by_value" func main() { a := ret_by_value.Get_test() diff --git a/Examples/test-suite/go/return_const_value_runme.go b/Examples/test-suite/go/return_const_value_runme.go index 790921b74..aadb1265e 100644 --- a/Examples/test-suite/go/return_const_value_runme.go +++ b/Examples/test-suite/go/return_const_value_runme.go @@ -1,6 +1,6 @@ package main -import "./return_const_value" +import "return_const_value" func main() { p := return_const_value.Foo_ptrGetPtr() diff --git a/Examples/test-suite/go/smart_pointer_extend_runme.go b/Examples/test-suite/go/smart_pointer_extend_runme.go index ee5ce0538..a851e26b7 100644 --- a/Examples/test-suite/go/smart_pointer_extend_runme.go +++ b/Examples/test-suite/go/smart_pointer_extend_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_extend" +import . "smart_pointer_extend" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/smart_pointer_member_runme.go b/Examples/test-suite/go/smart_pointer_member_runme.go index bf09fe5fc..e7fe7c4c2 100644 --- a/Examples/test-suite/go/smart_pointer_member_runme.go +++ b/Examples/test-suite/go/smart_pointer_member_runme.go @@ -1,7 +1,7 @@ package main import "fmt" -import . "./smart_pointer_member" +import . "smart_pointer_member" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/smart_pointer_multi_runme.go b/Examples/test-suite/go/smart_pointer_multi_runme.go index d1a5f92f4..7c76061af 100644 --- a/Examples/test-suite/go/smart_pointer_multi_runme.go +++ b/Examples/test-suite/go/smart_pointer_multi_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_multi" +import . "smart_pointer_multi" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/smart_pointer_multi_typedef_runme.go b/Examples/test-suite/go/smart_pointer_multi_typedef_runme.go index f71740bbb..e584cf7a2 100644 --- a/Examples/test-suite/go/smart_pointer_multi_typedef_runme.go +++ b/Examples/test-suite/go/smart_pointer_multi_typedef_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_multi_typedef" +import . "smart_pointer_multi_typedef" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/smart_pointer_overload_runme.go b/Examples/test-suite/go/smart_pointer_overload_runme.go index 5ffeae17c..9481554f0 100644 --- a/Examples/test-suite/go/smart_pointer_overload_runme.go +++ b/Examples/test-suite/go/smart_pointer_overload_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_overload" +import . "smart_pointer_overload" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/smart_pointer_rename_runme.go b/Examples/test-suite/go/smart_pointer_rename_runme.go index 678c305c8..44841f5e6 100644 --- a/Examples/test-suite/go/smart_pointer_rename_runme.go +++ b/Examples/test-suite/go/smart_pointer_rename_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_rename" +import . "smart_pointer_rename" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/smart_pointer_simple_runme.go b/Examples/test-suite/go/smart_pointer_simple_runme.go index 328654225..b468bd2e5 100644 --- a/Examples/test-suite/go/smart_pointer_simple_runme.go +++ b/Examples/test-suite/go/smart_pointer_simple_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_simple" +import . "smart_pointer_simple" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/smart_pointer_templatevariables_runme.go b/Examples/test-suite/go/smart_pointer_templatevariables_runme.go index bf58ba52c..6d4ea91de 100644 --- a/Examples/test-suite/go/smart_pointer_templatevariables_runme.go +++ b/Examples/test-suite/go/smart_pointer_templatevariables_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_templatevariables" +import . "smart_pointer_templatevariables" func main() { d := NewDiffImContainerPtr_D(Create(1234, 5678)) diff --git a/Examples/test-suite/go/smart_pointer_typedef_runme.go b/Examples/test-suite/go/smart_pointer_typedef_runme.go index a67a0ccda..e89a8b150 100644 --- a/Examples/test-suite/go/smart_pointer_typedef_runme.go +++ b/Examples/test-suite/go/smart_pointer_typedef_runme.go @@ -1,6 +1,6 @@ package main -import . "./smart_pointer_typedef" +import . "smart_pointer_typedef" func main() { f := NewFoo() diff --git a/Examples/test-suite/go/sneaky1_runme.go b/Examples/test-suite/go/sneaky1_runme.go index ee38ae21b..57c779724 100644 --- a/Examples/test-suite/go/sneaky1_runme.go +++ b/Examples/test-suite/go/sneaky1_runme.go @@ -1,6 +1,6 @@ package main -import "./sneaky1" +import "sneaky1" func main() { _ = sneaky1.Add(3, 4) diff --git a/Examples/test-suite/go/special_variable_macros_runme.go b/Examples/test-suite/go/special_variable_macros_runme.go index c4f687ea9..9338e6558 100644 --- a/Examples/test-suite/go/special_variable_macros_runme.go +++ b/Examples/test-suite/go/special_variable_macros_runme.go @@ -1,6 +1,6 @@ package main -import "./special_variable_macros" +import "special_variable_macros" func main() { name := special_variable_macros.NewName() diff --git a/Examples/test-suite/go/static_const_member_2_runme.go b/Examples/test-suite/go/static_const_member_2_runme.go index 0d345c3d6..ff8cbbbcd 100644 --- a/Examples/test-suite/go/static_const_member_2_runme.go +++ b/Examples/test-suite/go/static_const_member_2_runme.go @@ -1,6 +1,6 @@ package main -import . "./static_const_member_2" +import . "static_const_member_2" func main() { _ = NewTest_int() diff --git a/Examples/test-suite/go/struct_initialization_runme.go b/Examples/test-suite/go/struct_initialization_runme.go index 58ac25010..a815bd3f5 100644 --- a/Examples/test-suite/go/struct_initialization_runme.go +++ b/Examples/test-suite/go/struct_initialization_runme.go @@ -1,6 +1,6 @@ package main -import . "./struct_initialization" +import . "struct_initialization" func main() { if GetInstanceC1().GetX() != 10 { diff --git a/Examples/test-suite/go/struct_rename_runme.go b/Examples/test-suite/go/struct_rename_runme.go index 845dac5be..de99fc320 100644 --- a/Examples/test-suite/go/struct_rename_runme.go +++ b/Examples/test-suite/go/struct_rename_runme.go @@ -1,6 +1,6 @@ package main -import "./struct_rename" +import "struct_rename" func main() { _ = struct_rename.NewBar() diff --git a/Examples/test-suite/go/struct_value_runme.go b/Examples/test-suite/go/struct_value_runme.go index d0b60bd23..3b5e5c1dc 100644 --- a/Examples/test-suite/go/struct_value_runme.go +++ b/Examples/test-suite/go/struct_value_runme.go @@ -1,6 +1,6 @@ package main -import "./struct_value" +import "struct_value" func main() { b := struct_value.NewBar() diff --git a/Examples/test-suite/go/template_default_arg_runme.go b/Examples/test-suite/go/template_default_arg_runme.go index 3d9346b05..d67e63fa7 100644 --- a/Examples/test-suite/go/template_default_arg_runme.go +++ b/Examples/test-suite/go/template_default_arg_runme.go @@ -1,6 +1,6 @@ package main -import "./template_default_arg" +import "template_default_arg" func main() { helloInt := template_default_arg.NewHello_int() diff --git a/Examples/test-suite/go/template_extend1_runme.go b/Examples/test-suite/go/template_extend1_runme.go index 5d6d376f5..0912fa6ed 100644 --- a/Examples/test-suite/go/template_extend1_runme.go +++ b/Examples/test-suite/go/template_extend1_runme.go @@ -1,6 +1,6 @@ package main -import "./template_extend1" +import "template_extend1" func main() { a := template_extend1.NewLBaz() diff --git a/Examples/test-suite/go/template_extend2_runme.go b/Examples/test-suite/go/template_extend2_runme.go index 312410e27..ced3d93cc 100644 --- a/Examples/test-suite/go/template_extend2_runme.go +++ b/Examples/test-suite/go/template_extend2_runme.go @@ -1,6 +1,6 @@ package main -import "./template_extend2" +import "template_extend2" func main() { a := template_extend2.NewLBaz() diff --git a/Examples/test-suite/go/template_inherit_runme.go b/Examples/test-suite/go/template_inherit_runme.go index c0aca77c4..a8d5126dc 100644 --- a/Examples/test-suite/go/template_inherit_runme.go +++ b/Examples/test-suite/go/template_inherit_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_inherit" +import . "template_inherit" func main() { a := NewFooInt() diff --git a/Examples/test-suite/go/template_ns4_runme.go b/Examples/test-suite/go/template_ns4_runme.go index 4caf8f587..6c658ec97 100644 --- a/Examples/test-suite/go/template_ns4_runme.go +++ b/Examples/test-suite/go/template_ns4_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_ns4" +import . "template_ns4" func main() { d := Make_Class_DD() diff --git a/Examples/test-suite/go/template_ns_runme.go b/Examples/test-suite/go/template_ns_runme.go index 6385eccf9..cfc56fa3c 100644 --- a/Examples/test-suite/go/template_ns_runme.go +++ b/Examples/test-suite/go/template_ns_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_ns" +import . "template_ns" func main() { p1 := NewPairii(2, 3) diff --git a/Examples/test-suite/go/template_opaque_runme.go b/Examples/test-suite/go/template_opaque_runme.go index 201f7ba16..71701df53 100644 --- a/Examples/test-suite/go/template_opaque_runme.go +++ b/Examples/test-suite/go/template_opaque_runme.go @@ -1,6 +1,6 @@ package main -import "./template_opaque" +import "template_opaque" func main() { v := template_opaque.NewOpaqueVectorType(int64(10)) diff --git a/Examples/test-suite/go/template_ref_type_runme.go b/Examples/test-suite/go/template_ref_type_runme.go index e4bf626fb..a01ce3d31 100644 --- a/Examples/test-suite/go/template_ref_type_runme.go +++ b/Examples/test-suite/go/template_ref_type_runme.go @@ -1,6 +1,6 @@ package main -import "./template_ref_type" +import "template_ref_type" func main() { xr := template_ref_type.NewXC() diff --git a/Examples/test-suite/go/template_rename_runme.go b/Examples/test-suite/go/template_rename_runme.go index 757ac7355..6e04f8845 100644 --- a/Examples/test-suite/go/template_rename_runme.go +++ b/Examples/test-suite/go/template_rename_runme.go @@ -1,6 +1,6 @@ package main -import "./template_rename" +import "template_rename" func main() { i := template_rename.NewIFoo() diff --git a/Examples/test-suite/go/template_static_runme.go b/Examples/test-suite/go/template_static_runme.go index 7fa50760a..f10ea78f7 100644 --- a/Examples/test-suite/go/template_static_runme.go +++ b/Examples/test-suite/go/template_static_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_static" +import . "template_static" func main() { FooBar_double(1) diff --git a/Examples/test-suite/go/template_tbase_template_runme.go b/Examples/test-suite/go/template_tbase_template_runme.go index 9a52e2fac..e1c46aaf7 100644 --- a/Examples/test-suite/go/template_tbase_template_runme.go +++ b/Examples/test-suite/go/template_tbase_template_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_tbase_template" +import . "template_tbase_template" func main() { a := Make_Class_dd() diff --git a/Examples/test-suite/go/template_type_namespace_runme.go b/Examples/test-suite/go/template_type_namespace_runme.go index a3712ff59..1356f9b08 100644 --- a/Examples/test-suite/go/template_type_namespace_runme.go +++ b/Examples/test-suite/go/template_type_namespace_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_type_namespace" +import . "template_type_namespace" func main() { if Foo().Get(0) == "" { diff --git a/Examples/test-suite/go/template_typedef_cplx3_runme.go b/Examples/test-suite/go/template_typedef_cplx3_runme.go index d616777e0..0a2b31301 100644 --- a/Examples/test-suite/go/template_typedef_cplx3_runme.go +++ b/Examples/test-suite/go/template_typedef_cplx3_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_typedef_cplx3" +import . "template_typedef_cplx3" func main() { // this is OK diff --git a/Examples/test-suite/go/template_typedef_cplx4_runme.go b/Examples/test-suite/go/template_typedef_cplx4_runme.go index 3e536d6f2..d8952cfb6 100644 --- a/Examples/test-suite/go/template_typedef_cplx4_runme.go +++ b/Examples/test-suite/go/template_typedef_cplx4_runme.go @@ -1,6 +1,6 @@ package main -import . "./template_typedef_cplx4" +import . "template_typedef_cplx4" func main() { // this is OK diff --git a/Examples/test-suite/go/threads_exception_runme.go b/Examples/test-suite/go/threads_exception_runme.go index 742a827bd..e3da1dc25 100644 --- a/Examples/test-suite/go/threads_exception_runme.go +++ b/Examples/test-suite/go/threads_exception_runme.go @@ -1,7 +1,7 @@ package main import "strings" -import "./threads_exception" +import "threads_exception" func main() { t := threads_exception.NewTest() diff --git a/Examples/test-suite/go/typedef_class_runme.go b/Examples/test-suite/go/typedef_class_runme.go index ec25162de..d94126d3b 100644 --- a/Examples/test-suite/go/typedef_class_runme.go +++ b/Examples/test-suite/go/typedef_class_runme.go @@ -1,6 +1,6 @@ package main -import "./typedef_class" +import "typedef_class" func main() { a := typedef_class.NewRealA() diff --git a/Examples/test-suite/go/typedef_funcptr_runme.go b/Examples/test-suite/go/typedef_funcptr_runme.go index 49d7086b1..9d55f3f04 100644 --- a/Examples/test-suite/go/typedef_funcptr_runme.go +++ b/Examples/test-suite/go/typedef_funcptr_runme.go @@ -1,6 +1,6 @@ package main -import . "./typedef_funcptr" +import . "typedef_funcptr" func main() { a := 100 diff --git a/Examples/test-suite/go/typedef_inherit_runme.go b/Examples/test-suite/go/typedef_inherit_runme.go index 49097999c..7a65569f2 100644 --- a/Examples/test-suite/go/typedef_inherit_runme.go +++ b/Examples/test-suite/go/typedef_inherit_runme.go @@ -1,6 +1,6 @@ package main -import "./typedef_inherit" +import "typedef_inherit" func main() { a := typedef_inherit.NewFoo() diff --git a/Examples/test-suite/go/typedef_scope_runme.go b/Examples/test-suite/go/typedef_scope_runme.go index 1c4314427..af282b16f 100644 --- a/Examples/test-suite/go/typedef_scope_runme.go +++ b/Examples/test-suite/go/typedef_scope_runme.go @@ -1,6 +1,6 @@ package main -import "./typedef_scope" +import "typedef_scope" func main() { b := typedef_scope.NewBar() diff --git a/Examples/test-suite/go/typemap_namespace_runme.go b/Examples/test-suite/go/typemap_namespace_runme.go index 45184fd1e..a2880d4a8 100644 --- a/Examples/test-suite/go/typemap_namespace_runme.go +++ b/Examples/test-suite/go/typemap_namespace_runme.go @@ -1,6 +1,6 @@ package main -import . "./typemap_namespace" +import . "typemap_namespace" func main() { if Test1("hello") != "hello" { diff --git a/Examples/test-suite/go/typemap_ns_using_runme.go b/Examples/test-suite/go/typemap_ns_using_runme.go index 877e44b3a..c4c21cf75 100644 --- a/Examples/test-suite/go/typemap_ns_using_runme.go +++ b/Examples/test-suite/go/typemap_ns_using_runme.go @@ -1,6 +1,6 @@ package main -import "./typemap_ns_using" +import "typemap_ns_using" func main() { if typemap_ns_using.Spam(37) != 37 { diff --git a/Examples/test-suite/go/typemap_out_optimal_runme.go b/Examples/test-suite/go/typemap_out_optimal_runme.go index 7cbd0ad9b..7cc3b38e3 100644 --- a/Examples/test-suite/go/typemap_out_optimal_runme.go +++ b/Examples/test-suite/go/typemap_out_optimal_runme.go @@ -1,6 +1,6 @@ package main -import . "./typemap_out_optimal" +import . "typemap_out_optimal" func main() { SetXXDebug(false) diff --git a/Examples/test-suite/go/typename_runme.go b/Examples/test-suite/go/typename_runme.go index 0bc15f11a..d1665099c 100644 --- a/Examples/test-suite/go/typename_runme.go +++ b/Examples/test-suite/go/typename_runme.go @@ -1,6 +1,6 @@ package main -import "./typename" +import "typename" func main() { f := typename.NewFoo() diff --git a/Examples/test-suite/go/unions_runme.go b/Examples/test-suite/go/unions_runme.go index ba9c27b17..b76ca5c75 100644 --- a/Examples/test-suite/go/unions_runme.go +++ b/Examples/test-suite/go/unions_runme.go @@ -3,7 +3,7 @@ package main -import "./unions" +import "unions" func main() { // Create new instances of SmallStruct and BigStruct for later use diff --git a/Examples/test-suite/go/using1_runme.go b/Examples/test-suite/go/using1_runme.go index 8cc571288..a6a6fa738 100644 --- a/Examples/test-suite/go/using1_runme.go +++ b/Examples/test-suite/go/using1_runme.go @@ -1,6 +1,6 @@ package main -import "./using1" +import "using1" func main() { if using1.Spam(37) != 37 { diff --git a/Examples/test-suite/go/using2_runme.go b/Examples/test-suite/go/using2_runme.go index f679b0c40..f6b8d49b5 100644 --- a/Examples/test-suite/go/using2_runme.go +++ b/Examples/test-suite/go/using2_runme.go @@ -1,6 +1,6 @@ package main -import "./using2" +import "using2" func main() { if using2.Spam(37) != 37 { diff --git a/Examples/test-suite/go/using_composition_runme.go b/Examples/test-suite/go/using_composition_runme.go index 47e245719..712d1fad5 100644 --- a/Examples/test-suite/go/using_composition_runme.go +++ b/Examples/test-suite/go/using_composition_runme.go @@ -1,6 +1,6 @@ package main -import . "./using_composition" +import . "using_composition" func main() { f := NewFooBar() diff --git a/Examples/test-suite/go/using_extend_runme.go b/Examples/test-suite/go/using_extend_runme.go index 830c958e5..27d1ccc62 100644 --- a/Examples/test-suite/go/using_extend_runme.go +++ b/Examples/test-suite/go/using_extend_runme.go @@ -1,6 +1,6 @@ package main -import . "./using_extend" +import . "using_extend" func main() { f := NewFooBar() diff --git a/Examples/test-suite/go/using_inherit_runme.go b/Examples/test-suite/go/using_inherit_runme.go index db29efb64..a88171817 100644 --- a/Examples/test-suite/go/using_inherit_runme.go +++ b/Examples/test-suite/go/using_inherit_runme.go @@ -1,6 +1,6 @@ package main -import . "./using_inherit" +import . "using_inherit" func main() { b := NewBar() diff --git a/Examples/test-suite/go/using_private_runme.go b/Examples/test-suite/go/using_private_runme.go index d683ef856..2da62dc2e 100644 --- a/Examples/test-suite/go/using_private_runme.go +++ b/Examples/test-suite/go/using_private_runme.go @@ -1,6 +1,6 @@ package main -import . "./using_private" +import . "using_private" func main() { f := NewFooBar() diff --git a/Examples/test-suite/go/using_protected_runme.go b/Examples/test-suite/go/using_protected_runme.go index 65edb5001..3fd5029f7 100644 --- a/Examples/test-suite/go/using_protected_runme.go +++ b/Examples/test-suite/go/using_protected_runme.go @@ -1,6 +1,6 @@ package main -import . "./using_protected" +import . "using_protected" func main() { f := NewFooBar() diff --git a/Examples/test-suite/go/varargs_overload_runme.go b/Examples/test-suite/go/varargs_overload_runme.go index 5978be005..8ce580d65 100644 --- a/Examples/test-suite/go/varargs_overload_runme.go +++ b/Examples/test-suite/go/varargs_overload_runme.go @@ -1,6 +1,6 @@ package main -import "./varargs_overload" +import "varargs_overload" func main() { if varargs_overload.Vararg_over1("Hello") != "Hello" { diff --git a/Examples/test-suite/go/varargs_runme.go b/Examples/test-suite/go/varargs_runme.go index 4009c3ed3..60bd8829a 100644 --- a/Examples/test-suite/go/varargs_runme.go +++ b/Examples/test-suite/go/varargs_runme.go @@ -1,6 +1,6 @@ package main -import "./varargs" +import "varargs" func main() { if varargs.Test("Hello") != "Hello" { diff --git a/Examples/test-suite/go/virtual_derivation_runme.go b/Examples/test-suite/go/virtual_derivation_runme.go index 48a7033a2..4e2c6e585 100644 --- a/Examples/test-suite/go/virtual_derivation_runme.go +++ b/Examples/test-suite/go/virtual_derivation_runme.go @@ -1,6 +1,6 @@ package main -import . "./virtual_derivation" +import . "virtual_derivation" // very innocent example diff --git a/Examples/test-suite/go/virtual_poly_runme.go b/Examples/test-suite/go/virtual_poly_runme.go index 487b371ba..32906b391 100644 --- a/Examples/test-suite/go/virtual_poly_runme.go +++ b/Examples/test-suite/go/virtual_poly_runme.go @@ -1,6 +1,6 @@ package main -import "./virtual_poly" +import "virtual_poly" func main() { d := virtual_poly.NewNDouble(3.5) diff --git a/Examples/test-suite/go/voidtest_runme.go b/Examples/test-suite/go/voidtest_runme.go index 0a685f081..133545cea 100644 --- a/Examples/test-suite/go/voidtest_runme.go +++ b/Examples/test-suite/go/voidtest_runme.go @@ -1,6 +1,6 @@ package main -import "./voidtest" +import "voidtest" func main() { voidtest.Globalfunc() diff --git a/Examples/test-suite/go/wrapmacro_runme.go b/Examples/test-suite/go/wrapmacro_runme.go index dc7e7bf5b..a251a05e8 100644 --- a/Examples/test-suite/go/wrapmacro_runme.go +++ b/Examples/test-suite/go/wrapmacro_runme.go @@ -1,6 +1,6 @@ package main -import "./wrapmacro" +import "wrapmacro" func main() { a := 2 diff --git a/Examples/test-suite/go_subdir_import.list b/Examples/test-suite/go_subdir_import.list index e117d32fa..074c795b3 100644 --- a/Examples/test-suite/go_subdir_import.list +++ b/Examples/test-suite/go_subdir_import.list @@ -1,3 +1,3 @@ testdir/go_subdir_import/go_subdir_import_c -go_subdir_import_b +testdir/go_subdir_import/go_subdir_import_b go_subdir_import_a diff --git a/Source/Modules/go.cxx b/Source/Modules/go.cxx index 9e8162b5d..0163f71df 100644 --- a/Source/Modules/go.cxx +++ b/Source/Modules/go.cxx @@ -125,6 +125,8 @@ class GO:public Language { String *prefix_option; // -fgo-pkgpath option. String *pkgpath_option; + // Prefix for translating %import directive to import statements. + String *import_prefix; // Whether to use a shared library. bool use_shlib; // Name of shared library to import. @@ -204,6 +206,7 @@ public: go_prefix(NULL), prefix_option(NULL), pkgpath_option(NULL), + import_prefix(NULL), use_shlib(false), soname(NULL), intgo_type_size(0), @@ -293,6 +296,15 @@ private: } else { Swig_arg_error(); } + } else if (strcmp(argv[i], "-import-prefix") == 0) { + if (argv[i + 1]) { + import_prefix = NewString(argv[i + 1]); + Swig_mark_arg(i); + Swig_mark_arg(i + 1); + i++; + } else { + Swig_arg_error(); + } } else if (strcmp(argv[i], "-use-shlib") == 0) { Swig_mark_arg(i); use_shlib = true; @@ -743,7 +755,11 @@ private: if (modname) { if (!Getattr(go_imports, modname)) { Setattr(go_imports, modname, modname); - Printv(f_go_imports, "import \"", modname, "\"\n", NULL); + Printv(f_go_imports, "import \"", NULL); + if (import_prefix) { + Printv(f_go_imports, import_prefix, "/", NULL); + } + Printv(f_go_imports, modname, "\"\n", NULL); } imported_package = modname; saw_import = true; @@ -6983,9 +6999,10 @@ const char * const GO::usage = "\ Go Options (available with -go)\n\ -cgo - Generate cgo input files\n\ -no-cgo - Do not generate cgo input files\n\ - -gccgo - Generate code for gccgo rather than 6g/8g\n\ + -gccgo - Generate code for gccgo rather than gc\n\ -go-pkgpath

      - Like gccgo -fgo-pkgpath option\n\ -go-prefix

      - Like gccgo -fgo-prefix option\n\ + -import-prefix

      - Prefix to add to %import directives\n\ -intgosize - Set size of Go int type--32 or 64 bits\n\ -package - Set name of the Go package to \n\ -use-shlib - Force use of a shared library\n\ From 11b54b0cbdac8707ee4c9ef4b32e51eebe7b669e Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 25 Apr 2019 23:12:23 +0100 Subject: [PATCH 114/134] Fix command line error handling to work like in 3.0.12 Output is once again: $ swig -versioon Unable to find option or file '-versioon', Use 'swig -help' for more information. instead of $ swig -versioon No target language specified --- Source/Modules/main.cxx | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/Source/Modules/main.cxx b/Source/Modules/main.cxx index 0b615ce0a..c6bd148e2 100644 --- a/Source/Modules/main.cxx +++ b/Source/Modules/main.cxx @@ -970,11 +970,6 @@ int SWIG_main(int argc, char *argv[], const TargetLanguageModule *tlm) { SWIG_exit(EXIT_SUCCESS); // Exit if we're in help mode } - if (!tlm) { - Printf(stderr, "No target language specified\n"); - return 1; - } - // Check all of the options to make sure we're cool. // Don't check for an input file if -external-runtime is passed Swig_check_options(external_runtime ? 0 : 1); @@ -1070,7 +1065,7 @@ int SWIG_main(int argc, char *argv[], const TargetLanguageModule *tlm) { char *cfile = Char(input_file); if (cfile && cfile[0] == '-') { Printf(stderr, "Unable to find option or file '%s', ", input_file); - Printf(stderr, "use 'swig -help' for more information.\n"); + Printf(stderr, "Use 'swig -help' for more information.\n"); } else { Printf(stderr, "Unable to find file '%s'.\n", input_file); } @@ -1079,6 +1074,13 @@ int SWIG_main(int argc, char *argv[], const TargetLanguageModule *tlm) { Swig_warning(WARN_DEPRECATED_INPUT_FILE, "SWIG", 1, "Use of the include path to find the input file is deprecated and will not work with ccache. Please include the path when specifying the input file.\n"); // so that behaviour is like c/c++ compilers } } + + if (!tlm) { + Printf(stderr, "No target language specified.\n"); + Printf(stderr, "Use 'swig -help' for more information.\n"); + SWIG_exit(EXIT_FAILURE); + } + if (!no_cpp) { fclose(df); Printf(fs, "%%include \n"); From 2937f0529615a6220418bc3bcdf18902ed8bb9a9 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 26 Apr 2019 19:21:40 +0100 Subject: [PATCH 115/134] Add 4.0.0 release date --- ANNOUNCE | 2 +- CHANGES.current | 2 +- Doc/Manual/Sections.html | 2 +- README | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/ANNOUNCE b/ANNOUNCE index 764f39c92..2ef6eb131 100644 --- a/ANNOUNCE +++ b/ANNOUNCE @@ -1,4 +1,4 @@ -*** ANNOUNCE: SWIG 4.0.0 (in progress) *** +*** ANNOUNCE: SWIG 4.0.0 (27 Apr 2019) *** http://www.swig.org diff --git a/CHANGES.current b/CHANGES.current index fa13e9e48..6ead3a621 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -4,7 +4,7 @@ See the RELEASENOTES file for a summary of changes in each release. Issue # numbers mentioned below can be found on Github. For more details, add the issue number to the end of the URL: https://github.com/swig/swig/issues/ -Version 4.0.0 (in progress) +Version 4.0.0 (27 Apr 2019) =========================== 2019-04-24: vadz diff --git a/Doc/Manual/Sections.html b/Doc/Manual/Sections.html index f57108535..6db5c3cc1 100644 --- a/Doc/Manual/Sections.html +++ b/Doc/Manual/Sections.html @@ -8,7 +8,7 @@

      SWIG-4.0 Documentation

      -Last update : SWIG-4.0.0 (in progress) +Last update : SWIG-4.0.0 (27 Apr 2019)

      Sections

      diff --git a/README b/README index db468d8d4..ecf4f87fc 100644 --- a/README +++ b/README @@ -1,6 +1,6 @@ SWIG (Simplified Wrapper and Interface Generator) -Version: 4.0.0 (in progress) +Version: 4.0.0 (27 Apr 2019) Tagline: SWIG is a compiler that integrates C and C++ with languages including Perl, Python, Tcl, Ruby, PHP, Java, C#, D, Go, Lua, From 9c3faeb0ee6c588bc4772bd186554796cc1e446e Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Fri, 26 Apr 2019 19:48:33 +0100 Subject: [PATCH 116/134] Travis testing of Go changes Use gimme to install a version of Go to test. Travis already uses gimme to pre-install a version of Go. Switch some of the Go testing from travis to xenial. --- .travis.yml | 13 +++++++++---- Tools/travis-linux-install.sh | 3 +++ 2 files changed, 12 insertions(+), 4 deletions(-) diff --git a/.travis.yml b/.travis.yml index 78d8883b5..61021b4e4 100644 --- a/.travis.yml +++ b/.travis.yml @@ -31,14 +31,19 @@ matrix: dist: trusty - compiler: gcc os: linux - env: SWIGLANG=go + env: SWIGLANG=go VER=1.3 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux - env: SWIGLANG=go VER=1.5 + env: SWIGLANG=go VER=1.8 sudo: required - dist: trusty + dist: xenial + - compiler: gcc + os: linux + env: SWIGLANG=go VER=1.12 + sudo: required + dist: xenial - compiler: gcc os: linux env: SWIGLANG=guile diff --git a/Tools/travis-linux-install.sh b/Tools/travis-linux-install.sh index dc8526546..bfa7bf8eb 100755 --- a/Tools/travis-linux-install.sh +++ b/Tools/travis-linux-install.sh @@ -37,6 +37,9 @@ case "$SWIGLANG" in travis_retry sudo dpkg -i dmd_2.066.0-0_amd64.deb ;; "go") + if [[ "$VER" ]]; then + eval "$(gimme ${VER}.x)" + fi ;; "javascript") case "$ENGINE" in From 6a91723fcfeb413350d46908343de2eb5562e3b4 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sun, 28 Apr 2019 21:01:21 +0100 Subject: [PATCH 117/134] Bump version to 4.0.1 --- ANNOUNCE | 20 +- CHANGES | 1535 ++++++++++++++++++++++++++++++++++++++ CHANGES.current | 1533 +------------------------------------ Doc/Manual/Sections.html | 2 +- README | 2 +- configure.ac | 2 +- 6 files changed, 1548 insertions(+), 1546 deletions(-) diff --git a/ANNOUNCE b/ANNOUNCE index 2ef6eb131..b83921cc4 100644 --- a/ANNOUNCE +++ b/ANNOUNCE @@ -1,8 +1,8 @@ -*** ANNOUNCE: SWIG 4.0.0 (27 Apr 2019) *** +*** ANNOUNCE: SWIG 4.0.1 (in progress) *** http://www.swig.org -We're pleased to announce SWIG-4.0.0, the latest SWIG release. +We're pleased to announce SWIG-4.0.1, the latest SWIG release. What is SWIG? ============= @@ -10,13 +10,11 @@ What is SWIG? SWIG is a software development tool that reads C/C++ header files and generates the wrapper code needed to make C and C++ code accessible from other programming languages including Perl, Python, Tcl, Ruby, -PHP, C#, Go, Java, Javascript, Lua, Scheme (Guile, MzScheme), -D, Ocaml, Octave, R, Scilab. -SWIG can also export its parse tree in -the form of XML. Major applications of SWIG -include generation of scripting language extension modules, rapid -prototyping, testing, and user interface development for large -C/C++ systems. +PHP, C#, Go, Java, Javascript, Lua, Scheme (Guile, MzScheme), D, +Ocaml, Octave, R, Scilab. SWIG can also export its parse tree in +the form of XML. Major applications of SWIG include generation of +scripting language extension modules, rapid prototyping, testing, +and user interface development for large C/C++ systems. Release Notes ============= @@ -27,11 +25,11 @@ Availability ============ The release is available for download on Sourceforge at - http://prdownloads.sourceforge.net/swig/swig-4.0.0.tar.gz + http://prdownloads.sourceforge.net/swig/swig-4.0.1.tar.gz A Windows version is also available at - http://prdownloads.sourceforge.net/swig/swigwin-4.0.0.zip + http://prdownloads.sourceforge.net/swig/swigwin-4.0.1.zip Please report problems with this release to the swig-devel mailing list, details at http://www.swig.org/mail.html. diff --git a/CHANGES b/CHANGES index 958e7cb0c..77d570ddb 100644 --- a/CHANGES +++ b/CHANGES @@ -5,6 +5,1541 @@ See the RELEASENOTES file for a summary of changes in each release. Issue # numbers mentioned below can be found on Github. For more details, add the issue number to the end of the URL: https://github.com/swig/swig/issues/ +Version 4.0.0 (27 Apr 2019) +=========================== + +2019-04-24: vadz + #1517 Fix crash if "@return" Doxygen tag was used on a node without any return type. + +2019-04-24: vadz + #1515 Fix parsing of enums with trailing comma when using -doxygen. + +2019-04-19: ianlancetaylor + [Go] #1055 When generating Go code, make -cgo the default. Add new -no-cgo option + to disable the default. + +2019-04-19: pbecherer + [Tcl] #1508 Fix Visual Studio 2015 and later compilation errors due to snprintf macro + definition. + +2019-04-09: wsfulton + [C#] Fix FxCop warning CA2002 in SWIGPendingException - a lock on a reference of + type 'Type'. + +2019-03-30: wsfulton + [Java, D] Add the parameters typemap attribute to the javadestruct, + javadestruct_derived, ddispose, ddispose_derived typemaps to mirror enhanced + flexibility in the csdisposing and csdisposing_derived (C#) typemaps. If provided + the contents are generated as the delete/dispose method's parameters declaration. + +2019-03-30: wsfulton + [C#] #421 Fix FxCop warning CA1063 by implementing the recommended Dispose methods for + the IDisposable interface. Previously just the Dispose() method was generated. + Now the Dispose() and Dispose(bool disposing) methods are generated. + Changes are required if custom "csfinalize", "csdestruct" or "csdestruct_derived" + typemaps are being used. Details in #421 on Github. SWIG will error out if one of + the "csfinalize, "csdestruct" or "csdestruct_derived" typemaps are found. Example + error message: + + foo.h:60: Error: A deprecated csfinalize typemap was found for Foo, please remove + it and replace all csdestruct, csdestruct_derived and csfinalize typemaps by the + csdispose, csdispose_derived, csdisposing and csdisposing_derived typemaps. + + *** POTENTIAL INCOMPATIBILITY *** + +2019-03-25: Liryna + [C#] #1143 Add std_list.i for std::list support. + The C# std::list wrappers are made to look and feel like a C# + System.Collections.Generic.LinkedList<> collection. + The IEnumerable<> interface is implemented in the proxy class. + The ICollection<> interface can also be implemented to provide enhanced functionality + whenever a C++ operator== is available. This is the case for when T is a + primitive type or a pointer. If T does define an operator==, then use the + SWIG_STD_LIST_ENHANCED macro to obtain this enhanced functionality, for example: + + SWIG_STD_LIST_ENHANCED(SomeNamespace::Klass) + %template(ListKlass) std::list; + +2019-03-18: richardbeare + [R] #1328 Non-trivial enums are working now. The enum values are now obtained from + the C/C++ layer. const reference enums and C++11 enum classes are also now working. + +2019-03-14: mochizk + [Javascript] #1500 Fix compilation errors due to deprecating V8 API in Node.js. + New V8 API is used if node.js >= v10.12, or if V8 >= v7.0. + +2019-03-12: vadz + [C#] #1495 Add std_set.i for std::set support. + +2019-03-11: dirteat,opoplawski + [Octave] Fix compilation errors in Octave 5.1. + + error: format not a string literal and no format arguments [-Werror=format-security] + +2019-02-28: wsfulton + [Java] std::vector improvements for types that do not have a default constructor. + + The std::vector wrappers have been changed to work by default for elements that are + not default insertable, i.e. have no default constructor. This has been achieved by + not wrapping: + + vector(size_type n); + + Previously the above had to be ignored via %ignore. + + If the above constructor is still required it can be added back in again via %extend: + + %extend std::vector { + vector(size_type count) { return new std::vector< T >(count); } + } + + Alternatively, the following wrapped constructor could be used as it provides near-enough + equivalent functionality: + + vector(jint count, const value_type& value); + + *** POTENTIAL INCOMPATIBILITY *** + +2019-02-25: wsfulton + [Python] Fix compile errors wrapping overloaded functions/constructors where a vararg + function is declared after a non-vararg function. + +2019-02-23: zphensley42 + Use fully qualified name 'java.lang.Object' instead of 'Object' in generated code to + avoid clashes with wrapped C++ classes called 'Object'. + +2019-02-23: gtbX + [Java] #1035 Add (const char *STRING, size_t LENGTH) typemaps in addition to the non-const + typemaps (char *STRING, size_t LENGTH) which does not attempt to write back to the const + string. + +2019-02-22: tamuratak + [Ruby] #984 Add support for RTypedData introduced in Ruby 1.9.3. + +2019-02-22: ZackerySpytz + #1483 Fix compilation failures when a director class has final methods. + +2019-02-21: wsfulton + [Java] #1240 Suppress Java 9 deprecation warnings on finalize method. + +2019-02-21: ZackerySpytz + #1480 Fix some rejections of valid floating-point literals. + +2019-02-19: wsfulton + #1475 Fix regression parsing gcc preprocessor linemarkers in the form: + + # linenum filename flags + +2019-02-18: jakecobb + [Python] #945 #1234 Elements in std::vector memory access fix. + + Accessing an element in a std::vector obtains a reference to the element via an + iterator pointing to the element in the container. If the vector is garbage collected, + the SWIG wrapper containing the pointer to the element becomes invalid. The fix is + to obtain a back-reference to the container by the wrapper to the element in the Python + layer to prevent the garbage collector from destroying the underlying container. + +2019-02-17: wsfulton + Fix typemap matching to expand template parameters when the name contains + template parameters. In the %typemap below the type is T and the name is X::make + and the name now expands correctly to X< int >::make + + template struct X { + %typemap(out) T X::make "..." + T make(); + }; + + %template(Xint) X; + +2019-02-16: wsfulton + Fix parser error containing multiple #define statements inside an enum. + + The second #define fails to parse: + + enum FooEnum { + ENUM1 = 0, + ENUM2 = 1, + + #define MACRO_DEF1 "Hello" + #define MACRO_DEF2 "World!" + + ENUM3 = 2, + ENUM4 = 3, + }; + + Bug mentioned at https://sourceforge.net/p/swig/patches/333/ + +2019-02-14: wsfulton + Add some missing copy constructors into STL containers. + +2019-02-14: bkotzz + [Java] #1356 Add STL containers: + std::unordered_map + std::unordered_set + std::set + +2019-02-14: bkotzz + [Java] #1356 std::map wrappers have been modified. Now the Java proxy class + extends java.util.AbstractMap. The std::map container looks and feels much like + a java.util.HashMap from Java. + + A few members have changed their names. If the old method signatures are needed, + then copy std_map.i from swig-3.0.12 and use that instead. Alternatively, + add the old missing methods to the new methods by using the following %proxycode: + + %extend std::map { + %proxycode %{ + // Old API + public boolean empty() { + return isEmpty(); + } + public void set($typemap(jboxtype, K) key, $typemap(jboxtype, T) x) { + put(key, x); + } + public void del($typemap(jboxtype, K) key) { + remove(key); + } + public boolean has_key($typemap(jboxtype, K) key) { + return containsKey(key); + } + %} + } + + *** POTENTIAL INCOMPATIBILITY *** + +2019-02-13: ZackerySpytz + #1469 Add support for C++17 hexadecimal floating literals. + +2019-02-11: wsfulton + [OCaml] #1437 OCaml has been give the 'Experimental' language status. The examples work + and most of the test-suite is also working, so it is quite close to being a 'Supported' language. + +2019-02-10: ZackerySpytz + #1464 Add support for C++14 binary integer literals. + +2019-02-10: ZackerySpytz + #1450 Add support for C++11 UCS-2 and UCS-4 character literals. Also, add support for + C++17 UTF-8 character literals. + +2019-02-10: wsfulton + [MzScheme] #1437 MzScheme/Racket is now an 'Experimental' language. The examples work + and a large portion of the test-suite is also working. + +2019-02-10: wsfulton + [MzScheme] Destructor wrappers were not being generated. + +2019-02-10: wsfulton + [MzScheme] Static variable wrappers fixed - $argnum was not expanded. + +2019-02-10: sethrj + #1452 Fix %apply for anonymous template instantiations + +2019-02-09: olly + [PHP] Fix access to already released memory during PHP module + shutdown, which often didn't cause visible problems, but could + result in segmentation faults, bus errors, etc. Fixes #1170, + reported by Jitka Plesníková. + +2019-02-09: olly + [PHP] A renamed constructor is now wrapped as a static method in + PHP. + +2019-02-08: olly + [PHP] Don't generate code which references $r when $r hasn't been + defined. This could happen in overloaded methods which returned + void and took at least one const std::string& parameter. + +2019-02-08: olly + [PHP] The generated code is now compatible with PHP 7.3, and the + testsuite now runs cleanly with this version too. + +2019-02-05: wsfulton + #1437 SWIG now classifies the status of target languages into either 'Experimental' or + 'Supported'. This status is provided to indicate the level of maturity to expect when using + a particular target language as not all target languages are fully developed. Details are + in the Introduction.html chapter of the documentation. + +2019-02-04: wsfulton + [CFFI] #1447 Common Lisp CFFI has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-04: wsfulton + [Allegrocl] #1447 Allegro Common Lisp has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-04: wsfulton + [Chicken] #1447 CHICKEN has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-04: wsfulton + [CLISP] #1447 GNU Common Lisp has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-04: wsfulton + [S-EXP] #1447 Common Lisp S-Exp has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-04: wsfulton + [UFFI] #1447 Common Lisp UFFI has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-04: wsfulton + [Pike] #1447 Pike has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-04: wsfulton + [Modula3] #1447 Modula3 has been disabled as a target language in SWIG as part of a + clean up to remove target languages that have been neglected/not functional. + +2019-02-02: ahnolds + [Python] Documentation enhancements for Python: + + #728 Fixed the handling of autodoc when using -fastproxy. + + #1367 Added documentation to wrapped member variables using the + property(... doc="...") construct. + + Only show a single documentation entry for functions with default arguments when + using autodoc. + + Fixed a bug where a cached doxygen docstring could be deleted while still in use, + causing swig to segfault. + +2019-01-31: olly + SWIG now requires a target language to be specified instead of + defaulting to wrapping for Tcl. Specifying swig --help without + a target language now just shows the generic help. The -nolang + option has been removed. + +2019-01-28: ZackerySpytz + [OCaml] #1429 Remove support for OCaml versions < 3.12.0. + + *** POTENTIAL INCOMPATIBILITY *** + +2019-01-22: vadz + [Ruby, Octave] #1424 Improve autodoc parameter naming. + +2019-01-22: vadz + [Python] #1271 #1423 Always include default parameter values in autodoc strings. + +2019-01-19: vadz + #1272, #1421 When a function's parameter is a keyword, the name of the paramater is + no longer simply changed to argN, where N is the argument number. Instead the + parameter name is changed to the renaming rules for keywords that normally apply to + symbols such as classes/functions etc. Note that unlike other symbol renaming, + parameter renaming does not issue a warning when the parameter is renamed. This + change only affects languages where the parameter names are actually used, for example, + Java function parameter lists in the proxy class or Python documentation comments. + +2019-01-18: wsfulton + #1420 Fix gdb debugger functions 'swigprint' and 'locswigprint' from swig.gdb to + work with newer versions of gdb-8. Fixes errors when debugging SWIG source with gdb: + + (gdb) swigprint n + Undefined command: "Printf". Try "help". + +2019-01-16: wsfulton + Python static method wrapper changes + + - Static method wrappers were using the 'fastproxy' approach by default. + This is inconsistent with instance method wrappers. The fastproxy approach + is now turned off by default to be consistent with instance methods. + Static method wrappers can now also be controlled using the -fastproxy and + -olddefs options. + + Example: + + struct Klass { + static int statmethod(int a = 2); + }; + + generates by default: + + class Klass(object): + ... + @staticmethod + def statmethod(a=2): + return _example.Klass_statmethod(a) + + instead of the following (which can be restored by using -fastproxy): + + class Klass(object): + ... + statmethod = staticmethod(_example.Klass_statmethod) + + - Modernise wrappers for static methods to use decorator syntax - @staticmethod. + + - Add missing runtime test for static class methods and using the actual class method. + +2019-01-12: ZackerySpytz + [OCaml] #1403 #1194 Fix compilation problems for OCaml >= 4.03.0 due to OCaml using + int64_t instead of int64. + +2019-01-11: ZackerySpytz + [OCaml] #1400 Fix the getters and setters of non-static member variables. + +2019-01-07: wsfulton + #358 Add VOID to windows.i + +2019-01-05: wsfulton + #948 #1019 #1273 Fix for C++11 raw strings where the delimiters were mistakenly left + in the string contents in situations where the string was copied into generated code. + For example, %constant, the "docstring" feature and for C#/Java/D constants turned on + with %javaconst/%csconst/%dmanifestconst. + +2019-01-05: wsfulton + [Ruby] #538. Fix Ruby support for %feature("docstring"). + +2019-01-03: wsfulton + #1202 Fix overloading of non-pointer class types in scripting languages when overloaded + with a pointer and a NULL scripting language equivalent is used, eg None in Python. + + The implementation changes the SWIGTYPE, SWIGTYPE& and SWIGTYPE&& typecheck typemaps to + prevent accepting a conversion to a NULL pointer. + +2019-01-03: ZackerySpytz + [OCaml] #1386 Fix the OCaml examples and test suite for out-of-source builds. + +2019-01-01: wsfulton + [Python] #639 remove duplicate proxy method definitions for global function wrappers. + + Global functions previously generated two definitions, eg: + + def foo(): + return _example.foo() + foo = _example.foo + + The first definition is replaced by the second definition and so the second definition + is the one used when the method is actually called. Now just the first definition is + generated by default and if the -fastproxy command line option is used, just the second + definition is generated. The second definition is faster as it avoids the proxy Python + method as it calls the low-level C wrapper directly. Using both -fastproxy and -olddefs + command line options will restore the previously generated code as it will generate both + method definitions. + + With this change, the wrappers for global C/C++ functions and C++ class methods now work + in the same way wrt to generating just a proxy method by default and control via + -fastproxy/-olddefs options. + +2018-12-20: hasinoff,wsfulton + [Java] #1334 Set Java thread name to native thread name when using directors. + + Default is to use name "Thread-XXX" and is still works like this by default. However, + adding the following will turn on the thread name setting (works for more recent + versions of Linux and MacOS): + + %begin %{ + #define SWIG_JAVA_USE_THREAD_NAME + %} + +2018-12-20: chlandsi + [Python] #1357. Fix overriding __new__ in Python 3.6. + + Fixes SystemError: Objects/tupleobject.c:81: bad argument to internal function" + +2018-12-16: wsfulton + [Python] #848 #1343 The module import logic has changed to stop obfuscating real ImportError + problems. Only one import of the low-level C/C++ module from the pure Python module is + attempted now. Previously a second import of the low-level C/C++ module was attempted + after an ImportError occurred and was done to support 'split modules'. A 'split module' is + a configuration where the pure Python module is a module within a Python package and the + low-level C/C++ module is a global Python module. Now a 'split module' configuration is + no longer supported by default. This configuration can be supported with a simple + customization, such as: + + %module(package="mypackage", moduleimport="import $module") foo + + or if using -builtin: + + %module(package="mypackage", moduleimport="from $module import *") foo + + instead of + + %module(package="mypackage") foo + + See the updated Python chapter titled "Location of modules" in the documentation. + +2018-12-11: tlby + [Perl] #1374 repair EXTEND() handling in typemaps + +2018-12-06: vadz + #1359 #1364 Add missing nested class destructor wrapper when the nested class is + inside a template. Removes associated bogus 'Illegal destructor name' warning. Only + occurred when the nested class' destructor is explicitly specified. + +2018-12-04: adr26 + [Python] #1368 #1369 Access Violation in tp_print caused by mismatched Python/extension + CRT usage + + Remove all use of tp_print, as this API uses a FILE*, which can be + mismatched when modules are built with different C libraries from + the main python executable. + + This change also brings consistent output between Python 2 and 3 for the 'cvar' SWIG + object (that contains the global variables) and SWIG packed objects (such as callback + constants). + +2018-12-04: wsfulton + [Python] #1282 Fix running 'python -m' when using 'swig -builtin' + + Similar to the earlier PEP 366 conforming fix for non-builtin. + +2018-11-29: adr26 + [Python] #1360 Leak of SWIG var link object + + Fix reference counting on _SWIG_globals to allow var link to be freed on module unload. + +2018-11-28: wsfulton + [Python] When using -builtin, the two step C-extension module import is now + one step and the wrapped API is only available once and not in an underlying + module attribute like it is without -builtin. To understand this, consider a + module named 'example' (using: %module example). The C-extension is compiled into + a Python module called '_example' and a pure Python module provides the actual + API from the module called 'example'. It was previously possible to additionally + access the API from the module attribute 'example._example'. The latter was an + implementation detail and is no longer available. It shouldn't have been used, but + if necessary it can be resurrected using the moduleimport attribute described in the + Python chapter of the documentation. If both modules are provided in a Python + package, try: + + %module(moduleimport="from . import _example\nfrom ._example import *") example + or more generically: + %module(moduleimport="from . import $module\nfrom .$module import *") example + + and if both are provided as global modules, try: + + %module(moduleimport="import _example\nfrom _example import *") example + or more generically: + %module(moduleimport="import $module\nfrom $module import *") example + + The module import code shown will appear in the example.py file. + +2018-11-24: vadz + #1358 Fix handling of abstract base classes nested inside templates + + Correct detecting of whether a derived class method overrides a pure virtual + base class method when both classes are nested inside a template class: this + notably didn't work correctly for methods taking parameters of the base class + type. + +2018-11-22: rupertnash + [Python] #1282 Make generated module runnable via python -m (PEP 366 conforming) + + Previously any SWIG generated modules in a package would fail with an ImportError + when using 'python -m' for example 'python -m mypkg.mymodule'. + + This fix also allows the SWIG generated module to be placed into a directory and + then renamed __init__.py to convert the module into a package again. This ability + stopped working in swig-3.0.9. However, only Python 2.7 or 3.3 and later work. If + Python 3.2 support is needed, use moduleimport in %module to customise the import + code. + +2018-11-13: wsfulton + #1340 Remove -cppcast and -nocppcast command line options (this was an option + available to the scripting language targets). + + The -cppcast option is still turned on by default. The -nocppcast option + to turn off the use of c++ casts (const_cast, static_cast etc) has been + removed. However, defining SWIG_NO_CPLUSPLUS_CAST will still generate C casts + instead of C++ casts for C++ wrappers. + + *** POTENTIAL INCOMPATIBILITY *** + +2018-11-13: wsfulton + [Python] #1340 Remove -outputtuple and -nooutputtuple command line options. + + Both the command line and %module options of the same name have been + removed. These were undocumented. The -outputtuple option returned a + Python tuple instead of a list, mostly typically in the OUTPUT + typemap implementations. + + It unclear why a tuple instead of a list return type is needed and + hence this option has been removed as part of the simplification of + the SWIG Python command line options for SWIG 4. + +2018-11-13: wsfulton + [Python] #1340 Remove -noproxyimport command line option. + + This option turned off the insertion of Python import statements + derived from a %import directive. For example given: + + %module module_b + %import "module_a.i" + + then module_b.py will contain: + + import module_a + + *** POTENTIAL INCOMPATIBILITY *** + +2018-10-29: AlexanderGabriel + [PHP] The following PHP7 reserved keywords are now only renamed by + SWIG when used as function names in the API being wrapper: + __halt_compiler array die echo empty eval exit include include_once + isset list print require require_once return unset + +2018-10-22: olly,wsfulton + [Python] #1261 #1340 Turn on many optimisation options by default and rationalise the + number of command line options. + + There were an unnecessary number of command line options and many of these have now + been removed in a drive for simplification. Some were needed to support older versions + of Python (2.6 and earlier). + + Many of the options could be turned on individually and when using -O. Previously -O + resulted in turning on a set of options: + + -modern -fastdispatch -nosafecstrings -fvirtual -noproxydel + -fastproxy -fastinit -fastunpack -fastquery -modernargs -nobuildnone + + Now -O results in turning on this reduced set: + + -fastdispatch -fastproxy -fvirtual + + The following options are now on by default, a deprecated warning is displayed if they + are used: + -fastinit Class initialisation code done in C/C++ rather than in Python code. + -fastquery Python dictionary used for lookup of types. + -fastunpack Faster unpacking of function arguments in C/C++ wrappers. + -modern Use Python 2.3 features such as object and property. + -modernargs Use Python 2.3 C APIs for unpacking arguments in tuples. + -noproxydel Stop generating a proxy __del__ method for backwards compatiblity. + -safecstrings No discernable difference + + The following options have been removed altogether: + -aliasobj0 + -buildnone + -classptr + -new_repr + -newrepr + -noaliasobj0 + -nobuildnone + -nocastmode + -nodirvtable + -noextranative + -nofastinit + -nofastproxy + -nofastquery + -nomodern + -nomodernargs + -nooutputtuple + -nosafecstrings + -old_repr + -oldrepr + -proxydel + + -new_vwm is no longer supported. Use the -newvwm alias instead. + + *** POTENTIAL INCOMPATIBILITY *** + +2018-10-22: olly + [Python] #1261 Remove command line option no longer needed as Python 2.3 and earlier + are no longer supported: + + -classic + +2018-10-09: wsfulton + [D, Go, Guile, Lua, Mzscheme, Ocaml, Perl5, Php, Scilab, Tcl] + Allow wrapping of std::map using non-default comparison function. + +2018-10-09: vadz + [Java] #1274 Allow wrapping of std::map using non-default comparison function. + +2018-10-04: wsfulton + [Python] #1126 Fix C default arguments with -builtin and -fastunpack and -modernargs. + Problem occurred when there is just one (defaulted) parameter in the parameter list. + +2018-09-24: wsfulton + [Python] #1319 C++11 hash tables implementation is finished now (including for -builtin): + std::unordered_map + std::unordered_set + std::unordered_multimap + std::unordered_multiset + +2018-09-21: wsfulton + [Python] Fix when using -builtin and wrapping std::map, std::set, std::unordered_map or + std::unordered_set to ensure __contains__ is called. This is a wrapper for the STL + container's find method. Without it, Python will do its own slower sequence search. + +2018-09-19: wsfulton + [Python] Fix functors (wrapped as __call__) when using -builtin -modern -fastunpack. + +2018-09-02: andreas.gaeer,tkrasnukha + [Python] #1321 Fix assert in PyTuple_GET_SIZE in debug interpreter builds of python-3.7 + when calling tp_new. + +2018-09-01: ChristopherHogan + [Guile] #1288 Fix garbage collection for guile >= 2.0.12. + +2018-08-31: wsfulton + [Python] #1319 C++11 hash tables support: + std::unordered_map + std::unordered_set + std::unordered_multimap + std::unordered_multiset + is now compiling and working (sorting using -builtin not fully functional yet though). + +2018-08-20: wkalinin + #1305 Fix nested structure symbol tables in C mode to fix member name conflicts + in different structs with the same nested struct member name. + +2018-08-18: wsfulton + [Python] #688 Fix makefile recursion when running python test-suite. + +2018-08-18: wsfulton + [Python] #1310 Re-implement Python -fastproxy option. + + The previous implementation failed with Python 3 and abstract base clases. + The new implementation replaces the Python 2 implementation using + new.instancemethod with the C API PyMethod_New to match the equivalent Python 3 + implementation which uses PyInstanceMethod_New. + + The new approach runs slightly faster. See #1310. + +2018-08-12: gmazzamuto + [Python] #1283 Update pybuffer.i library to use new-style Python buffer C API. + +2018-08-12: brianhatwood,wsfulton + [Java] #1303 #1304 Fix crash in directors when using OUTPUT and INOUT typemaps in typemaps.i and + passing NULL pointers in C++ to director method overloaded and implemented in Java. + +2018-08-10: wsfulton + [Python] #1293 Improve TypeError message inconsistencies between default and fastdispatch + mode when handling overloaded C++ functions. Previously the error message did not always + display the possible C/C++ prototypes in fastdispatch mode. + +2018-08-02: furylynx,jacobwgillespie,p2k + [Javascript] #1290, #968. Add support for NodeJS versions 2-10. + +2018-07-31: wsfulton + [Python] #1293 Overloaded C++ function wrappers now raise a TypeError instead + of NotImplementedError when the types passed are incorrect. This change means + there is now consistency with non-overloaded function wrappers which have always + raised TypeError when the incorrect types are passed. The error message remains + the same and is for example now: + + TypeError: Wrong number or type of arguments for overloaded function 'f'. + Possible C/C++ prototypes are: + f(int) + f(char const *) + + instead of: + + NotImplementedError: Wrong number or type of arguments for overloaded function 'f'. + Possible C/C++ prototypes are: + f(int) + f(char const *) + + *** POTENTIAL INCOMPATIBILITY *** + +2018-06-23: wsfulton + [Python] #718 Fix pythonnondynamic feature for modern classes + + Fixes nondynamic mode when an instance variable is set with the same + name as a class variable in a class derived from a SWIG proxy class. + This corner case set an instance variable instead of raising an AttributeError. + + Also fix %pythonnondynamic in Python 3 with -modern. The metaclass + containing the implementation was previously not being applied in Python 3. + +2018-07-17: petrmitrichev,wsfulton + [Python] #1275 #1279 Initialize function-local statics (singletons) that call Python + code during Python module initialization in order to avoid deadlocks with subsequent + multi-threaded usage. + +2018-06-15: wsfulton + [Python] Fix seg fault using Python 2 when passing a Python string, containing + invalid utf-8 content, to a wstring or wchar * parameter. A TypeError is thrown instead, eg: + + %include + void instring(const std::wstring& s); + + instring(b"h\xe9llooo") # Python + +2018-06-15: wsfulton + [Python] Python 3.7 support: Replace use of deprecated PyUnicode_GetSize with + PyUnicode_GetLength to remove deprecated warnings compiling the C/C++ wrappers. + +2018-06-12: wsfulton + [Python] Python 3.7 support: The %pythonabc feature in pyabc.i now uses base classes + collections.abc.MutableSequence + collections.abc.MutableMapping + collections.abc.MutableSet + instead of + collections.MutableSequence + collections.MutableMapping + collections.MutableSet + as the latter are deprecated in Python 3.7 and are due to be removed in Python 3.8. + The classes in collections.abc.* are available from Python 3.3 onwards. If you + require support for Python 3.2, then copy the pyabc.i file and modify by removing + the few instances of the .abc sub-module. + + *** POTENTIAL INCOMPATIBILITY *** + +2018-06-12: olly,wsfulton + [Python] #701 Remove support for Python versions < 2.7 and 3.0 and 3.1. + + *** POTENTIAL INCOMPATIBILITY *** + +2018-06-11: olly + [Python] Fix new GCC8 warnings in generated code by avoiding casts + between incompatible function types where possible, and by + suppressing the warning when it's due to the design of Python's C + API. Fixes #1259. + +2018-06-08: philippkraft + [Python] Stop exposing _swigregister to Python. It's not + useful for user Python code to call this, and it just clutters the + API unnecessarily. Fixes #1225. + +2018-06-07: cmfoil, kabbi, Jamie Kirkpatrick, markok314, vadz, wsfulton, Yann Diorcet + #170 Doxygen documentation support added. This allows translation of Doxygen comments + into JavaDoc and PyDoc documentation. It is enabled via the -doxygen command line + option. See the Doxygen.html chapter in the documentation for further information. + +2018-06-07: olly + [PHP] We've finally removed support for %pragma(php4) which was + deprecated back in 2008. Use %pragma(php) instead, which has been + supported since at least 2005. + + *** POTENTIAL INCOMPATIBILITY *** + +2018-06-07: olly + [PHP5] Support for PHP5 has been removed. PHP5 is no longer + actively supported by the PHP developers and security support for + it ends completely at the end of 2018, so it doesn't make sense + to include support for it in the upcoming SWIG 4.0.0 release. + + *** POTENTIAL INCOMPATIBILITY *** + +2018-06-06: olly + [Lua] Improve configure probes for Lua headers and libs used in testsuite. + +2018-05-15: kwwette + [Octave] add support for version 4.4 + - Should not introduce any user-visible incompatibilities + +2018-05-15: wsfulton + [C#, D, Java] Fix lookup of csconstruct, dconstruct and javaconstruct typemaps. + The C++ namespace was previously ignored when looking up the typemap. + +2018-05-15: wsfulton + [Javascript] Fix generated C++ code when using %nspace on namespaces that are more + than two levels deep. + +2018-05-14: wsfulton + Issue #1251 Add support for C++17 nested namespace definitions, + for example: + namespace A::B { ... } + +2018-05-11: wsfulton + [C#, D, Java] Add support so that the %csmethodmodifiers, %dmethodmodifiers, + %javamethodmodifiers can modify the method modifiers for the destructor wrappers + in the proxy class: dispose, Dispose, delete. With this feature, it is now possible + to make a C# proxy class sealed, eg when wrapping a class X, the virtual method modifiers + can be removed using: + + %typemap(csclassmodifiers) X "public sealed class" + %csmethodmodifiers X::~X "public /*virtual*/"; + +2018-04-18: olly + [Python] Suppress new pycodestyle warning: + E252 missing whitespace around parameter equals + +2018-04-07: goatshriek + [Ruby] #1213 Fix ruby %alias directive for global C/C++ functions. + +2018-04-03: olly + [Ruby] Fix to pass Qnil instead of NULL to rb_funcall(), which silences GCC + -Wconversion-null warning (on by default with recent GCC). + +2018-03-09: wsfulton + [Java] #1184 Fix swigReleaseOwnership() and swigTakeOwnership() regression + for non-director classes. Restores a dynamic_cast which was previously removed. + +2018-03-07: llongi + Github PR #1166 - Fix preprocessor handling of macros with commas + in a // comment. + +2018-02-18: JPEWdev + Patch #1164 - Add support for a command-line options file, also sometimes + called a response file. This is useful if the command-line options exceed + the system command-line length limit. To use, put the command-line options + into a file, then provide the file name prefixed with @, for example using + a file called args.txt: + + swig @args.txt + +2018-02-11: wsfulton + [Javascript] #1187 Fix compilation error wrapping std::complex via + std_complex.i. + +2018-01-30: smarchetto + [Scilab] add type name argument in SWIG_ptr() function to cast from pointer address to typed pointers + +2018-01-16: wsfulton + Expressions following a preprocessor directive must now be separated by whitespace + or non-numeric characters. This syntax change makes the SWIG preprocessor work like + the C preprocessor in this area. + + For example, the following code used be accepted as valid syntax: + #if1 + #define ABC 123 + #endif + + Now you get an error: + example.h:1: Error: Unknown SWIG preprocessor directive: if1 (if this is a block of + target language code, delimit it with %{ and %}) + example.h:3: Error: Extraneous #endif. + + The following is the correct syntax: + #if 1 + #define ABC 123 + #endif + + The following of course also works: + #if(1) + #define ABC 123 + #endif + + *** POTENTIAL INCOMPATIBILITY *** + +2018-01-15: wsfulton + Fix issue #1183. Floating point exception evaluating preprocessor expressions + resulting in division by zero. + +2018-01-14: wsfulton + Fix issue #1172. Seg fault parsing invalid exponents in the preprocessor. + +2018-01-12: Liryna + [C#] Patch #1128. Add ToArray function to std::vector wrappers. + +2018-01-12: wsfulton + [Java] Fix issue #1156. Add missing throws clause for interfaces when using the + %interface family of macros. + +2018-01-05: wsfulton + Fix default arguments using expressions containing -> syntax error. Problem reported on + swig-user mailing list. + +2017-12-30: wsfulton + [Python] Replace pep8 with pycodestyle for checking the Python code style when + running Python tests. + +2017-12-30: davedissian + Fixed a symbol lookup issue when encountering a typedef of a symbol from the tag + namespace to the global namespace when the names are identical, such as 'typedef + struct Foo Foo;'. + +2017-12-13: wsfulton + [Perl] add missing support for directorfree typemaps. + +2017-12-13: wsfulton + Issue #1167 Fix directorout typemaps which were causing undefined behaviour when + returning pointers by reference. + +2017-12-08: olly + [PHP] Use ZEND_MODULE_GLOBALS_ACCESSOR to access globals - this + should make the generated code work with PHP 7.2.0. + +2017-12-04: wsfulton + [Python] Add missing checks for failures in calls to PyUnicode_AsUTF8String. Previously a + seg fault could occur when passing invalid UTF8 strings (low surrogates), eg passing + u"\udcff" to the C layer (Python 3). + +2017-11-24: joequant + [R] Fix #1124 and return R_NilValue for null pointers + +2017-11-29: wsfulton + [Java] director exception handling improvements. + + When a director method throws an exception and it is caught by DirectorException + and passed back to Java using Swig::DirectorException::throwException, the Java + stack trace now contains the original source line that threw the exception. + + Deprecate Swig::DirectorException::raiseJavaException, please replace usage with + Swig::DirectorException::throwException. + + *** POTENTIAL INCOMPATIBILITY *** + +2017-10-26: wsfulton + Add support for C++11 ref-qualifiers when using directors. + +2017-10-26: wsfulton + Fix generated code when using directors and methods returning const ref pointers. + +2017-10-26: wsfulton + [C#, D, Java, Octave, R, Scilab] Port director typemaps to these additional languages. + Issue #700. + +2017-10-26: radarsat1 + [Ruby Python] Patch #1029 - Correct handling of null using directors and shared_ptr. + +2017-10-10: joequant + [R] pass enum expressions to R. This will generate + incorrect files when there is an arithmetic expression + in the enum, but this is better than silently generating + incorrect code + +2017-10-09: olly + [PHP] Fix incorrect wrapper code generated when there's a + combination of overloading, parameters with a default value + and %newobject. Fixes https://sourceforge.net/p/swig/bugs/1350/ + +2017-10-09: olly + Remove GCJ support. It isn't in a good state and doesn't seem to + be used, and GCC7 dropped GCJ. Closes + https://sourceforge.net/p/swig/bugs/823/ + +2017-10-07: olly + Fix preprocessor handling of empty macro arguments to match that of + C/C++ compilers. Fixes issue #1111 and + https://sourceforge.net/p/swig/bugs/826/ + +2017-10-06: wsfulton + [Python] Issue #1108. Fix platform inconsistency in Python default argument handling. + 32 bit and 64 bit compiled versions of SWIG generated different Python files + when default arguments were outside the range of 32 bit signed integers. + The default arguments specified in Python are now only those that are in the + range of a 32 bit signed integer, otherwise the default is obtained from C/C++ code. + +2017-10-02: wsfulton + [C#] Fix std::complex types passed by value. + +2017-10-02: wsfulton + [Javascript, Python, Ruby] Issue #732 - Missing type information for std::complex + in std_complex.i meant that previously std::complex always had to be fully qualified + in order to be wrapped with the appropriate typemaps. + +2017-10-01: joequant + allow R package names with docs + allowing multiple get accessors in R + fix smart-pointer and NAMESPACE support + constructors now returning smart pointers (if class + declared as such) + smart-pointer classes deriving from parent smart-pointers + +2017-09-29: wsfulton + Issue #1100 - Allow an instantiated template to have the same name in the target + language as the C++ template name, for example, this is now possible: + + template struct X { ... }; + %template(X) X; + +2017-09-23: wsfulton + Issue #1098. Fix overloading of shared_ptr with underlying pointer types, eg: + + void m(std::shared_ptr p); + void m(T &p); + void m(T *p); + + Only the first method is wrapped and the others are ignored/shadowed. + The implementation is done via a new attribute in the 'typecheck' typemap called + 'equivalent'. If specified, it must contain the equivalent pointer type for overloading + and can only be used for the special SWIG_TYPECHECK_POINTER precedence level. + The shared_ptr 'typecheck' typemaps have been modified accordingly. + Here is a simplified version: + + %typemap(typecheck, precedence=SWIG_TYPECHECK_POINTER, equivalent="T *") + T, + T CONST &, + T CONST *, + T *CONST&, + std::shared_ptr< T >, + std::shared_ptr< T > &, + std::shared_ptr< T > *, + std::shared_ptr< T > *& + { ... } + + Overloading with any of these types will result in SWIG ignoring all but the first + overloaded method by default. Without the 'equivalent' attribute, wrapping the overloaded + methods resulted in types being shadowed (scripting languages) or code that did not + compile (statically typed languages). + +2017-09-19: futatuki + [Python] #1003 Add --with-2to3=/path/to/2to3 option to configure. + +2017-09-18: wsfulton + Fix type promotion wrapping constant expressions of the form: + # define EXPR_MIXED1 (0x80 + 11.1) - 1 + This was previously an integral type instead of a floating point type. + +2017-09-17: wsfulton + Fix generated code for constant expressions containing wchar_t L literals such as: + # define __WCHAR_MAX (0x7fffffff + L'\0') + # define __WCHAR_MIN (-__WCHAR_MAX - 1) + +2017-09-10: mlamarre + [Python] Patch #1083. Define_DEBUG to 1 to do exactly like Visual Studio + /LDd, /MDd or /MTd compiler options. + +2017-08-25: wsfulton + Issue #1059. Add support for C++11 ref-qualifiers on non-static member functions. + Members with lvalue ref-qualifiers such as: + + struct RQ { + void m1(int x) &; + void m2(int x) const &; + }; + + are wrapped like any other member function. Member functions with rvalue ref-qualifiers + are ignored by default, such as: + + struct RQ { + void m3(int x) &&; + void m4(int x) const &&; + }; + + example.i:7: Warning 405: Method with rvalue ref-qualifier m3(int) && ignored. + example.i:8: Warning 405: Method with rvalue ref-qualifier m4(int) const && ignored. + + These can be unignored and exposed to the target language, see further documentation in + CPlusPlus11.html. + +2017-08-16: wsfulton + Fix #1063. Add using declarations to templates into typedef table. + + Using declarations to templates were missing in SWIG's internal typedef tables. + This led to a few problems, such as, templates that did not instantiate and generated + C++ code that did not compile as SWIG did not know what scope the template was + in. This happened mostly when a using declaration was used on a template type in a + completely unrelated namespace. + +2017-08-16: wsfulton + Fix type lookup in the presence of using directives and using declarations. + + Fix some cases of type lookup failure via a combination of both using directives and + using declarations resulting in C++ code that did not compile as the generated type was + not fully qualified for use in the global namespace. Example below: + + namespace Space5 { + namespace SubSpace5 { + namespace SubSubSpace5 { + struct F {}; + } + } + using namespace SubSpace5; + using SubSubSpace5::F; + void func(SubSubSpace5::F f); + } + +2017-08-16: wsfulton + Issue #1051. %template scope enforcement and class definition fixes. + + The scoping rules around %template have been specified and enforced. + The %template directive for a class template is the equivalent to an + explicit instantiation of a C++ class template. The scope for a valid + %template instantiation is now the same as the scope required for a + valid explicit instantiation of a C++ template. A definition of the + template for the explicit instantiation must be in scope where the + instantiation is declared and must not be enclosed within a different + namespace. + + For example, a few %template and C++ explicit instantiations of std::vector + are shown below: + + // valid + namespace std { + %template(vin) vector; + template class vector; + } + + // valid + using namespace std; + %template(vin) vector; + template class vector; + + // valid + using std::vector; + %template(vin) vector; + template class vector; + + // ill-formed + namespace unrelated { + using std::vector; + %template(vin) vector; + template class vector; + } + + // ill-formed + namespace unrelated { + using namespace std; + %template(vin) vector; + template class vector; + } + + // ill-formed + namespace unrelated { + namespace std { + %template(vin) vector; + template class vector; + } + } + + // ill-formed + namespace unrelated { + %template(vin) std::vector; + template class std::vector; + } + + When the scope is incorrect, an error now occurs such as: + + cpp_template_scope.i:34: Error: 'vector' resolves to 'std::vector' and + was incorrectly instantiated in scope 'unrelated' instead of within scope 'std'. + + Previously SWIG accepted the ill-formed examples above but this led to + numerous subtle template scope problems especially in the presence of + using declarations and using directives as well as with %feature and %typemap. + + Actually, a valid instantiation is one which conforms to the C++03 + standard as C++11 made a change to disallow using declarations and + using directives to find a template. + + // valid C++03, ill-formed C++11 + using std::vector; + template class vector; + + Similar fixes for defining classes using forward class references have + also been put in place. For example: + + namespace Space1 { + struct A; + } + namespace Space2 { + struct Space1::A { + void x(); + } + } + + will now error out with: + + cpp_class_definition.i:5: Error: 'Space1::A' resolves to 'Space1::A' and + was incorrectly instantiated in scope 'Space2' instead of within scope 'Space1'. + + Previously some symbols would have been instantiated in the wrong scope and led + to lots of scope problems involving SWIG typemaps, features, renames etc. + You will need to correct the scope used in other SWIG directives which do not + support 'using declarations' and 'using directives'. For example, if you previously had: + + %rename(Zap) vector::clear; + using namespace std; + %template(VectorInt) vector; + + Prior versions of SWIG incorrectly instantiated vector in the global namespace + and so the %rename matched. Now the template is instantiated in the correct namespace, + so is fully qualified as std::vector. The other SWIG directives need correcting as + they do not follow 'using declarations' and 'using directives'. Change it to: + + %rename(Zap) std::vector::clear; + using namespace std; + %template(vin) vector; + + + *** POTENTIAL INCOMPATIBILITY *** + +2017-08-16: wsfulton + Fix scope lookup for template parameters containing unary scope operators. + + Fixes cases like: + + namespace Alloc { + template struct Rebind { + typedef int Integer; + }; + } + %template(RebindBucket) Alloc::Rebind< Bucket >; + OR + %template(RebindBucket) Alloc::Rebind< ::Bucket >; + + Alloc::Rebind< Bucket >::Integer Bucket1(); + Alloc::Rebind< ::Bucket >::Integer Bucket2(); + Alloc::Rebind<::template TemplateBucket>::Integer Bucket3(); + +2017-08-16: wsfulton + For templates only, the template parameters are fully resolved when + handling typemaps. Without this, it is too hard to have decent rules + to apply typemaps when parameter types are typedef'd and template + parameters have default values. + + Fixes %clear for typedefs in templates, eg: + + %typemap("in") XXX::Long "..." + template typename struct XXX { + typedef long Long; + }; + %clear XXX::Long; + + as the typemap was previously incorrectly stored as a typemap for long + instead of XXX::Long. + +2017-08-05: olly + [C++11] Allow static_assert at the top level (and disallow it right + after template). Fixes issue 1031 reported by Artem V L. + +2017-08-02: wsfulton + Fix incorrectly shown warning when an empty template instantiation was used on a + class used as a base class and that base class was explicitly ignored with %ignore. + Example of the warning which will no longer appear: + + Warning 401: Base class 'Functor< int,int >' has no name as it is an empty + template instantiated with '%template()'. Ignored. + +2017-07-17: fflexo + [Java] #674 Add std_list.i to add support for std::list containers. The Java proxy + extends java.util.AbstractSequentialList and makes the C++ std::list container look + and feel much like a java.util.LinkedList from Java. + +2017-07-07: wsfulton + [Python] Fix display of documented template types when using the autodoc + feature. For example when wrapping: + + %feature("autodoc"); + template struct T {}; + %template(TInteger) T; + + the generated documentation contains: + """Proxy of C++ T< int > class.""" + instead of: + """Proxy of C++ T<(int)> class.""" + and + """__init__(TInteger self) -> TInteger""" + instead of + """__init__(T<(int)> self) -> TInteger""" + +2017-06-27: nihaln + [PHP] Update the OUTPUT Typemap to add return statement to the + PHP Wrapper. + +2017-06-27: nihaln + [PHP] Update the enum and value examples to use the OO wrappers + rather than the flat functions produced with -noproxy. There's + not been a good reason to use -noproxy for since PHP5 OO wrapping + was fixed back in 2005. + +2017-06-23: m7thon + [Python] fix and improve default argument handling: + + 1. Fix negative octals. Currently not handled correctly by `-py3` + (unusual case, but incorrect). + 2. Fix arguments of type "octal + something" (e.g. `0640 | 04`). + Currently drops everything after the first octal. Nasty! + 3. Fix bool arguments "0 + something" (e.g. `0 | 1`) are always + "False" (unusual case, but incorrect). + 4. Remove special handling of "TRUE" and "FALSE" from + `convertValue` since there's no reason these have to match + "true" and "false". + 5. Remove the Python 2 vs. Python 3 distinction based on the + `-py3` flag. Now the same python code is produced for default + arguments for Python 2 and Python 3. For this, octal default + arguments, e.g. 0644, are now wrapped as `int('644', 8)`. This + is required, as Python 2 and Python 3 have incompatible syntax + for octal literals. + + Fixes #707 + +2017-06-21: futatuki + #1004 - Fix ccache-swig executable name to respect configure's --program-prefix and + --program-suffix values if used. + +2017-06-21: tamuratak + [Ruby] #911 - Add std::wstring support. + +2017-06-19: wsfulton + [Python] Fix handling of rich comparisons when wrapping overloaded operators: + + operator< operator<= operator> operator>= operator== operator!= + + Previously a TypeError was always thrown if the type was not correct. NotImplemented + is now returned from these wrapped functions if the type being compared with is + not correct. The subsequent behaviour varies between different versions of Python + and the comparison function being used, but is now consistent with normal Python + behaviour. For example, for the first 4 operator overloads above, a TypeError + 'unorderable types' is thrown in Python 3, but Python 2 will return True or False. + NotImplemented should be returned when the comparison cannot be done, see PEP 207 and + https://docs.python.org/3/library/constants.html#NotImplemented + + Note that the bug was only present when overloaded operators did not also have a + function overload. + + Fixes SF bug #1208 (3441262) and SF patch #303. + + *** POTENTIAL INCOMPATIBILITY *** + +2017-06-17: fabrice102 + [Go] Fix Go callback example. Fixes github #600, #955, #1000. + +2017-06-16: wsfulton + Make sure warning and error messages are not split up by other processes writing to + stdout at the same time. + +2017-06-16: wsfulton + [R] Fix wrapping function pointers containing rvalue and lvalue reference parameters. + +2017-06-13: olly + [Perl] Fix testsuite to work without . in @INC - it was removed in + Perl 5.26 for security reasons, and has also been removed from + older versions in some distros. Fixes #997 reported by lfam. + +2017-06-03: wsfulton + Fix %import on a file containing a file scope %fragment forced inclusion to not + generate the fragment contents as %import should not result in code being generated. + The behaviour is now the same as importing code insertion blocks. + Wrapping FileC.i in the following example will result in no generated code, whereas + previously "#include " was generated: + + // FileA.i + %fragment("", "header") %{ + #include + %} + + %{ + #include + %} + %fragment(""); + + // FileC.i + %import "FileA.i" + + *** POTENTIAL INCOMPATIBILITY *** + +2017-05-26: Volker Diels-Grabsch, vadz + [Java] #842 Extend from java.util.AbstractList<> and implement java.util.RandomAccess for + std::vector wrappers. This notably allows to iterate over wrapped vectors in a natural way. + Note that boxed types are now used in the Java layer when wrapping vector of C primitive + types, for example. This may introduce some subtle incompatibilities due to some + differences in how Java converts boxed types and unboxed types. For example, + + int i=0; + double d1 = i; // ok + Double d2 = i; // error: incompatible types: int cannot be converted to Double + + This can be a problem when calling the add and set functions. A suggested backwards + compatible workaround is to use something like (shown for std::vector: + + #if defined(SWIGJAVA) + // Add in old api that uses non-boxed types + %extend std::vector { + %proxycode %{ + public void add(double x) { + add(Double.valueOf(x)); + } + public void set(int i, double val) { + set(i, Double.valueOf(val)); + } + %} + } + #endif + + %include "std_vector.i" + %template(VectorDouble) std::vector; + + *** POTENTIAL INCOMPATIBILITY *** + +2017-05-30: davidcl + [Scilab] #994 Undefined symbol error when loading in Scilab 6 + +2017-05-25: asibross + [Java] #370 #417 Missing smart pointer handling in Java director extra methods + swigReleaseOwnership() and swigTakeOwnership(). + +2017-05-23: wsfulton + [Java] #230 #759 Fix Java shared_ptr and directors for derived classes java compilation + error. + + For shared_ptr proxy proxy classes, add a protected method swigSetCMemOwn for modifying + the swigCMemOwn and swigCMemOwnDerived member variables which are used by various other + methods for controlling memory ownership. + +2017-05-21: Sghirate + [Java, C#, D] #449 Remove unnecessary use of dynamic_cast in directors to enable + non-RTTI compilation. + +2017-05-21: wsfulton + [Python] #993 Fix handling of default -ve unsigned values, such as: + void f(unsigned = -1U); + +2017-05-20: jschueller + [Python] #991 Fix E731 PEP8 warning: do not assign a lambda expression + +2017-05-16: nihal95 + [PHP] Add %pragma version directive to allow the version of the + extension to be set. Patch #970, fixes #360. + +2017-05-13: yag00 + Patch #975 - Add support for noexcept on director methods. + +2017-04-27: redbrain + Issue #974, Patch #976 - Fix preprocessor handling of macros with commas in a comment. + +2017-04-25: jleveque + [Lua] #959 - Fix Visual Studio C4244 conversion warnings in Lua wrappers. + +2017-04-21: tamuratak + [Ruby] #964 - Add shared_ptr director typemaps. + +2017-04-20: wsfulton + [Ruby] #586, #935 Add assert for invalid NULL type parameter when calling SWIG_Ruby_NewPointerObj. + +2017-04-20: tamuratak + [Ruby] #930, #937 - Fix containers of std::shared_ptr. + Upcasting, const types (eg vector>) and NULL/nullptr support added. + +2017-04-12: smarchetto + [Scilab] New parameter targetversion to specify the Scilab target version (5, 6, ..) for code generation + With Scilab 6 target specified, identifier names truncation is disabled (no longer necessary) + +2017-03-24: tamuratak + [Ruby] Fix #939 - Wrapping std::vector fix due to incorrect null checks + on VALUE obj. + +2017-03-17: vadz + [C#] #947 Add support for std::complex + +2017-03-17: wsfulton + [Go] Fix handling of typedef'd function pointers and typedef'd member function pointers + such as: + + typedef int (*FnPtr_td)(int, int); + int do_op(int x, int y, FnPtr_td op); + +2017-03-16: wsfulton + Add support for member const function pointers such as: + + int fn(short (Funcs::* parm)(bool)) const; + + Also fix parsing of references/pointers and qualifiers to member + pointers such as: + + int fn(short (Funcs::* const parm)(bool)); + int fn(short (Funcs::* & parm)(bool)); + +2017-03-10: wsfulton + Extend C++11 alternate function syntax parsing to support const and noexcept, such as: + + auto sum1(int x, int y) const -> int { return x + y; } + auto sum2(int x, int y) noexcept -> int { return x + y; } + +2017-02-29: tamuratak + [Ruby] #917 - Add Enumerable module to all container class wrappers. It was missing + for std::list, std::multiset, std::unordered_multiset and std::unordered_map. + +2017-02-27: assambar + [C++11] Extend parser to support throw specifier in combination + with override and/or final. + +2017-02-10: tamuratak + [Ruby] #883 - Add support for C++11 hash tables: + std::unordered_map + std::unordered_set + std::unordered_multimap + std::unordered_multiset + +2017-02-08: jcsharp + [C#] #887 Improve std::vector wrapper constructors - + Replace constructor taking ICollection with IEnumerable and also add IEnumerable + constructor to avoid the boxing and unboxing overhead of the original constructor, + when the type parameter is a value type. + Version 3.0.12 (27 Jan 2017) ============================ diff --git a/CHANGES.current b/CHANGES.current index 6ead3a621..06373dbea 100644 --- a/CHANGES.current +++ b/CHANGES.current @@ -4,1537 +4,6 @@ See the RELEASENOTES file for a summary of changes in each release. Issue # numbers mentioned below can be found on Github. For more details, add the issue number to the end of the URL: https://github.com/swig/swig/issues/ -Version 4.0.0 (27 Apr 2019) +Version 4.0.1 (in progress) =========================== -2019-04-24: vadz - #1517 Fix crash if "@return" Doxygen tag was used on a node without any return type. - -2019-04-24: vadz - #1515 Fix parsing of enums with trailing comma when using -doxygen. - -2019-04-19: ianlancetaylor - [Go] #1055 When generating Go code, make -cgo the default. Add new -no-cgo option - to disable the default. - -2019-04-19: pbecherer - [Tcl] #1508 Fix Visual Studio 2015 and later compilation errors due to snprintf macro - definition. - -2019-04-09: wsfulton - [C#] Fix FxCop warning CA2002 in SWIGPendingException - a lock on a reference of - type 'Type'. - -2019-03-30: wsfulton - [Java, D] Add the parameters typemap attribute to the javadestruct, - javadestruct_derived, ddispose, ddispose_derived typemaps to mirror enhanced - flexibility in the csdisposing and csdisposing_derived (C#) typemaps. If provided - the contents are generated as the delete/dispose method's parameters declaration. - -2019-03-30: wsfulton - [C#] #421 Fix FxCop warning CA1063 by implementing the recommended Dispose methods for - the IDisposable interface. Previously just the Dispose() method was generated. - Now the Dispose() and Dispose(bool disposing) methods are generated. - Changes are required if custom "csfinalize", "csdestruct" or "csdestruct_derived" - typemaps are being used. Details in #421 on Github. SWIG will error out if one of - the "csfinalize, "csdestruct" or "csdestruct_derived" typemaps are found. Example - error message: - - foo.h:60: Error: A deprecated csfinalize typemap was found for Foo, please remove - it and replace all csdestruct, csdestruct_derived and csfinalize typemaps by the - csdispose, csdispose_derived, csdisposing and csdisposing_derived typemaps. - - *** POTENTIAL INCOMPATIBILITY *** - -2019-03-25: Liryna - [C#] #1143 Add std_list.i for std::list support. - The C# std::list wrappers are made to look and feel like a C# - System.Collections.Generic.LinkedList<> collection. - The IEnumerable<> interface is implemented in the proxy class. - The ICollection<> interface can also be implemented to provide enhanced functionality - whenever a C++ operator== is available. This is the case for when T is a - primitive type or a pointer. If T does define an operator==, then use the - SWIG_STD_LIST_ENHANCED macro to obtain this enhanced functionality, for example: - - SWIG_STD_LIST_ENHANCED(SomeNamespace::Klass) - %template(ListKlass) std::list; - -2019-03-18: richardbeare - [R] #1328 Non-trivial enums are working now. The enum values are now obtained from - the C/C++ layer. const reference enums and C++11 enum classes are also now working. - -2019-03-14: mochizk - [Javascript] #1500 Fix compilation errors due to deprecating V8 API in Node.js. - New V8 API is used if node.js >= v10.12, or if V8 >= v7.0. - -2019-03-12: vadz - [C#] #1495 Add std_set.i for std::set support. - -2019-03-11: dirteat,opoplawski - [Octave] Fix compilation errors in Octave 5.1. - - error: format not a string literal and no format arguments [-Werror=format-security] - -2019-02-28: wsfulton - [Java] std::vector improvements for types that do not have a default constructor. - - The std::vector wrappers have been changed to work by default for elements that are - not default insertable, i.e. have no default constructor. This has been achieved by - not wrapping: - - vector(size_type n); - - Previously the above had to be ignored via %ignore. - - If the above constructor is still required it can be added back in again via %extend: - - %extend std::vector { - vector(size_type count) { return new std::vector< T >(count); } - } - - Alternatively, the following wrapped constructor could be used as it provides near-enough - equivalent functionality: - - vector(jint count, const value_type& value); - - *** POTENTIAL INCOMPATIBILITY *** - -2019-02-25: wsfulton - [Python] Fix compile errors wrapping overloaded functions/constructors where a vararg - function is declared after a non-vararg function. - -2019-02-23: zphensley42 - Use fully qualified name 'java.lang.Object' instead of 'Object' in generated code to - avoid clashes with wrapped C++ classes called 'Object'. - -2019-02-23: gtbX - [Java] #1035 Add (const char *STRING, size_t LENGTH) typemaps in addition to the non-const - typemaps (char *STRING, size_t LENGTH) which does not attempt to write back to the const - string. - -2019-02-22: tamuratak - [Ruby] #984 Add support for RTypedData introduced in Ruby 1.9.3. - -2019-02-22: ZackerySpytz - #1483 Fix compilation failures when a director class has final methods. - -2019-02-21: wsfulton - [Java] #1240 Suppress Java 9 deprecation warnings on finalize method. - -2019-02-21: ZackerySpytz - #1480 Fix some rejections of valid floating-point literals. - -2019-02-19: wsfulton - #1475 Fix regression parsing gcc preprocessor linemarkers in the form: - - # linenum filename flags - -2019-02-18: jakecobb - [Python] #945 #1234 Elements in std::vector memory access fix. - - Accessing an element in a std::vector obtains a reference to the element via an - iterator pointing to the element in the container. If the vector is garbage collected, - the SWIG wrapper containing the pointer to the element becomes invalid. The fix is - to obtain a back-reference to the container by the wrapper to the element in the Python - layer to prevent the garbage collector from destroying the underlying container. - -2019-02-17: wsfulton - Fix typemap matching to expand template parameters when the name contains - template parameters. In the %typemap below the type is T and the name is X::make - and the name now expands correctly to X< int >::make - - template struct X { - %typemap(out) T X::make "..." - T make(); - }; - - %template(Xint) X; - -2019-02-16: wsfulton - Fix parser error containing multiple #define statements inside an enum. - - The second #define fails to parse: - - enum FooEnum { - ENUM1 = 0, - ENUM2 = 1, - - #define MACRO_DEF1 "Hello" - #define MACRO_DEF2 "World!" - - ENUM3 = 2, - ENUM4 = 3, - }; - - Bug mentioned at https://sourceforge.net/p/swig/patches/333/ - -2019-02-14: wsfulton - Add some missing copy constructors into STL containers. - -2019-02-14: bkotzz - [Java] #1356 Add STL containers: - std::unordered_map - std::unordered_set - std::set - -2019-02-14: bkotzz - [Java] #1356 std::map wrappers have been modified. Now the Java proxy class - extends java.util.AbstractMap. The std::map container looks and feels much like - a java.util.HashMap from Java. - - A few members have changed their names. If the old method signatures are needed, - then copy std_map.i from swig-3.0.12 and use that instead. Alternatively, - add the old missing methods to the new methods by using the following %proxycode: - - %extend std::map { - %proxycode %{ - // Old API - public boolean empty() { - return isEmpty(); - } - public void set($typemap(jboxtype, K) key, $typemap(jboxtype, T) x) { - put(key, x); - } - public void del($typemap(jboxtype, K) key) { - remove(key); - } - public boolean has_key($typemap(jboxtype, K) key) { - return containsKey(key); - } - %} - } - - *** POTENTIAL INCOMPATIBILITY *** - -2019-02-13: ZackerySpytz - #1469 Add support for C++17 hexadecimal floating literals. - -2019-02-11: wsfulton - [OCaml] #1437 OCaml has been give the 'Experimental' language status. The examples work - and most of the test-suite is also working, so it is quite close to being a 'Supported' language. - -2019-02-10: ZackerySpytz - #1464 Add support for C++14 binary integer literals. - -2019-02-10: ZackerySpytz - #1450 Add support for C++11 UCS-2 and UCS-4 character literals. Also, add support for - C++17 UTF-8 character literals. - -2019-02-10: wsfulton - [MzScheme] #1437 MzScheme/Racket is now an 'Experimental' language. The examples work - and a large portion of the test-suite is also working. - -2019-02-10: wsfulton - [MzScheme] Destructor wrappers were not being generated. - -2019-02-10: wsfulton - [MzScheme] Static variable wrappers fixed - $argnum was not expanded. - -2019-02-10: sethrj - #1452 Fix %apply for anonymous template instantiations - -2019-02-09: olly - [PHP] Fix access to already released memory during PHP module - shutdown, which often didn't cause visible problems, but could - result in segmentation faults, bus errors, etc. Fixes #1170, - reported by Jitka Plesníková. - -2019-02-09: olly - [PHP] A renamed constructor is now wrapped as a static method in - PHP. - -2019-02-08: olly - [PHP] Don't generate code which references $r when $r hasn't been - defined. This could happen in overloaded methods which returned - void and took at least one const std::string& parameter. - -2019-02-08: olly - [PHP] The generated code is now compatible with PHP 7.3, and the - testsuite now runs cleanly with this version too. - -2019-02-05: wsfulton - #1437 SWIG now classifies the status of target languages into either 'Experimental' or - 'Supported'. This status is provided to indicate the level of maturity to expect when using - a particular target language as not all target languages are fully developed. Details are - in the Introduction.html chapter of the documentation. - -2019-02-04: wsfulton - [CFFI] #1447 Common Lisp CFFI has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-04: wsfulton - [Allegrocl] #1447 Allegro Common Lisp has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-04: wsfulton - [Chicken] #1447 CHICKEN has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-04: wsfulton - [CLISP] #1447 GNU Common Lisp has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-04: wsfulton - [S-EXP] #1447 Common Lisp S-Exp has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-04: wsfulton - [UFFI] #1447 Common Lisp UFFI has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-04: wsfulton - [Pike] #1447 Pike has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-04: wsfulton - [Modula3] #1447 Modula3 has been disabled as a target language in SWIG as part of a - clean up to remove target languages that have been neglected/not functional. - -2019-02-02: ahnolds - [Python] Documentation enhancements for Python: - - #728 Fixed the handling of autodoc when using -fastproxy. - - #1367 Added documentation to wrapped member variables using the - property(... doc="...") construct. - - Only show a single documentation entry for functions with default arguments when - using autodoc. - - Fixed a bug where a cached doxygen docstring could be deleted while still in use, - causing swig to segfault. - -2019-01-31: olly - SWIG now requires a target language to be specified instead of - defaulting to wrapping for Tcl. Specifying swig --help without - a target language now just shows the generic help. The -nolang - option has been removed. - -2019-01-28: ZackerySpytz - [OCaml] #1429 Remove support for OCaml versions < 3.12.0. - - *** POTENTIAL INCOMPATIBILITY *** - -2019-01-22: vadz - [Ruby, Octave] #1424 Improve autodoc parameter naming. - -2019-01-22: vadz - [Python] #1271 #1423 Always include default parameter values in autodoc strings. - -2019-01-19: vadz - #1272, #1421 When a function's parameter is a keyword, the name of the paramater is - no longer simply changed to argN, where N is the argument number. Instead the - parameter name is changed to the renaming rules for keywords that normally apply to - symbols such as classes/functions etc. Note that unlike other symbol renaming, - parameter renaming does not issue a warning when the parameter is renamed. This - change only affects languages where the parameter names are actually used, for example, - Java function parameter lists in the proxy class or Python documentation comments. - -2019-01-18: wsfulton - #1420 Fix gdb debugger functions 'swigprint' and 'locswigprint' from swig.gdb to - work with newer versions of gdb-8. Fixes errors when debugging SWIG source with gdb: - - (gdb) swigprint n - Undefined command: "Printf". Try "help". - -2019-01-16: wsfulton - Python static method wrapper changes - - - Static method wrappers were using the 'fastproxy' approach by default. - This is inconsistent with instance method wrappers. The fastproxy approach - is now turned off by default to be consistent with instance methods. - Static method wrappers can now also be controlled using the -fastproxy and - -olddefs options. - - Example: - - struct Klass { - static int statmethod(int a = 2); - }; - - generates by default: - - class Klass(object): - ... - @staticmethod - def statmethod(a=2): - return _example.Klass_statmethod(a) - - instead of the following (which can be restored by using -fastproxy): - - class Klass(object): - ... - statmethod = staticmethod(_example.Klass_statmethod) - - - Modernise wrappers for static methods to use decorator syntax - @staticmethod. - - - Add missing runtime test for static class methods and using the actual class method. - -2019-01-12: ZackerySpytz - [OCaml] #1403 #1194 Fix compilation problems for OCaml >= 4.03.0 due to OCaml using - int64_t instead of int64. - -2019-01-11: ZackerySpytz - [OCaml] #1400 Fix the getters and setters of non-static member variables. - -2019-01-07: wsfulton - #358 Add VOID to windows.i - -2019-01-05: wsfulton - #948 #1019 #1273 Fix for C++11 raw strings where the delimiters were mistakenly left - in the string contents in situations where the string was copied into generated code. - For example, %constant, the "docstring" feature and for C#/Java/D constants turned on - with %javaconst/%csconst/%dmanifestconst. - -2019-01-05: wsfulton - [Ruby] #538. Fix Ruby support for %feature("docstring"). - -2019-01-03: wsfulton - #1202 Fix overloading of non-pointer class types in scripting languages when overloaded - with a pointer and a NULL scripting language equivalent is used, eg None in Python. - - The implementation changes the SWIGTYPE, SWIGTYPE& and SWIGTYPE&& typecheck typemaps to - prevent accepting a conversion to a NULL pointer. - -2019-01-03: ZackerySpytz - [OCaml] #1386 Fix the OCaml examples and test suite for out-of-source builds. - -2019-01-01: wsfulton - [Python] #639 remove duplicate proxy method definitions for global function wrappers. - - Global functions previously generated two definitions, eg: - - def foo(): - return _example.foo() - foo = _example.foo - - The first definition is replaced by the second definition and so the second definition - is the one used when the method is actually called. Now just the first definition is - generated by default and if the -fastproxy command line option is used, just the second - definition is generated. The second definition is faster as it avoids the proxy Python - method as it calls the low-level C wrapper directly. Using both -fastproxy and -olddefs - command line options will restore the previously generated code as it will generate both - method definitions. - - With this change, the wrappers for global C/C++ functions and C++ class methods now work - in the same way wrt to generating just a proxy method by default and control via - -fastproxy/-olddefs options. - -2018-12-20: hasinoff,wsfulton - [Java] #1334 Set Java thread name to native thread name when using directors. - - Default is to use name "Thread-XXX" and is still works like this by default. However, - adding the following will turn on the thread name setting (works for more recent - versions of Linux and MacOS): - - %begin %{ - #define SWIG_JAVA_USE_THREAD_NAME - %} - -2018-12-20: chlandsi - [Python] #1357. Fix overriding __new__ in Python 3.6. - - Fixes SystemError: Objects/tupleobject.c:81: bad argument to internal function" - -2018-12-16: wsfulton - [Python] #848 #1343 The module import logic has changed to stop obfuscating real ImportError - problems. Only one import of the low-level C/C++ module from the pure Python module is - attempted now. Previously a second import of the low-level C/C++ module was attempted - after an ImportError occurred and was done to support 'split modules'. A 'split module' is - a configuration where the pure Python module is a module within a Python package and the - low-level C/C++ module is a global Python module. Now a 'split module' configuration is - no longer supported by default. This configuration can be supported with a simple - customization, such as: - - %module(package="mypackage", moduleimport="import $module") foo - - or if using -builtin: - - %module(package="mypackage", moduleimport="from $module import *") foo - - instead of - - %module(package="mypackage") foo - - See the updated Python chapter titled "Location of modules" in the documentation. - -2018-12-11: tlby - [Perl] #1374 repair EXTEND() handling in typemaps - -2018-12-06: vadz - #1359 #1364 Add missing nested class destructor wrapper when the nested class is - inside a template. Removes associated bogus 'Illegal destructor name' warning. Only - occurred when the nested class' destructor is explicitly specified. - -2018-12-04: adr26 - [Python] #1368 #1369 Access Violation in tp_print caused by mismatched Python/extension - CRT usage - - Remove all use of tp_print, as this API uses a FILE*, which can be - mismatched when modules are built with different C libraries from - the main python executable. - - This change also brings consistent output between Python 2 and 3 for the 'cvar' SWIG - object (that contains the global variables) and SWIG packed objects (such as callback - constants). - -2018-12-04: wsfulton - [Python] #1282 Fix running 'python -m' when using 'swig -builtin' - - Similar to the earlier PEP 366 conforming fix for non-builtin. - -2018-11-29: adr26 - [Python] #1360 Leak of SWIG var link object - - Fix reference counting on _SWIG_globals to allow var link to be freed on module unload. - -2018-11-28: wsfulton - [Python] When using -builtin, the two step C-extension module import is now - one step and the wrapped API is only available once and not in an underlying - module attribute like it is without -builtin. To understand this, consider a - module named 'example' (using: %module example). The C-extension is compiled into - a Python module called '_example' and a pure Python module provides the actual - API from the module called 'example'. It was previously possible to additionally - access the API from the module attribute 'example._example'. The latter was an - implementation detail and is no longer available. It shouldn't have been used, but - if necessary it can be resurrected using the moduleimport attribute described in the - Python chapter of the documentation. If both modules are provided in a Python - package, try: - - %module(moduleimport="from . import _example\nfrom ._example import *") example - or more generically: - %module(moduleimport="from . import $module\nfrom .$module import *") example - - and if both are provided as global modules, try: - - %module(moduleimport="import _example\nfrom _example import *") example - or more generically: - %module(moduleimport="import $module\nfrom $module import *") example - - The module import code shown will appear in the example.py file. - -2018-11-24: vadz - #1358 Fix handling of abstract base classes nested inside templates - - Correct detecting of whether a derived class method overrides a pure virtual - base class method when both classes are nested inside a template class: this - notably didn't work correctly for methods taking parameters of the base class - type. - -2018-11-22: rupertnash - [Python] #1282 Make generated module runnable via python -m (PEP 366 conforming) - - Previously any SWIG generated modules in a package would fail with an ImportError - when using 'python -m' for example 'python -m mypkg.mymodule'. - - This fix also allows the SWIG generated module to be placed into a directory and - then renamed __init__.py to convert the module into a package again. This ability - stopped working in swig-3.0.9. However, only Python 2.7 or 3.3 and later work. If - Python 3.2 support is needed, use moduleimport in %module to customise the import - code. - -2018-11-13: wsfulton - #1340 Remove -cppcast and -nocppcast command line options (this was an option - available to the scripting language targets). - - The -cppcast option is still turned on by default. The -nocppcast option - to turn off the use of c++ casts (const_cast, static_cast etc) has been - removed. However, defining SWIG_NO_CPLUSPLUS_CAST will still generate C casts - instead of C++ casts for C++ wrappers. - - *** POTENTIAL INCOMPATIBILITY *** - -2018-11-13: wsfulton - [Python] #1340 Remove -outputtuple and -nooutputtuple command line options. - - Both the command line and %module options of the same name have been - removed. These were undocumented. The -outputtuple option returned a - Python tuple instead of a list, mostly typically in the OUTPUT - typemap implementations. - - It unclear why a tuple instead of a list return type is needed and - hence this option has been removed as part of the simplification of - the SWIG Python command line options for SWIG 4. - -2018-11-13: wsfulton - [Python] #1340 Remove -noproxyimport command line option. - - This option turned off the insertion of Python import statements - derived from a %import directive. For example given: - - %module module_b - %import "module_a.i" - - then module_b.py will contain: - - import module_a - - *** POTENTIAL INCOMPATIBILITY *** - -2018-10-29: AlexanderGabriel - [PHP] The following PHP7 reserved keywords are now only renamed by - SWIG when used as function names in the API being wrapper: - __halt_compiler array die echo empty eval exit include include_once - isset list print require require_once return unset - -2018-10-22: olly,wsfulton - [Python] #1261 #1340 Turn on many optimisation options by default and rationalise the - number of command line options. - - There were an unnecessary number of command line options and many of these have now - been removed in a drive for simplification. Some were needed to support older versions - of Python (2.6 and earlier). - - Many of the options could be turned on individually and when using -O. Previously -O - resulted in turning on a set of options: - - -modern -fastdispatch -nosafecstrings -fvirtual -noproxydel - -fastproxy -fastinit -fastunpack -fastquery -modernargs -nobuildnone - - Now -O results in turning on this reduced set: - - -fastdispatch -fastproxy -fvirtual - - The following options are now on by default, a deprecated warning is displayed if they - are used: - -fastinit Class initialisation code done in C/C++ rather than in Python code. - -fastquery Python dictionary used for lookup of types. - -fastunpack Faster unpacking of function arguments in C/C++ wrappers. - -modern Use Python 2.3 features such as object and property. - -modernargs Use Python 2.3 C APIs for unpacking arguments in tuples. - -noproxydel Stop generating a proxy __del__ method for backwards compatiblity. - -safecstrings No discernable difference - - The following options have been removed altogether: - -aliasobj0 - -buildnone - -classptr - -new_repr - -newrepr - -noaliasobj0 - -nobuildnone - -nocastmode - -nodirvtable - -noextranative - -nofastinit - -nofastproxy - -nofastquery - -nomodern - -nomodernargs - -nooutputtuple - -nosafecstrings - -old_repr - -oldrepr - -proxydel - - -new_vwm is no longer supported. Use the -newvwm alias instead. - - *** POTENTIAL INCOMPATIBILITY *** - -2018-10-22: olly - [Python] #1261 Remove command line option no longer needed as Python 2.3 and earlier - are no longer supported: - - -classic - -2018-10-09: wsfulton - [D, Go, Guile, Lua, Mzscheme, Ocaml, Perl5, Php, Scilab, Tcl] - Allow wrapping of std::map using non-default comparison function. - -2018-10-09: vadz - [Java] #1274 Allow wrapping of std::map using non-default comparison function. - -2018-10-04: wsfulton - [Python] #1126 Fix C default arguments with -builtin and -fastunpack and -modernargs. - Problem occurred when there is just one (defaulted) parameter in the parameter list. - -2018-09-24: wsfulton - [Python] #1319 C++11 hash tables implementation is finished now (including for -builtin): - std::unordered_map - std::unordered_set - std::unordered_multimap - std::unordered_multiset - -2018-09-21: wsfulton - [Python] Fix when using -builtin and wrapping std::map, std::set, std::unordered_map or - std::unordered_set to ensure __contains__ is called. This is a wrapper for the STL - container's find method. Without it, Python will do its own slower sequence search. - -2018-09-19: wsfulton - [Python] Fix functors (wrapped as __call__) when using -builtin -modern -fastunpack. - -2018-09-02: andreas.gaeer,tkrasnukha - [Python] #1321 Fix assert in PyTuple_GET_SIZE in debug interpreter builds of python-3.7 - when calling tp_new. - -2018-09-01: ChristopherHogan - [Guile] #1288 Fix garbage collection for guile >= 2.0.12. - -2018-08-31: wsfulton - [Python] #1319 C++11 hash tables support: - std::unordered_map - std::unordered_set - std::unordered_multimap - std::unordered_multiset - is now compiling and working (sorting using -builtin not fully functional yet though). - -2018-08-20: wkalinin - #1305 Fix nested structure symbol tables in C mode to fix member name conflicts - in different structs with the same nested struct member name. - -2018-08-18: wsfulton - [Python] #688 Fix makefile recursion when running python test-suite. - -2018-08-18: wsfulton - [Python] #1310 Re-implement Python -fastproxy option. - - The previous implementation failed with Python 3 and abstract base clases. - The new implementation replaces the Python 2 implementation using - new.instancemethod with the C API PyMethod_New to match the equivalent Python 3 - implementation which uses PyInstanceMethod_New. - - The new approach runs slightly faster. See #1310. - -2018-08-12: gmazzamuto - [Python] #1283 Update pybuffer.i library to use new-style Python buffer C API. - -2018-08-12: brianhatwood,wsfulton - [Java] #1303 #1304 Fix crash in directors when using OUTPUT and INOUT typemaps in typemaps.i and - passing NULL pointers in C++ to director method overloaded and implemented in Java. - -2018-08-10: wsfulton - [Python] #1293 Improve TypeError message inconsistencies between default and fastdispatch - mode when handling overloaded C++ functions. Previously the error message did not always - display the possible C/C++ prototypes in fastdispatch mode. - -2018-08-02: furylynx,jacobwgillespie,p2k - [Javascript] #1290, #968. Add support for NodeJS versions 2-10. - -2018-07-31: wsfulton - [Python] #1293 Overloaded C++ function wrappers now raise a TypeError instead - of NotImplementedError when the types passed are incorrect. This change means - there is now consistency with non-overloaded function wrappers which have always - raised TypeError when the incorrect types are passed. The error message remains - the same and is for example now: - - TypeError: Wrong number or type of arguments for overloaded function 'f'. - Possible C/C++ prototypes are: - f(int) - f(char const *) - - instead of: - - NotImplementedError: Wrong number or type of arguments for overloaded function 'f'. - Possible C/C++ prototypes are: - f(int) - f(char const *) - - *** POTENTIAL INCOMPATIBILITY *** - -2018-06-23: wsfulton - [Python] #718 Fix pythonnondynamic feature for modern classes - - Fixes nondynamic mode when an instance variable is set with the same - name as a class variable in a class derived from a SWIG proxy class. - This corner case set an instance variable instead of raising an AttributeError. - - Also fix %pythonnondynamic in Python 3 with -modern. The metaclass - containing the implementation was previously not being applied in Python 3. - -2018-07-17: petrmitrichev,wsfulton - [Python] #1275 #1279 Initialize function-local statics (singletons) that call Python - code during Python module initialization in order to avoid deadlocks with subsequent - multi-threaded usage. - -2018-06-15: wsfulton - [Python] Fix seg fault using Python 2 when passing a Python string, containing - invalid utf-8 content, to a wstring or wchar * parameter. A TypeError is thrown instead, eg: - - %include - void instring(const std::wstring& s); - - instring(b"h\xe9llooo") # Python - -2018-06-15: wsfulton - [Python] Python 3.7 support: Replace use of deprecated PyUnicode_GetSize with - PyUnicode_GetLength to remove deprecated warnings compiling the C/C++ wrappers. - -2018-06-12: wsfulton - [Python] Python 3.7 support: The %pythonabc feature in pyabc.i now uses base classes - collections.abc.MutableSequence - collections.abc.MutableMapping - collections.abc.MutableSet - instead of - collections.MutableSequence - collections.MutableMapping - collections.MutableSet - as the latter are deprecated in Python 3.7 and are due to be removed in Python 3.8. - The classes in collections.abc.* are available from Python 3.3 onwards. If you - require support for Python 3.2, then copy the pyabc.i file and modify by removing - the few instances of the .abc sub-module. - - *** POTENTIAL INCOMPATIBILITY *** - -2018-06-12: olly,wsfulton - [Python] #701 Remove support for Python versions < 2.7 and 3.0 and 3.1. - - *** POTENTIAL INCOMPATIBILITY *** - -2018-06-11: olly - [Python] Fix new GCC8 warnings in generated code by avoiding casts - between incompatible function types where possible, and by - suppressing the warning when it's due to the design of Python's C - API. Fixes #1259. - -2018-06-08: philippkraft - [Python] Stop exposing _swigregister to Python. It's not - useful for user Python code to call this, and it just clutters the - API unnecessarily. Fixes #1225. - -2018-06-07: cmfoil, kabbi, Jamie Kirkpatrick, markok314, vadz, wsfulton, Yann Diorcet - #170 Doxygen documentation support added. This allows translation of Doxygen comments - into JavaDoc and PyDoc documentation. It is enabled via the -doxygen command line - option. See the Doxygen.html chapter in the documentation for further information. - -2018-06-07: olly - [PHP] We've finally removed support for %pragma(php4) which was - deprecated back in 2008. Use %pragma(php) instead, which has been - supported since at least 2005. - - *** POTENTIAL INCOMPATIBILITY *** - -2018-06-07: olly - [PHP5] Support for PHP5 has been removed. PHP5 is no longer - actively supported by the PHP developers and security support for - it ends completely at the end of 2018, so it doesn't make sense - to include support for it in the upcoming SWIG 4.0.0 release. - - *** POTENTIAL INCOMPATIBILITY *** - -2018-06-06: olly - [Lua] Improve configure probes for Lua headers and libs used in testsuite. - -2018-05-15: kwwette - [Octave] add support for version 4.4 - - Should not introduce any user-visible incompatibilities - -2018-05-15: wsfulton - [C#, D, Java] Fix lookup of csconstruct, dconstruct and javaconstruct typemaps. - The C++ namespace was previously ignored when looking up the typemap. - -2018-05-15: wsfulton - [Javascript] Fix generated C++ code when using %nspace on namespaces that are more - than two levels deep. - -2018-05-14: wsfulton - Issue #1251 Add support for C++17 nested namespace definitions, - for example: - namespace A::B { ... } - -2018-05-11: wsfulton - [C#, D, Java] Add support so that the %csmethodmodifiers, %dmethodmodifiers, - %javamethodmodifiers can modify the method modifiers for the destructor wrappers - in the proxy class: dispose, Dispose, delete. With this feature, it is now possible - to make a C# proxy class sealed, eg when wrapping a class X, the virtual method modifiers - can be removed using: - - %typemap(csclassmodifiers) X "public sealed class" - %csmethodmodifiers X::~X "public /*virtual*/"; - -2018-04-18: olly - [Python] Suppress new pycodestyle warning: - E252 missing whitespace around parameter equals - -2018-04-07: goatshriek - [Ruby] #1213 Fix ruby %alias directive for global C/C++ functions. - -2018-04-03: olly - [Ruby] Fix to pass Qnil instead of NULL to rb_funcall(), which silences GCC - -Wconversion-null warning (on by default with recent GCC). - -2018-03-09: wsfulton - [Java] #1184 Fix swigReleaseOwnership() and swigTakeOwnership() regression - for non-director classes. Restores a dynamic_cast which was previously removed. - -2018-03-07: llongi - Github PR #1166 - Fix preprocessor handling of macros with commas - in a // comment. - -2018-02-18: JPEWdev - Patch #1164 - Add support for a command-line options file, also sometimes - called a response file. This is useful if the command-line options exceed - the system command-line length limit. To use, put the command-line options - into a file, then provide the file name prefixed with @, for example using - a file called args.txt: - - swig @args.txt - -2018-02-11: wsfulton - [Javascript] #1187 Fix compilation error wrapping std::complex via - std_complex.i. - -2018-01-30: smarchetto - [Scilab] add type name argument in SWIG_ptr() function to cast from pointer address to typed pointers - -2018-01-16: wsfulton - Expressions following a preprocessor directive must now be separated by whitespace - or non-numeric characters. This syntax change makes the SWIG preprocessor work like - the C preprocessor in this area. - - For example, the following code used be accepted as valid syntax: - #if1 - #define ABC 123 - #endif - - Now you get an error: - example.h:1: Error: Unknown SWIG preprocessor directive: if1 (if this is a block of - target language code, delimit it with %{ and %}) - example.h:3: Error: Extraneous #endif. - - The following is the correct syntax: - #if 1 - #define ABC 123 - #endif - - The following of course also works: - #if(1) - #define ABC 123 - #endif - - *** POTENTIAL INCOMPATIBILITY *** - -2018-01-15: wsfulton - Fix issue #1183. Floating point exception evaluating preprocessor expressions - resulting in division by zero. - -2018-01-14: wsfulton - Fix issue #1172. Seg fault parsing invalid exponents in the preprocessor. - -2018-01-12: Liryna - [C#] Patch #1128. Add ToArray function to std::vector wrappers. - -2018-01-12: wsfulton - [Java] Fix issue #1156. Add missing throws clause for interfaces when using the - %interface family of macros. - -2018-01-05: wsfulton - Fix default arguments using expressions containing -> syntax error. Problem reported on - swig-user mailing list. - -2017-12-30: wsfulton - [Python] Replace pep8 with pycodestyle for checking the Python code style when - running Python tests. - -2017-12-30: davedissian - Fixed a symbol lookup issue when encountering a typedef of a symbol from the tag - namespace to the global namespace when the names are identical, such as 'typedef - struct Foo Foo;'. - -2017-12-13: wsfulton - [Perl] add missing support for directorfree typemaps. - -2017-12-13: wsfulton - Issue #1167 Fix directorout typemaps which were causing undefined behaviour when - returning pointers by reference. - -2017-12-08: olly - [PHP] Use ZEND_MODULE_GLOBALS_ACCESSOR to access globals - this - should make the generated code work with PHP 7.2.0. - -2017-12-04: wsfulton - [Python] Add missing checks for failures in calls to PyUnicode_AsUTF8String. Previously a - seg fault could occur when passing invalid UTF8 strings (low surrogates), eg passing - u"\udcff" to the C layer (Python 3). - -2017-11-24: joequant - [R] Fix #1124 and return R_NilValue for null pointers - -2017-11-29: wsfulton - [Java] director exception handling improvements. - - When a director method throws an exception and it is caught by DirectorException - and passed back to Java using Swig::DirectorException::throwException, the Java - stack trace now contains the original source line that threw the exception. - - Deprecate Swig::DirectorException::raiseJavaException, please replace usage with - Swig::DirectorException::throwException. - - *** POTENTIAL INCOMPATIBILITY *** - -2017-10-26: wsfulton - Add support for C++11 ref-qualifiers when using directors. - -2017-10-26: wsfulton - Fix generated code when using directors and methods returning const ref pointers. - -2017-10-26: wsfulton - [C#, D, Java, Octave, R, Scilab] Port director typemaps to these additional languages. - Issue #700. - -2017-10-26: radarsat1 - [Ruby Python] Patch #1029 - Correct handling of null using directors and shared_ptr. - -2017-10-10: joequant - [R] pass enum expressions to R. This will generate - incorrect files when there is an arithmetic expression - in the enum, but this is better than silently generating - incorrect code - -2017-10-09: olly - [PHP] Fix incorrect wrapper code generated when there's a - combination of overloading, parameters with a default value - and %newobject. Fixes https://sourceforge.net/p/swig/bugs/1350/ - -2017-10-09: olly - Remove GCJ support. It isn't in a good state and doesn't seem to - be used, and GCC7 dropped GCJ. Closes - https://sourceforge.net/p/swig/bugs/823/ - -2017-10-07: olly - Fix preprocessor handling of empty macro arguments to match that of - C/C++ compilers. Fixes issue #1111 and - https://sourceforge.net/p/swig/bugs/826/ - -2017-10-06: wsfulton - [Python] Issue #1108. Fix platform inconsistency in Python default argument handling. - 32 bit and 64 bit compiled versions of SWIG generated different Python files - when default arguments were outside the range of 32 bit signed integers. - The default arguments specified in Python are now only those that are in the - range of a 32 bit signed integer, otherwise the default is obtained from C/C++ code. - -2017-10-02: wsfulton - [C#] Fix std::complex types passed by value. - -2017-10-02: wsfulton - [Javascript, Python, Ruby] Issue #732 - Missing type information for std::complex - in std_complex.i meant that previously std::complex always had to be fully qualified - in order to be wrapped with the appropriate typemaps. - -2017-10-01: joequant - allow R package names with docs - allowing multiple get accessors in R - fix smart-pointer and NAMESPACE support - constructors now returning smart pointers (if class - declared as such) - smart-pointer classes deriving from parent smart-pointers - -2017-09-29: wsfulton - Issue #1100 - Allow an instantiated template to have the same name in the target - language as the C++ template name, for example, this is now possible: - - template struct X { ... }; - %template(X) X; - -2017-09-23: wsfulton - Issue #1098. Fix overloading of shared_ptr with underlying pointer types, eg: - - void m(std::shared_ptr p); - void m(T &p); - void m(T *p); - - Only the first method is wrapped and the others are ignored/shadowed. - The implementation is done via a new attribute in the 'typecheck' typemap called - 'equivalent'. If specified, it must contain the equivalent pointer type for overloading - and can only be used for the special SWIG_TYPECHECK_POINTER precedence level. - The shared_ptr 'typecheck' typemaps have been modified accordingly. - Here is a simplified version: - - %typemap(typecheck, precedence=SWIG_TYPECHECK_POINTER, equivalent="T *") - T, - T CONST &, - T CONST *, - T *CONST&, - std::shared_ptr< T >, - std::shared_ptr< T > &, - std::shared_ptr< T > *, - std::shared_ptr< T > *& - { ... } - - Overloading with any of these types will result in SWIG ignoring all but the first - overloaded method by default. Without the 'equivalent' attribute, wrapping the overloaded - methods resulted in types being shadowed (scripting languages) or code that did not - compile (statically typed languages). - -2017-09-19: futatuki - [Python] #1003 Add --with-2to3=/path/to/2to3 option to configure. - -2017-09-18: wsfulton - Fix type promotion wrapping constant expressions of the form: - # define EXPR_MIXED1 (0x80 + 11.1) - 1 - This was previously an integral type instead of a floating point type. - -2017-09-17: wsfulton - Fix generated code for constant expressions containing wchar_t L literals such as: - # define __WCHAR_MAX (0x7fffffff + L'\0') - # define __WCHAR_MIN (-__WCHAR_MAX - 1) - -2017-09-10: mlamarre - [Python] Patch #1083. Define_DEBUG to 1 to do exactly like Visual Studio - /LDd, /MDd or /MTd compiler options. - -2017-08-25: wsfulton - Issue #1059. Add support for C++11 ref-qualifiers on non-static member functions. - Members with lvalue ref-qualifiers such as: - - struct RQ { - void m1(int x) &; - void m2(int x) const &; - }; - - are wrapped like any other member function. Member functions with rvalue ref-qualifiers - are ignored by default, such as: - - struct RQ { - void m3(int x) &&; - void m4(int x) const &&; - }; - - example.i:7: Warning 405: Method with rvalue ref-qualifier m3(int) && ignored. - example.i:8: Warning 405: Method with rvalue ref-qualifier m4(int) const && ignored. - - These can be unignored and exposed to the target language, see further documentation in - CPlusPlus11.html. - -2017-08-16: wsfulton - Fix #1063. Add using declarations to templates into typedef table. - - Using declarations to templates were missing in SWIG's internal typedef tables. - This led to a few problems, such as, templates that did not instantiate and generated - C++ code that did not compile as SWIG did not know what scope the template was - in. This happened mostly when a using declaration was used on a template type in a - completely unrelated namespace. - -2017-08-16: wsfulton - Fix type lookup in the presence of using directives and using declarations. - - Fix some cases of type lookup failure via a combination of both using directives and - using declarations resulting in C++ code that did not compile as the generated type was - not fully qualified for use in the global namespace. Example below: - - namespace Space5 { - namespace SubSpace5 { - namespace SubSubSpace5 { - struct F {}; - } - } - using namespace SubSpace5; - using SubSubSpace5::F; - void func(SubSubSpace5::F f); - } - -2017-08-16: wsfulton - Issue #1051. %template scope enforcement and class definition fixes. - - The scoping rules around %template have been specified and enforced. - The %template directive for a class template is the equivalent to an - explicit instantiation of a C++ class template. The scope for a valid - %template instantiation is now the same as the scope required for a - valid explicit instantiation of a C++ template. A definition of the - template for the explicit instantiation must be in scope where the - instantiation is declared and must not be enclosed within a different - namespace. - - For example, a few %template and C++ explicit instantiations of std::vector - are shown below: - - // valid - namespace std { - %template(vin) vector; - template class vector; - } - - // valid - using namespace std; - %template(vin) vector; - template class vector; - - // valid - using std::vector; - %template(vin) vector; - template class vector; - - // ill-formed - namespace unrelated { - using std::vector; - %template(vin) vector; - template class vector; - } - - // ill-formed - namespace unrelated { - using namespace std; - %template(vin) vector; - template class vector; - } - - // ill-formed - namespace unrelated { - namespace std { - %template(vin) vector; - template class vector; - } - } - - // ill-formed - namespace unrelated { - %template(vin) std::vector; - template class std::vector; - } - - When the scope is incorrect, an error now occurs such as: - - cpp_template_scope.i:34: Error: 'vector' resolves to 'std::vector' and - was incorrectly instantiated in scope 'unrelated' instead of within scope 'std'. - - Previously SWIG accepted the ill-formed examples above but this led to - numerous subtle template scope problems especially in the presence of - using declarations and using directives as well as with %feature and %typemap. - - Actually, a valid instantiation is one which conforms to the C++03 - standard as C++11 made a change to disallow using declarations and - using directives to find a template. - - // valid C++03, ill-formed C++11 - using std::vector; - template class vector; - - Similar fixes for defining classes using forward class references have - also been put in place. For example: - - namespace Space1 { - struct A; - } - namespace Space2 { - struct Space1::A { - void x(); - } - } - - will now error out with: - - cpp_class_definition.i:5: Error: 'Space1::A' resolves to 'Space1::A' and - was incorrectly instantiated in scope 'Space2' instead of within scope 'Space1'. - - Previously some symbols would have been instantiated in the wrong scope and led - to lots of scope problems involving SWIG typemaps, features, renames etc. - You will need to correct the scope used in other SWIG directives which do not - support 'using declarations' and 'using directives'. For example, if you previously had: - - %rename(Zap) vector::clear; - using namespace std; - %template(VectorInt) vector; - - Prior versions of SWIG incorrectly instantiated vector in the global namespace - and so the %rename matched. Now the template is instantiated in the correct namespace, - so is fully qualified as std::vector. The other SWIG directives need correcting as - they do not follow 'using declarations' and 'using directives'. Change it to: - - %rename(Zap) std::vector::clear; - using namespace std; - %template(vin) vector; - - - *** POTENTIAL INCOMPATIBILITY *** - -2017-08-16: wsfulton - Fix scope lookup for template parameters containing unary scope operators. - - Fixes cases like: - - namespace Alloc { - template struct Rebind { - typedef int Integer; - }; - } - %template(RebindBucket) Alloc::Rebind< Bucket >; - OR - %template(RebindBucket) Alloc::Rebind< ::Bucket >; - - Alloc::Rebind< Bucket >::Integer Bucket1(); - Alloc::Rebind< ::Bucket >::Integer Bucket2(); - Alloc::Rebind<::template TemplateBucket>::Integer Bucket3(); - -2017-08-16: wsfulton - For templates only, the template parameters are fully resolved when - handling typemaps. Without this, it is too hard to have decent rules - to apply typemaps when parameter types are typedef'd and template - parameters have default values. - - Fixes %clear for typedefs in templates, eg: - - %typemap("in") XXX::Long "..." - template typename struct XXX { - typedef long Long; - }; - %clear XXX::Long; - - as the typemap was previously incorrectly stored as a typemap for long - instead of XXX::Long. - -2017-08-05: olly - [C++11] Allow static_assert at the top level (and disallow it right - after template). Fixes issue 1031 reported by Artem V L. - -2017-08-02: wsfulton - Fix incorrectly shown warning when an empty template instantiation was used on a - class used as a base class and that base class was explicitly ignored with %ignore. - Example of the warning which will no longer appear: - - Warning 401: Base class 'Functor< int,int >' has no name as it is an empty - template instantiated with '%template()'. Ignored. - -2017-07-17: fflexo - [Java] #674 Add std_list.i to add support for std::list containers. The Java proxy - extends java.util.AbstractSequentialList and makes the C++ std::list container look - and feel much like a java.util.LinkedList from Java. - -2017-07-07: wsfulton - [Python] Fix display of documented template types when using the autodoc - feature. For example when wrapping: - - %feature("autodoc"); - template struct T {}; - %template(TInteger) T; - - the generated documentation contains: - """Proxy of C++ T< int > class.""" - instead of: - """Proxy of C++ T<(int)> class.""" - and - """__init__(TInteger self) -> TInteger""" - instead of - """__init__(T<(int)> self) -> TInteger""" - -2017-06-27: nihaln - [PHP] Update the OUTPUT Typemap to add return statement to the - PHP Wrapper. - -2017-06-27: nihaln - [PHP] Update the enum and value examples to use the OO wrappers - rather than the flat functions produced with -noproxy. There's - not been a good reason to use -noproxy for since PHP5 OO wrapping - was fixed back in 2005. - -2017-06-23: m7thon - [Python] fix and improve default argument handling: - - 1. Fix negative octals. Currently not handled correctly by `-py3` - (unusual case, but incorrect). - 2. Fix arguments of type "octal + something" (e.g. `0640 | 04`). - Currently drops everything after the first octal. Nasty! - 3. Fix bool arguments "0 + something" (e.g. `0 | 1`) are always - "False" (unusual case, but incorrect). - 4. Remove special handling of "TRUE" and "FALSE" from - `convertValue` since there's no reason these have to match - "true" and "false". - 5. Remove the Python 2 vs. Python 3 distinction based on the - `-py3` flag. Now the same python code is produced for default - arguments for Python 2 and Python 3. For this, octal default - arguments, e.g. 0644, are now wrapped as `int('644', 8)`. This - is required, as Python 2 and Python 3 have incompatible syntax - for octal literals. - - Fixes #707 - -2017-06-21: futatuki - #1004 - Fix ccache-swig executable name to respect configure's --program-prefix and - --program-suffix values if used. - -2017-06-21: tamuratak - [Ruby] #911 - Add std::wstring support. - -2017-06-19: wsfulton - [Python] Fix handling of rich comparisons when wrapping overloaded operators: - - operator< operator<= operator> operator>= operator== operator!= - - Previously a TypeError was always thrown if the type was not correct. NotImplemented - is now returned from these wrapped functions if the type being compared with is - not correct. The subsequent behaviour varies between different versions of Python - and the comparison function being used, but is now consistent with normal Python - behaviour. For example, for the first 4 operator overloads above, a TypeError - 'unorderable types' is thrown in Python 3, but Python 2 will return True or False. - NotImplemented should be returned when the comparison cannot be done, see PEP 207 and - https://docs.python.org/3/library/constants.html#NotImplemented - - Note that the bug was only present when overloaded operators did not also have a - function overload. - - Fixes SF bug #1208 (3441262) and SF patch #303. - - *** POTENTIAL INCOMPATIBILITY *** - -2017-06-17: fabrice102 - [Go] Fix Go callback example. Fixes github #600, #955, #1000. - -2017-06-16: wsfulton - Make sure warning and error messages are not split up by other processes writing to - stdout at the same time. - -2017-06-16: wsfulton - [R] Fix wrapping function pointers containing rvalue and lvalue reference parameters. - -2017-06-13: olly - [Perl] Fix testsuite to work without . in @INC - it was removed in - Perl 5.26 for security reasons, and has also been removed from - older versions in some distros. Fixes #997 reported by lfam. - -2017-06-03: wsfulton - Fix %import on a file containing a file scope %fragment forced inclusion to not - generate the fragment contents as %import should not result in code being generated. - The behaviour is now the same as importing code insertion blocks. - Wrapping FileC.i in the following example will result in no generated code, whereas - previously "#include " was generated: - - // FileA.i - %fragment("", "header") %{ - #include - %} - - %{ - #include - %} - %fragment(""); - - // FileC.i - %import "FileA.i" - - *** POTENTIAL INCOMPATIBILITY *** - -2017-05-26: Volker Diels-Grabsch, vadz - [Java] #842 Extend from java.util.AbstractList<> and implement java.util.RandomAccess for - std::vector wrappers. This notably allows to iterate over wrapped vectors in a natural way. - Note that boxed types are now used in the Java layer when wrapping vector of C primitive - types, for example. This may introduce some subtle incompatibilities due to some - differences in how Java converts boxed types and unboxed types. For example, - - int i=0; - double d1 = i; // ok - Double d2 = i; // error: incompatible types: int cannot be converted to Double - - This can be a problem when calling the add and set functions. A suggested backwards - compatible workaround is to use something like (shown for std::vector: - - #if defined(SWIGJAVA) - // Add in old api that uses non-boxed types - %extend std::vector { - %proxycode %{ - public void add(double x) { - add(Double.valueOf(x)); - } - public void set(int i, double val) { - set(i, Double.valueOf(val)); - } - %} - } - #endif - - %include "std_vector.i" - %template(VectorDouble) std::vector; - - *** POTENTIAL INCOMPATIBILITY *** - -2017-05-30: davidcl - [Scilab] #994 Undefined symbol error when loading in Scilab 6 - -2017-05-25: asibross - [Java] #370 #417 Missing smart pointer handling in Java director extra methods - swigReleaseOwnership() and swigTakeOwnership(). - -2017-05-23: wsfulton - [Java] #230 #759 Fix Java shared_ptr and directors for derived classes java compilation - error. - - For shared_ptr proxy proxy classes, add a protected method swigSetCMemOwn for modifying - the swigCMemOwn and swigCMemOwnDerived member variables which are used by various other - methods for controlling memory ownership. - -2017-05-21: Sghirate - [Java, C#, D] #449 Remove unnecessary use of dynamic_cast in directors to enable - non-RTTI compilation. - -2017-05-21: wsfulton - [Python] #993 Fix handling of default -ve unsigned values, such as: - void f(unsigned = -1U); - -2017-05-20: jschueller - [Python] #991 Fix E731 PEP8 warning: do not assign a lambda expression - -2017-05-16: nihal95 - [PHP] Add %pragma version directive to allow the version of the - extension to be set. Patch #970, fixes #360. - -2017-05-13: yag00 - Patch #975 - Add support for noexcept on director methods. - -2017-04-27: redbrain - Issue #974, Patch #976 - Fix preprocessor handling of macros with commas in a comment. - -2017-04-25: jleveque - [Lua] #959 - Fix Visual Studio C4244 conversion warnings in Lua wrappers. - -2017-04-21: tamuratak - [Ruby] #964 - Add shared_ptr director typemaps. - -2017-04-20: wsfulton - [Ruby] #586, #935 Add assert for invalid NULL type parameter when calling SWIG_Ruby_NewPointerObj. - -2017-04-20: tamuratak - [Ruby] #930, #937 - Fix containers of std::shared_ptr. - Upcasting, const types (eg vector>) and NULL/nullptr support added. - -2017-04-12: smarchetto - [Scilab] New parameter targetversion to specify the Scilab target version (5, 6, ..) for code generation - With Scilab 6 target specified, identifier names truncation is disabled (no longer necessary) - -2017-03-24: tamuratak - [Ruby] Fix #939 - Wrapping std::vector fix due to incorrect null checks - on VALUE obj. - -2017-03-17: vadz - [C#] #947 Add support for std::complex - -2017-03-17: wsfulton - [Go] Fix handling of typedef'd function pointers and typedef'd member function pointers - such as: - - typedef int (*FnPtr_td)(int, int); - int do_op(int x, int y, FnPtr_td op); - -2017-03-16: wsfulton - Add support for member const function pointers such as: - - int fn(short (Funcs::* parm)(bool)) const; - - Also fix parsing of references/pointers and qualifiers to member - pointers such as: - - int fn(short (Funcs::* const parm)(bool)); - int fn(short (Funcs::* & parm)(bool)); - -2017-03-10: wsfulton - Extend C++11 alternate function syntax parsing to support const and noexcept, such as: - - auto sum1(int x, int y) const -> int { return x + y; } - auto sum2(int x, int y) noexcept -> int { return x + y; } - -2017-02-29: tamuratak - [Ruby] #917 - Add Enumerable module to all container class wrappers. It was missing - for std::list, std::multiset, std::unordered_multiset and std::unordered_map. - -2017-02-27: assambar - [C++11] Extend parser to support throw specifier in combination - with override and/or final. - -2017-02-10: tamuratak - [Ruby] #883 - Add support for C++11 hash tables: - std::unordered_map - std::unordered_set - std::unordered_multimap - std::unordered_multiset - -2017-02-08: jcsharp - [C#] #887 Improve std::vector wrapper constructors - - Replace constructor taking ICollection with IEnumerable and also add IEnumerable - constructor to avoid the boxing and unboxing overhead of the original constructor, - when the type parameter is a value type. diff --git a/Doc/Manual/Sections.html b/Doc/Manual/Sections.html index 6db5c3cc1..2cb1d2be4 100644 --- a/Doc/Manual/Sections.html +++ b/Doc/Manual/Sections.html @@ -8,7 +8,7 @@

      SWIG-4.0 Documentation

      -Last update : SWIG-4.0.0 (27 Apr 2019) +Last update : SWIG-4.0.1 (in progress)

      Sections

      diff --git a/README b/README index ecf4f87fc..165098cb5 100644 --- a/README +++ b/README @@ -1,6 +1,6 @@ SWIG (Simplified Wrapper and Interface Generator) -Version: 4.0.0 (27 Apr 2019) +Version: 4.0.1 (in progress) Tagline: SWIG is a compiler that integrates C and C++ with languages including Perl, Python, Tcl, Ruby, PHP, Java, C#, D, Go, Lua, diff --git a/configure.ac b/configure.ac index 1873797d6..cc46a6521 100644 --- a/configure.ac +++ b/configure.ac @@ -2,7 +2,7 @@ dnl Process this file with autoconf to produce a configure script. dnl The macros which aren't shipped with the autotools are stored in the dnl Tools/config directory in .m4 files. -AC_INIT([swig],[4.0.0],[http://www.swig.org]) +AC_INIT([swig],[4.0.1],[http://www.swig.org]) AC_PREREQ(2.60) AC_CONFIG_SRCDIR([Source/Swig/swig.h]) From 6606a164f0624108b8075e847c5f2c213606ed72 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 30 Apr 2019 19:10:31 +0100 Subject: [PATCH 118/134] Migrate Travis tests from trusty to xenial Ubuntu trusty 14.04 is end of life April 2019. Ubuntu xenial 16.04 is the main platform for Travis now. Some languages are not working on xenial, so I've left them on trusty for now. --- .travis.yml | 130 +++++++++++++++++----------------- Tools/travis-linux-install.sh | 20 +++--- 2 files changed, 74 insertions(+), 76 deletions(-) diff --git a/.travis.yml b/.travis.yml index 61021b4e4..07fc0efbd 100644 --- a/.travis.yml +++ b/.travis.yml @@ -5,30 +5,30 @@ matrix: os: linux env: SWIGLANG= sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG= sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG= SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG= SWIG_CC=gcc-6 SWIG_CXX=g++-6 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=csharp sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=d sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=go VER=1.3 @@ -48,72 +48,72 @@ matrix: os: linux env: SWIGLANG=guile sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=java sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux - env: SWIGLANG=javascript ENGINE=node + env: SWIGLANG=javascript ENGINE=node VER=0.10 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=javascript ENGINE=node VER=4 CPP11=1 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=javascript ENGINE=node VER=6 CPP11=1 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=javascript ENGINE=node VER=8 CPP11=1 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=javascript ENGINE=node VER=10 CPP11=1 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=javascript ENGINE=jsc sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=javascript ENGINE=v8 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=lua sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=lua VER=5.3 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=mzscheme sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=ocaml sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=octave SWIGJOBS=-j2 # 3.8 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=octave SWIGJOBS=-j2 VER=4.0 @@ -133,17 +133,17 @@ matrix: os: linux env: SWIGLANG=perl5 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=php VER=7.0 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=php VER=7.1 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=php VER=7.2 @@ -153,110 +153,110 @@ matrix: os: linux env: SWIGLANG=php VER=7.3 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python # 2.7 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python PY3=3 VER=3.2 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python PY3=3 VER=3.3 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python PY3=3 VER=3.4 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python PY3=3 VER=3.5 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python PY3=3 VER=3.6 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python PY3=3 VER=3.7 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES=-builtin sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES="-builtin -O" sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=python SWIG_FEATURES=-builtin SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP11=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=python SWIG_FEATURES=-builtin SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP11=1 PY3=3 VER=3.7 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES=-builtin PY3=3 VER=3.4 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES=-builtin PY3=3 VER=3.5 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES=-builtin PY3=3 VER=3.7 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES="-builtin -O" PY3=3 VER=3.7 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES=-builtin PY3=3 VER=3.7 SWIGOPTPY3= sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES=-O sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=python SWIG_FEATURES=-O PY3=3 VER=3.7 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=r sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=ruby VER=1.9.3 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=ruby VER=2.0.0 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=ruby VER=2.3.0 @@ -271,11 +271,11 @@ matrix: os: linux env: SWIGLANG=tcl sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=csharp SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=go SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 sudo: required @@ -283,27 +283,27 @@ matrix: - os: linux env: SWIGLANG=java SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=python SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=r CPP11=1 # Note: making 'R CMD SHLIB' use a different compiler is non-trivial sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=ruby SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=tcl SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=csharp SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=go SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 sudo: required @@ -311,39 +311,39 @@ matrix: - os: linux env: SWIGLANG=java SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=python SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=ruby SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=tcl SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=java SWIG_CC=gcc-7 SWIG_CXX=g++-7 CPP14=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=python SWIG_CC=gcc-7 SWIG_CXX=g++-7 CPP14=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=csharp SWIG_CC=gcc-8 SWIG_CXX=g++-8 CPP17=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=java SWIG_CC=gcc-8 SWIG_CXX=g++-8 CPP17=1 sudo: required - dist: trusty + dist: xenial - os: linux env: SWIGLANG=python SWIG_CC=gcc-8 SWIG_CXX=g++-8 CPP17=1 PY3=3 VER=3.7 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: osx env: SWIGLANG= @@ -393,12 +393,12 @@ matrix: os: linux env: SWIGLANG=mzscheme sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=ocaml sudo: required - dist: trusty + dist: xenial before_install: - date -u diff --git a/Tools/travis-linux-install.sh b/Tools/travis-linux-install.sh index bfa7bf8eb..b801e2b00 100755 --- a/Tools/travis-linux-install.sh +++ b/Tools/travis-linux-install.sh @@ -44,14 +44,15 @@ case "$SWIGLANG" in "javascript") case "$ENGINE" in "node") - if [[ -z "$VER" ]]; then - travis_retry sudo apt-get install -qq nodejs node-gyp + travis_retry wget -qO- https://raw.githubusercontent.com/creationix/nvm/v0.33.10/install.sh | bash + export NVM_DIR="$HOME/.nvm" + [ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh" + travis_retry nvm install ${VER} + nvm use ${VER} + if [ "$VER" == "0.10" ] || [ "$VER" == "0.12" ] ; then +# travis_retry sudo apt-get install -qq nodejs node-gyp + travis_retry npm install -g node-gyp@$VER else - travis_retry wget -qO- https://raw.githubusercontent.com/creationix/nvm/v0.33.10/install.sh | bash - export NVM_DIR="$HOME/.nvm" - [ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh" - travis_retry nvm install ${VER} - nvm use ${VER} travis_retry npm install -g node-gyp fi ;; @@ -70,8 +71,6 @@ case "$SWIGLANG" in if [[ -z "$VER" ]]; then travis_retry sudo apt-get -qq install lua5.2 liblua5.2-dev else - travis_retry sudo add-apt-repository -y ppa:ubuntu-cloud-archive/mitaka-staging - travis_retry sudo apt-get -qq update travis_retry sudo apt-get -qq install lua${VER} liblua${VER}-dev fi ;; @@ -79,8 +78,7 @@ case "$SWIGLANG" in travis_retry sudo apt-get -qq install racket ;; "ocaml") - # configure also looks for ocamldlgen, but this isn't packaged. But it isn't used by default so this doesn't matter. - travis_retry sudo apt-get -qq install ocaml ocaml-findlib + travis_retry sudo apt-get -qq install ocaml camlp4 ;; "octave") if [[ -z "$VER" ]]; then From 9d0cf2ce61409975ecb1500a1b268f2acbd41d60 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 30 Apr 2019 19:53:35 +0100 Subject: [PATCH 119/134] Remove duplicate Travis xenial Octave testing --- .travis.yml | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/.travis.yml b/.travis.yml index 07fc0efbd..54805092c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -111,14 +111,9 @@ matrix: dist: xenial - compiler: gcc os: linux - env: SWIGLANG=octave SWIGJOBS=-j2 # 3.8 + env: SWIGLANG=octave SWIGJOBS=-j2 sudo: required dist: xenial - - compiler: gcc - os: linux - env: SWIGLANG=octave SWIGJOBS=-j2 VER=4.0 - sudo: required - dist: trusty - compiler: gcc os: linux env: SWIGLANG=octave SWIGJOBS=-j2 VER=4.2 CPP11=1 From 5d976b0ebe6e6644342c0768eea4f87401d592ad Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 30 Apr 2019 21:14:39 +0100 Subject: [PATCH 120/134] Fix php testcase warning --- Examples/test-suite/php/cpp_static_runme.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Examples/test-suite/php/cpp_static_runme.php b/Examples/test-suite/php/cpp_static_runme.php index 1d581bdb9..20b50dd9e 100644 --- a/Examples/test-suite/php/cpp_static_runme.php +++ b/Examples/test-suite/php/cpp_static_runme.php @@ -4,7 +4,7 @@ require "tests.php"; require "cpp_static.php"; // New functions -check::functions(array('staticfunctiontest_static_func','staticfunctiontest_static_func_2','staticfunctiontest_static_func_3','is_python_builtin')); +check::functions(array('staticfunctiontest_static_func','staticfunctiontest_static_func_2','staticfunctiontest_static_func_3','is_python_builtin','staticmembertest_grab_int','staticbase_grab_statty_base','staticderived_grab_statty_derived')); // New classes check::classes(array('StaticMemberTest','StaticFunctionTest','cpp_static','StaticBase','StaticDerived')); // New vars From dbb5fdda01eb51b5c3757c95f4c4bff81d92c6bd Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 30 Apr 2019 21:34:07 +0100 Subject: [PATCH 121/134] Fix php pragmas example . is not always in the include_path by default --- Examples/php/pragmas/example.i | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Examples/php/pragmas/example.i b/Examples/php/pragmas/example.i index f9307a663..b72828b0e 100644 --- a/Examples/php/pragmas/example.i +++ b/Examples/php/pragmas/example.i @@ -21,7 +21,7 @@ zend_printf("This was %%rshutdown\n"); } -%pragma(php) include="include.php"; +%pragma(php) include="./include.php"; %pragma(php) code=" # This code is inserted into example.php From 78a1515f4651f032d153e8d4ea8f25c83e97fa0c Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Mon, 29 Apr 2019 19:39:04 +0100 Subject: [PATCH 122/134] OCaml testing requires camlp4 --- configure.ac | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/configure.ac b/configure.ac index cc46a6521..133975f7e 100644 --- a/configure.ac +++ b/configure.ac @@ -2044,6 +2044,16 @@ if test x"${with_ocaml}" = xno; then AC_MSG_NOTICE([Disabling OCaml]) OCAMLC= else + # OCaml compiler + if test -z "$OCAMLC"; then + AC_CHECK_PROGS(OCAMLC, ocamlc) + fi + + # OCaml Pre-Processor-Pretty-Printer + if test -z "$CAMLP4"; then + AC_CHECK_PROGS(CAMLP4, camlp4) + fi + # OCaml DL load generator if test -z "$OCAMLDLGEN"; then AC_CHECK_PROGS(OCAMLDLGEN, ocamldlgen) @@ -2054,27 +2064,17 @@ else AC_CHECK_PROGS(OCAMLFIND, ocamlfind) fi - # OCaml compiler - if test -z "$OCAMLC"; then - AC_CHECK_PROGS(OCAMLC, ocamlc) - fi - # OCaml toplevel creator if test -z "$OCAMLMKTOP"; then AC_CHECK_PROGS(OCAMLMKTOP, ocamlmktop) fi - - # OCaml Pre-Processor-Pretty-Printer - if test -z "$CAMLP4"; then - AC_CHECK_PROGS(CAMLP4, camlp4) - fi fi AC_SUBST(OCAMLC) +AC_SUBST(CAMLP4) AC_SUBST(OCAMLDLGEN) AC_SUBST(OCAMLFIND) AC_SUBST(OCAMLMKTOP) -AC_SUBST(CAMLP4) #---------------------------------------------------------------- # Look for C# @@ -2636,7 +2636,7 @@ AC_SUBST(SKIP_PHP) SKIP_OCAML= -if test -z "$OCAMLC" ; then +if test -z "$OCAMLC" || test -z "$CAMLP4" ; then SKIP_OCAML="1" fi AC_SUBST(SKIP_OCAML) From be019a03ce7df11a748718fb63d47f35a8c297ec Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 2 May 2019 19:15:20 +0100 Subject: [PATCH 123/134] Appveyor testing - make sure language tests are not mistakenly skipped --- appveyor.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/appveyor.yml b/appveyor.yml index 1eb7ae41d..10bf064df 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -118,6 +118,7 @@ test_script: - if not "%OSVARIANT%"=="" CCache\ccache-swig -V - bash -c "file ./swig.exe" - bash -c "make check-%SWIGLANG%-version" +- bash -c "make check-%SWIGLANG%-enabled" - bash -c "time make -k check-%SWIGLANG%-examples %CHECK_OPTIONS% %CHECK_OPTIONS2%" - bash -c "time make -k check-%SWIGLANG%-test-suite -j%MAKEJOBS% %CHECK_OPTIONS% %CHECK_OPTIONS2%" From 48e61eea1d377c4d45526410c486a81dc47a8c58 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 2 May 2019 07:56:42 +0100 Subject: [PATCH 124/134] Travis gcc version refactor Use GCC env variable to hold gcc version to install instead of SWIG_CC and SWIG_CXX. --- .travis.yml | 47 +++++++++++++++++------------------ Tools/travis-linux-install.sh | 18 +++----------- Tools/travis-osx-install.sh | 2 ++ 3 files changed, 29 insertions(+), 38 deletions(-) diff --git a/.travis.yml b/.travis.yml index 54805092c..9aea6aac0 100644 --- a/.travis.yml +++ b/.travis.yml @@ -12,11 +12,11 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG= SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 + env: SWIGLANG= GCC=5 CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG= SWIG_CC=gcc-6 SWIG_CXX=g++-6 + env: SWIGLANG= GCC=6 sudo: required dist: xenial - compiler: gcc @@ -195,11 +195,11 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG=python SWIG_FEATURES=-builtin SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP11=1 + env: SWIGLANG=python SWIG_FEATURES=-builtin GCC=6 CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=python SWIG_FEATURES=-builtin SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP11=1 PY3=3 VER=3.7 + env: SWIGLANG=python SWIG_FEATURES=-builtin GCC=6 CPP11=1 PY3=3 VER=3.7 sudo: required dist: xenial - compiler: gcc @@ -268,19 +268,19 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG=csharp SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 + env: SWIGLANG=csharp GCC=5 CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=go SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 + env: SWIGLANG=go GCC=5 CPP11=1 sudo: required dist: trusty - os: linux - env: SWIGLANG=java SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 + env: SWIGLANG=java GCC=5 CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=python SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 + env: SWIGLANG=python GCC=5 CPP11=1 sudo: required dist: xenial - os: linux @@ -288,55 +288,55 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG=ruby SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 + env: SWIGLANG=ruby GCC=5 CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=tcl SWIG_CC=gcc-5 SWIG_CXX=g++-5 CPP11=1 + env: SWIGLANG=tcl GCC=5 CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=csharp SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 + env: SWIGLANG=csharp GCC=6 CPP14=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=go SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 + env: SWIGLANG=go GCC=6 CPP14=1 sudo: required dist: trusty - os: linux - env: SWIGLANG=java SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 + env: SWIGLANG=java GCC=6 CPP14=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=python SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 + env: SWIGLANG=python GCC=6 CPP14=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=ruby SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 + env: SWIGLANG=ruby GCC=6 CPP14=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=tcl SWIG_CC=gcc-6 SWIG_CXX=g++-6 CPP14=1 + env: SWIGLANG=tcl GCC=6 CPP14=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=java SWIG_CC=gcc-7 SWIG_CXX=g++-7 CPP14=1 + env: SWIGLANG=java GCC=7 CPP14=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=python SWIG_CC=gcc-7 SWIG_CXX=g++-7 CPP14=1 + env: SWIGLANG=python GCC=7 CPP14=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=csharp SWIG_CC=gcc-8 SWIG_CXX=g++-8 CPP17=1 + env: SWIGLANG=csharp GCC=8 CPP17=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=java SWIG_CC=gcc-8 SWIG_CXX=g++-8 CPP17=1 + env: SWIGLANG=java GCC=8 CPP17=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=python SWIG_CC=gcc-8 SWIG_CXX=g++-8 CPP17=1 PY3=3 VER=3.7 + env: SWIGLANG=python GCC=8 CPP17=1 PY3=3 VER=3.7 sudo: required dist: xenial - compiler: gcc @@ -400,9 +400,8 @@ before_install: - uname -a - if test "$TRAVIS_OS_NAME" = "linux"; then lscpu && cat /proc/cpuinfo | grep "model name" && cat /proc/meminfo | grep MemTotal; fi - if test "$TRAVIS_OS_NAME" = "osx"; then sysctl -a | grep brand_string; fi - # Travis overrides CC environment with compiler predefined values - - if test -n "$SWIG_CC"; then export CC="$SWIG_CC"; fi - - if test -n "$SWIG_CXX"; then export CXX="$SWIG_CXX"; fi + # Travis overrides CC environment with compiler predefined values + - if test -n "$GCC"; then export CC="gcc-$GCC" && export CXX="g++-$GCC"; fi install: - if test "$TRAVIS_OS_NAME" = "linux"; then source Tools/travis-linux-install.sh; fi - if test "$TRAVIS_OS_NAME" = "osx"; then source Tools/travis-osx-install.sh; fi diff --git a/Tools/travis-linux-install.sh b/Tools/travis-linux-install.sh index b801e2b00..8795229bb 100755 --- a/Tools/travis-linux-install.sh +++ b/Tools/travis-linux-install.sh @@ -1,26 +1,16 @@ #!/bin/bash +# Install Linux packages where the version has been overidden in .travis.yml + set -e # exit on failure (same as -o errexit) lsb_release -a travis_retry sudo apt-get -qq update -if [[ "$CC" == gcc-5 ]]; then +if [[ -n "$GCC" ]]; then travis_retry sudo add-apt-repository -y ppa:ubuntu-toolchain-r/test travis_retry sudo apt-get -qq update - travis_retry sudo apt-get install -qq g++-5 -elif [[ "$CC" == gcc-6 ]]; then - travis_retry sudo add-apt-repository -y ppa:ubuntu-toolchain-r/test - travis_retry sudo apt-get -qq update - travis_retry sudo apt-get install -qq g++-6 -elif [[ "$CC" == gcc-7 ]]; then - travis_retry sudo add-apt-repository -y ppa:ubuntu-toolchain-r/test - travis_retry sudo apt-get -qq update - travis_retry sudo apt-get install -qq g++-7 -elif [[ "$CC" == gcc-8 ]]; then - travis_retry sudo add-apt-repository -y ppa:ubuntu-toolchain-r/test - travis_retry sudo apt-get -qq update - travis_retry sudo apt-get install -qq g++-8 + travis_retry sudo apt-get install -qq g++-$GCC fi travis_retry sudo apt-get -qq install libboost-dev diff --git a/Tools/travis-osx-install.sh b/Tools/travis-osx-install.sh index 6bfb2276a..63a11efa5 100755 --- a/Tools/travis-osx-install.sh +++ b/Tools/travis-osx-install.sh @@ -1,5 +1,7 @@ #!/bin/bash +# Install MacOS packages where the version has been overidden in .travis.yml + set -e # exit on failure (same as -o errexit) sw_vers From 256446d29043c93e523eedee84b6ecd2b38f0b4a Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 2 May 2019 08:08:05 +0100 Subject: [PATCH 125/134] Expand Travis testing of core SWIG compilation to include more gcc versions --- .travis.yml | 26 +++++++++++++++++++++++++- 1 file changed, 25 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 9aea6aac0..643ad73ab 100644 --- a/.travis.yml +++ b/.travis.yml @@ -12,13 +12,37 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG= GCC=5 CPP11=1 + env: SWIGLANG= GCC=4.4 + sudo: required + dist: xenial + - os: linux + env: SWIGLANG= GCC=4.5 + sudo: required + dist: xenial + - os: linux + env: SWIGLANG= GCC=4.6 + sudo: required + dist: xenial + - os: linux + env: SWIGLANG= GCC=4.7 + sudo: required + dist: xenial + - os: linux + env: SWIGLANG= GCC=4.8 sudo: required dist: xenial - os: linux env: SWIGLANG= GCC=6 sudo: required dist: xenial + - os: linux + env: SWIGLANG= GCC=7 + sudo: required + dist: xenial + - os: linux + env: SWIGLANG= GCC=8 + sudo: required + dist: xenial - compiler: gcc os: linux env: SWIGLANG=csharp From 25c0397ec455a62b72d5a09ef8409e9344fd1349 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 2 May 2019 18:53:57 +0100 Subject: [PATCH 126/134] Travis testing gcc versions gcc-4.5 has package dependency problems Add gcc-4.9 --- .travis.yml | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/.travis.yml b/.travis.yml index 643ad73ab..3213e8b33 100644 --- a/.travis.yml +++ b/.travis.yml @@ -15,10 +15,6 @@ matrix: env: SWIGLANG= GCC=4.4 sudo: required dist: xenial - - os: linux - env: SWIGLANG= GCC=4.5 - sudo: required - dist: xenial - os: linux env: SWIGLANG= GCC=4.6 sudo: required @@ -31,6 +27,10 @@ matrix: env: SWIGLANG= GCC=4.8 sudo: required dist: xenial + - os: linux + env: SWIGLANG= GCC=4.9 + sudo: required + dist: xenial - os: linux env: SWIGLANG= GCC=6 sudo: required From 00fb2e56292a851ba35299dc5f91fa171475e5ac Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 2 May 2019 19:08:25 +0100 Subject: [PATCH 127/134] Travis output optimisation --- .travis.yml | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/.travis.yml b/.travis.yml index 3213e8b33..5aa5d7006 100644 --- a/.travis.yml +++ b/.travis.yml @@ -432,10 +432,7 @@ install: - if test -n "$CPP11"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++11 -Wall -Wextra" "CFLAGS=-std=c11 -Wall -Wextra") && export CSTD=c11 && export CPPSTD=c++11; fi - if test -n "$CPP14"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++14 -Wall -Wextra" "CFLAGS=-std=c11 -Wall -Wextra") && export CSTD=c11 && export CPPSTD=c++14; fi - if test -n "$CPP17"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++17 -Wall -Wextra" "CFLAGS=-std=c17 -Wall -Wextra") && export CSTD=c17 && export CPPSTD=c++17; fi - - ls -la $(which $CC) - - ls -la $(which $CXX) - - $CC --version - - $CXX --version + - ls -la $(which $CC) $(which $CXX) && $CC --version && $CXX --version script: - echo 'Configuring...' && echo -en 'travis_fold:start:script.1\\r' - if test -n "$SWIGLANG"; then CONFIGOPTS+=(--without-alllang --with-$WITHLANG); fi From 4539041c505eda94ac03055e5a6c073376e15f1f Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Thu, 2 May 2019 19:16:44 +0100 Subject: [PATCH 128/134] Travis output optimisation during configure --- .travis.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.travis.yml b/.travis.yml index 5aa5d7006..c572f0f38 100644 --- a/.travis.yml +++ b/.travis.yml @@ -429,12 +429,12 @@ before_install: install: - if test "$TRAVIS_OS_NAME" = "linux"; then source Tools/travis-linux-install.sh; fi - if test "$TRAVIS_OS_NAME" = "osx"; then source Tools/travis-osx-install.sh; fi - - if test -n "$CPP11"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++11 -Wall -Wextra" "CFLAGS=-std=c11 -Wall -Wextra") && export CSTD=c11 && export CPPSTD=c++11; fi - - if test -n "$CPP14"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++14 -Wall -Wextra" "CFLAGS=-std=c11 -Wall -Wextra") && export CSTD=c11 && export CPPSTD=c++14; fi - - if test -n "$CPP17"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++17 -Wall -Wextra" "CFLAGS=-std=c17 -Wall -Wextra") && export CSTD=c17 && export CPPSTD=c++17; fi - ls -la $(which $CC) $(which $CXX) && $CC --version && $CXX --version script: - echo 'Configuring...' && echo -en 'travis_fold:start:script.1\\r' + - if test -n "$CPP11"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++11 -Wall -Wextra" "CFLAGS=-std=c11 -Wall -Wextra") && export CSTD=c11 && export CPPSTD=c++11; fi + - if test -n "$CPP14"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++14 -Wall -Wextra" "CFLAGS=-std=c11 -Wall -Wextra") && export CSTD=c11 && export CPPSTD=c++14; fi + - if test -n "$CPP17"; then CONFIGOPTS+=(--enable-cpp11-testing --without-maximum-compile-warnings "CXXFLAGS=-std=c++17 -Wall -Wextra" "CFLAGS=-std=c17 -Wall -Wextra") && export CSTD=c17 && export CPPSTD=c++17; fi - if test -n "$SWIGLANG"; then CONFIGOPTS+=(--without-alllang --with-$WITHLANG); fi - echo "${CONFIGOPTS[@]}" - ./autogen.sh && mkdir -p build/build && cd build/build && ../../configure "${CONFIGOPTS[@]}" From 0cf01afc54f4435828a3e7901d862ba03c63f353 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 27 Apr 2019 23:51:08 +0100 Subject: [PATCH 129/134] Windows documentation minor improvement --- Doc/Manual/Windows.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Doc/Manual/Windows.html b/Doc/Manual/Windows.html index 301974b64..800e2e420 100644 --- a/Doc/Manual/Windows.html +++ b/Doc/Manual/Windows.html @@ -68,7 +68,7 @@ SWIG does not come with the usual Windows type installation program, however it

      -The swigwin distribution contains the SWIG Windows executable, swig.exe, which will run on 32 bit versions of Windows, ie Windows 95 and later. +The swigwin distribution contains the SWIG Windows 32-bit executable, swig.exe, which will run on both 32-bit and 64-bit versions of Windows. If you want to build your own swig.exe have a look at Building swig.exe on Windows.

      From 32c9e2ada8836806e02019a8f3d4e955861fc871 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 4 May 2019 22:31:48 +0100 Subject: [PATCH 130/134] Travis testing GCC=5 not needed for xenial. Default compiler is gcc 5 on xenial. --- .travis.yml | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/.travis.yml b/.travis.yml index c572f0f38..a8ccdce75 100644 --- a/.travis.yml +++ b/.travis.yml @@ -292,19 +292,19 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG=csharp GCC=5 CPP11=1 + env: SWIGLANG=csharp CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=go GCC=5 CPP11=1 + env: SWIGLANG=go CPP11=1 sudo: required dist: trusty - os: linux - env: SWIGLANG=java GCC=5 CPP11=1 + env: SWIGLANG=java CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=python GCC=5 CPP11=1 + env: SWIGLANG=python CPP11=1 sudo: required dist: xenial - os: linux @@ -312,11 +312,11 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG=ruby GCC=5 CPP11=1 + env: SWIGLANG=ruby CPP11=1 sudo: required dist: xenial - os: linux - env: SWIGLANG=tcl GCC=5 CPP11=1 + env: SWIGLANG=tcl CPP11=1 sudo: required dist: xenial - os: linux From 49195c536122e8cd89ea34c7745911a5e7197181 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Sat, 4 May 2019 22:47:19 +0100 Subject: [PATCH 131/134] Specify Go version to test with c++11 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Default version of Go 1.11.1 on Travis is broken for c++11 testing. gcc_libinit.c: In function ‘_cgo_try_pthread_create’: gcc_libinit.c:110:3: error: implicit declaration of function ‘nanosleep’ [-Werror=implicit-function-declaration] nanosleep(&ts, nil); --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index a8ccdce75..45266e7fc 100644 --- a/.travis.yml +++ b/.travis.yml @@ -296,7 +296,7 @@ matrix: sudo: required dist: xenial - os: linux - env: SWIGLANG=go CPP11=1 + env: SWIGLANG=go VER=1.6 CPP11=1 sudo: required dist: trusty - os: linux From ccbc451c7c3d3ecfd0e2c1f59d184cc919d701e9 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 7 May 2019 19:38:37 +0100 Subject: [PATCH 132/134] Disable Travis php 7.2 testing There is a certificate error on the unsupported Ubuntu Trusty machines. Php 7.2 is segfaulting on Ubuntu Xenial, so there is work to be done. --- .travis.yml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/.travis.yml b/.travis.yml index 45266e7fc..b44247baf 100644 --- a/.travis.yml +++ b/.travis.yml @@ -401,6 +401,12 @@ matrix: env: SWIGLANG=tcl allow_failures: + # certificate error on trusty + - compiler: gcc + os: linux + env: SWIGLANG=php VER=7.2 + sudo: required + dist: trusty # Sometimes hits the Travis 50 minute time limit - compiler: gcc os: linux From ed1fabe867cdcf93b83fa6c1cc6e68e4e26db104 Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 7 May 2019 19:42:07 +0100 Subject: [PATCH 133/134] Switch php 7.2 testing to xenial --- .travis.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.travis.yml b/.travis.yml index b44247baf..fc7714992 100644 --- a/.travis.yml +++ b/.travis.yml @@ -167,7 +167,7 @@ matrix: os: linux env: SWIGLANG=php VER=7.2 sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=php VER=7.3 @@ -401,12 +401,12 @@ matrix: env: SWIGLANG=tcl allow_failures: - # certificate error on trusty + # seg fault in director_basic testcase - compiler: gcc os: linux env: SWIGLANG=php VER=7.2 sudo: required - dist: trusty + dist: xenial # Sometimes hits the Travis 50 minute time limit - compiler: gcc os: linux From f06330e720b0867817679fbf67aa8705ce13bbcf Mon Sep 17 00:00:00 2001 From: William S Fulton Date: Tue, 7 May 2019 23:05:53 +0100 Subject: [PATCH 134/134] Move Scilab Travis testing from trusty to xenial --- .travis.yml | 2 +- Tools/travis-linux-install.sh | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index fc7714992..bede4a0d1 100644 --- a/.travis.yml +++ b/.travis.yml @@ -285,7 +285,7 @@ matrix: os: linux env: SWIGLANG=scilab sudo: required - dist: trusty + dist: xenial - compiler: gcc os: linux env: SWIGLANG=tcl diff --git a/Tools/travis-linux-install.sh b/Tools/travis-linux-install.sh index 8795229bb..d7d31505f 100755 --- a/Tools/travis-linux-install.sh +++ b/Tools/travis-linux-install.sh @@ -114,6 +114,10 @@ case "$SWIGLANG" in fi ;; "scilab") + # Travis has the wrong version of Java pre-installed resulting in error using scilab: + # /usr/bin/scilab-bin: error while loading shared libraries: libjava.so: cannot open shared object file: No such file or directory + echo "JAVA_HOME was set to $JAVA_HOME" + unset JAVA_HOME travis_retry sudo apt-get -qq install scilab ;; "tcl")