diff liboctave/oct-locbuf.h @ 8377:25bc2d31e1bf

improve OCTAVE_LOCAL_BUFFER
author Jaroslav Hajek <highegg@gmail.com>
date Wed, 29 Oct 2008 16:52:10 +0100
parents
children ad8ed668e0a4
line wrap: on
line diff
new file mode 100644
--- /dev/null
+++ b/liboctave/oct-locbuf.h
@@ -0,0 +1,81 @@
+/*
+
+Copyright (C) 2008 Jaroslav Hajek <highegg@gmail.com>
+
+This file is part of Octave.
+
+Octave is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 3 of the License, or (at your
+option) any later version.
+
+Octave is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You should have received a copy of the GNU General Public License
+along with Octave; see the file COPYING.  If not, see
+<http://www.gnu.org/licenses/>.
+
+*/
+
+#if !defined (octave_local_buffer_h)
+#define octave_local_buffer_h 1
+
+#include <cstddef>
+
+// The default local buffer simply encapsulates an *array* pointer that gets
+// delete[]d automatically. For common POD types, we provide specializations.
+
+template <class T>
+class octave_local_buffer
+{
+public:
+  octave_local_buffer (size_t size)
+    : data (0) 
+    { 
+      if (size) 
+        data = new T[size]; 
+    }
+  ~octave_local_buffer (void) { delete [] data; }
+  operator T *() const { return data; }
+private:
+  T *data;
+};
+
+
+// If the compiler supports dynamic stack arrays, we can use the attached hack to 
+// place small buffer arrays on the stack. 
+
+#ifdef HAVE_DYNAMIC_AUTO_ARRAYS
+
+// Maximum buffer size (in bytes) to be placed on the stack.
+
+#define OCTAVE_LOCAL_BUFFER_MAX_STACK_SIZE 8192
+
+// If we have automatic arrays, we use an automatic array if the size is small
+// enough.  To avoid possibly evaluating `size' multiple times, we first cache
+// it.  Note that we always construct both the stack array and the
+// octave_local_buffer object, but only one of them will be nonempty.
+
+#define OCTAVE_LOCAL_BUFFER(T, buf, size) \
+  const size_t _bufsize_ ## buf = size; \
+  const bool _lbufaut_ ## buf = _bufsize_ ## buf * sizeof (T) \
+     <= OCTAVE_LOCAL_BUFFER_MAX_STACK_SIZE; \
+  T _bufaut_ ## buf [_lbufaut_ ## buf ? _bufsize_ ## buf : 0]; \
+  octave_local_buffer<T> _bufheap_ ## buf (!_lbufaut_ ## buf ? _bufsize_ ## buf : 0); \
+  T *buf = _lbufaut_ ## buf ? _bufaut_ ## buf : static_cast<T *> (_bufheap_ ## buf);
+
+#else
+
+// If we don't have automatic arrays, we simply always use octave_local_buffer.
+
+#define OCTAVE_LOCAL_BUFFER(T, buf, size) \
+  octave_local_buffer<T> _buffer_ ## buf (size); \
+  T *buf = _buffer_ ## buf;
+
+#endif 
+
+#endif
+