summaryrefslogtreecommitdiff
path: root/Lib/octave
diff options
context:
space:
mode:
authorWilliam S Fulton <wsf@fultondesigns.co.uk>2022-08-01 23:49:14 +0100
committerWilliam S Fulton <wsf@fultondesigns.co.uk>2022-08-02 00:00:54 +0100
commit2ccc9bd0607664ff1b86b65be4c797eeb69fcc00 (patch)
tree2cdb48386bf64c913334b4df65662ca0c9becac9 /Lib/octave
parent1730e4126e4283d3fd42cc4cd4710eec1919b3f5 (diff)
downloadswig-2ccc9bd0607664ff1b86b65be4c797eeb69fcc00.tar.gz
Add Octave support for std::unique_ptr and std::auto_ptr
Equivalent to Ruby/Python implementations.
Diffstat (limited to 'Lib/octave')
-rw-r--r--Lib/octave/octrun.swg57
-rw-r--r--Lib/octave/std_auto_ptr.i33
-rw-r--r--Lib/octave/std_unique_ptr.i33
3 files changed, 105 insertions, 18 deletions
diff --git a/Lib/octave/octrun.swg b/Lib/octave/octrun.swg
index d94056c8c..71a907f9b 100644
--- a/Lib/octave/octrun.swg
+++ b/Lib/octave/octrun.swg
@@ -232,7 +232,7 @@ SWIGRUNTIME void swig_acquire_ownership_obj(void *vptr, int own);
const swig_type_info *construct_type; // type of special type object
std::vector < type_ptr_pair > types; // our c++ base classes
- int own; // whether we call c++ destructors when we die
+ int thisown; // whether we call c++ destructors when we die
typedef std::pair < const swig_octave_member *, octave_value > member_value_pair;
typedef std::map < std::string, member_value_pair > member_map;
@@ -412,7 +412,7 @@ SWIGRUNTIME void swig_acquire_ownership_obj(void *vptr, int own);
octave_swig_type(void *_ptr = 0, const swig_type_info *_type = 0, int _own = 0,
bool _always_static = false)
- : module(0), construct_type(_ptr ? 0 : _type), own(_own),
+ : module(0), construct_type(_ptr ? 0 : _type), thisown(_own),
always_static(_always_static) {
if (_type || _ptr)
types.push_back(std::make_pair(_type, _ptr));
@@ -426,7 +426,7 @@ SWIGRUNTIME void swig_acquire_ownership_obj(void *vptr, int own);
}
~octave_swig_type() {
- if (own) {
+ if (thisown) {
++count;
for (unsigned int j = 0; j < types.size(); ++j) {
if (!types[j].first || !types[j].first->clientdata)
@@ -559,7 +559,7 @@ SWIGRUNTIME void swig_acquire_ownership_obj(void *vptr, int own);
}
void merge(octave_swig_type &rhs) {
- rhs.own = 0;
+ rhs.thisown = 0;
for (unsigned int j = 0; j < rhs.types.size(); ++j) {
assert(!rhs.types[j].second.destroyed);
#ifdef SWIG_DIRECTORS
@@ -582,35 +582,56 @@ SWIGRUNTIME void swig_acquire_ownership_obj(void *vptr, int own);
swig_member_const_iterator swig_members_begin() { return members.begin(); }
swig_member_const_iterator swig_members_end() { return members.end(); }
- int cast(void **vptr, swig_type_info *type, int *_own, int flags) {
+ int cast(void **vptr, swig_type_info *type, int *own, int flags) {
int res = SWIG_ERROR;
- if (_own)
- *_own = own;
- if (flags &SWIG_POINTER_DISOWN)
- own = 0;
+ int clear_pointer = 0;
+
+ if (own)
+ *own = 0;
+ if (((flags & SWIG_POINTER_RELEASE) == SWIG_POINTER_RELEASE) && !thisown) {
+ return SWIG_ERROR_RELEASE_NOT_OWNED;
+ } else {
+ if (own)
+ *own = *own | thisown;
+ if (flags & SWIG_POINTER_DISOWN) {
+ thisown = 0;
+ }
+ if (flags & SWIG_POINTER_CLEAR) {
+ clear_pointer = 1;
+ }
+ }
+
if (!type && types.size()) {
- if(vptr)
+ if (vptr) {
*vptr = types[0].second.ptr;
+ if (clear_pointer)
+ types[0].second.ptr = 0;
+ }
return SWIG_OK;
}
for (unsigned int j = 0; j < types.size(); ++j)
if (type == types[j].first) {
- if(vptr)
+ if (vptr) {
*vptr = types[j].second.ptr;
+ if (clear_pointer)
+ types[j].second.ptr = 0;
+ }
return SWIG_OK;
}
for (unsigned int j = 0; j < types.size(); ++j) {
swig_cast_info *tc = SWIG_TypeCheck(types[j].first->name, type);
if (!tc)
continue;
- if(vptr) {
+ if (vptr) {
int newmemory = 0;
*vptr = SWIG_TypeCast(tc, types[j].second.ptr, &newmemory);
- if (newmemory == SWIG_CAST_NEW_MEMORY) {
- assert(_own); /* badly formed typemap which will lead to a memory leak - it must set and use own to delete *ptr */
- if (_own)
- *_own = *_own | SWIG_CAST_NEW_MEMORY;
- }
+ if (newmemory == SWIG_CAST_NEW_MEMORY) {
+ assert(own); /* badly formed typemap which will lead to a memory leak - it must set and use own to delete *ptr */
+ if (own)
+ *own = *own | SWIG_CAST_NEW_MEMORY;
+ }
+ if (clear_pointer)
+ types[j].second.ptr = 0;
}
res = SWIG_OK;
break;
@@ -619,7 +640,7 @@ SWIGRUNTIME void swig_acquire_ownership_obj(void *vptr, int own);
}
bool is_owned() const {
- return own;
+ return thisown;
}
#ifdef SWIG_DIRECTORS
diff --git a/Lib/octave/std_auto_ptr.i b/Lib/octave/std_auto_ptr.i
new file mode 100644
index 000000000..d062886e4
--- /dev/null
+++ b/Lib/octave/std_auto_ptr.i
@@ -0,0 +1,33 @@
+/* -----------------------------------------------------------------------------
+ * std_auto_ptr.i
+ *
+ * SWIG library file for handling std::auto_ptr.
+ * Memory ownership is passed from the std::auto_ptr C++ layer to the proxy
+ * class when returning a std::auto_ptr from a function.
+ * Memory ownership is passed from the proxy class to the std::auto_ptr in the
+ * C++ layer when passed as a parameter to a wrapped function.
+ * ----------------------------------------------------------------------------- */
+
+%define %auto_ptr(TYPE)
+%typemap(in, noblock=1) std::auto_ptr< TYPE > (void *argp = 0, int res = 0) {
+ res = SWIG_ConvertPtr($input, &argp, $descriptor(TYPE *), SWIG_POINTER_RELEASE | %convertptr_flags);
+ if (!SWIG_IsOK(res)) {
+ if (res == SWIG_ERROR_RELEASE_NOT_OWNED) {
+ %releasenotowned_fail(res, "TYPE *", $symname, $argnum);
+ } else {
+ %argument_fail(res, "TYPE *", $symname, $argnum);
+ }
+ }
+ $1.reset((TYPE *)argp);
+}
+
+%typemap (out) std::auto_ptr< TYPE > %{
+ %set_output(SWIG_NewPointerObj($1.release(), $descriptor(TYPE *), SWIG_POINTER_OWN | %newpointer_flags));
+%}
+
+%template() std::auto_ptr< TYPE >;
+%enddef
+
+namespace std {
+ template <class T> class auto_ptr {};
+}
diff --git a/Lib/octave/std_unique_ptr.i b/Lib/octave/std_unique_ptr.i
new file mode 100644
index 000000000..1a7ec06fa
--- /dev/null
+++ b/Lib/octave/std_unique_ptr.i
@@ -0,0 +1,33 @@
+/* -----------------------------------------------------------------------------
+ * std_unique_ptr.i
+ *
+ * SWIG library file for handling std::unique_ptr.
+ * Memory ownership is passed from the std::unique_ptr C++ layer to the proxy
+ * class when returning a std::unique_ptr from a function.
+ * Memory ownership is passed from the proxy class to the std::unique_ptr in the
+ * C++ layer when passed as a parameter to a wrapped function.
+ * ----------------------------------------------------------------------------- */
+
+%define %unique_ptr(TYPE)
+%typemap(in, noblock=1) std::unique_ptr< TYPE > (void *argp = 0, int res = 0) {
+ res = SWIG_ConvertPtr($input, &argp, $descriptor(TYPE *), SWIG_POINTER_RELEASE | %convertptr_flags);
+ if (!SWIG_IsOK(res)) {
+ if (res == SWIG_ERROR_RELEASE_NOT_OWNED) {
+ %releasenotowned_fail(res, "TYPE *", $symname, $argnum);
+ } else {
+ %argument_fail(res, "TYPE *", $symname, $argnum);
+ }
+ }
+ $1.reset((TYPE *)argp);
+}
+
+%typemap (out) std::unique_ptr< TYPE > %{
+ %set_output(SWIG_NewPointerObj($1.release(), $descriptor(TYPE *), SWIG_POINTER_OWN | %newpointer_flags));
+%}
+
+%template() std::unique_ptr< TYPE >;
+%enddef
+
+namespace std {
+ template <class T> class unique_ptr {};
+}