diff --git a/applications/test/IListStream/Make/files b/applications/test/IListStream/Make/files
new file mode 100644
index 0000000000..7f0914970b
--- /dev/null
+++ b/applications/test/IListStream/Make/files
@@ -0,0 +1,3 @@
+Test-IListStream.C
+
+EXE = $(FOAM_USER_APPBIN)/Test-IListStream
diff --git a/applications/test/IListStream/Make/options b/applications/test/IListStream/Make/options
new file mode 100644
index 0000000000..18e6fe47af
--- /dev/null
+++ b/applications/test/IListStream/Make/options
@@ -0,0 +1,2 @@
+/* EXE_INC = */
+/* EXE_LIBS = */
diff --git a/applications/test/IListStream/Test-IListStream.C b/applications/test/IListStream/Test-IListStream.C
new file mode 100644
index 0000000000..588550a7a9
--- /dev/null
+++ b/applications/test/IListStream/Test-IListStream.C
@@ -0,0 +1,151 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
+ \\/ M anipulation |
+-------------------------------------------------------------------------------
+License
+ This file is part of OpenFOAM.
+
+ OpenFOAM 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.
+
+ OpenFOAM 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 OpenFOAM. If not, see .
+
+Description
+
+\*---------------------------------------------------------------------------*/
+
+#include "ListStream.H"
+#include "UListStream.H"
+#include "wordList.H"
+#include "IOstreams.H"
+#include "argList.H"
+
+using namespace Foam;
+
+Ostream& toString(Ostream& os, const UList& list)
+{
+ os << '"';
+ for (const char c : list)
+ {
+ os << c;
+ }
+ os << '"';
+
+ return os;
+}
+
+
+template
+void printInfo(const BufType& buf)
+{
+ Info<< nl << "=========================" << endl;
+ buf.print(Info);
+ toString(Info, buf.list());
+ Info<< nl << "=========================" << endl;
+}
+
+
+void printTokens(Istream& is)
+{
+ label count = 0;
+ token t;
+ while (is.good())
+ {
+ is >> t;
+ if (t.good())
+ {
+ ++count;
+ Info<<"token: " << t << endl;
+ }
+ }
+
+ Info<< count << " tokens" << endl;
+}
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+// Main program:
+
+int main(int argc, char *argv[])
+{
+ // Buffer storage
+ DynamicList storage(16);
+
+ OListStream obuf(std::move(storage));
+ obuf << 1002 << " " << "abcd" << " " << "def" << " " << 3.14159 << ";\n";
+
+ // Move contents to output buffer
+ printInfo(obuf);
+
+ Info< newvalues(52);
+ // {
+ // for (int i=0; i<26; ++i)
+ // {
+ // newvalues[2*i+0] = char('a' + i);
+ // newvalues[2*i+1] = char('A' + i);
+ // }
+ // }
+ // ibuf.swap(newvalues);
+ //
+ // Info<.
+
+Description
+
+\*---------------------------------------------------------------------------*/
+
+#include "OCountStream.H"
+#include "StringStream.H"
+#include "IOstreams.H"
+#include "argList.H"
+
+using namespace Foam;
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+// Main program:
+
+int main(int argc, char *argv[])
+{
+ OCountStream cnt;
+ OStringStream str;
+
+ for (label i = 0; i < 50; ++i)
+ {
+ str << 1002 << " " << "abcd" << " "
+ << "def" << " " << 3.14159 << ";\n";
+
+ cnt << 1002 << " " << "abcd" << " "
+ << "def" << " " << 3.14159 << ";\n";
+ }
+
+ cnt.print(Info);
+ Info<< "via string-stream: " << str.str().size() << " chars" << endl;
+
+ Info<< "\nEnd\n" << endl;
+
+ return 0;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/OListStream/Make/options b/applications/test/OListStream/Make/options
index 4e772fdf9d..18e6fe47af 100644
--- a/applications/test/OListStream/Make/options
+++ b/applications/test/OListStream/Make/options
@@ -1,2 +1,2 @@
-/* EXE_INC = -I$(LIB_SRC)/finiteVolume/lnInclude */
-/* EXE_LIBS = -lfiniteVolume */
+/* EXE_INC = */
+/* EXE_LIBS = */
diff --git a/applications/test/OListStream/Test-OListStream.C b/applications/test/OListStream/Test-OListStream.C
index adbbc722d5..4c3a758f0f 100644
--- a/applications/test/OListStream/Test-OListStream.C
+++ b/applications/test/OListStream/Test-OListStream.C
@@ -25,7 +25,7 @@ Description
\*---------------------------------------------------------------------------*/
-#include "OListStream.H"
+#include "ListStream.H"
#include "wordList.H"
#include "IOstreams.H"
#include "argList.H"
@@ -45,10 +45,31 @@ Ostream& toString(Ostream& os, const UList& list)
}
-void printInfo(const OListStream& buf)
+template
+void printInfo(const BufType& buf)
{
- Info<< nl << buf.size() << " chars (" << buf.capacity() << " capacity) ";
- toString(Info, buf.list()) << endl;
+ Info<< nl << "=========================" << endl;
+ buf.print(Info);
+ toString(Info, buf.list());
+ Info<< nl << "=========================" << endl;
+}
+
+
+void printTokens(Istream& is)
+{
+ label count = 0;
+ token t;
+ while (is.good())
+ {
+ is >> t;
+ if (t.good())
+ {
+ ++count;
+ Info<<"token: " << t << endl;
+ }
+ }
+
+ Info<< count << " tokens" << endl;
}
@@ -58,18 +79,126 @@ void printInfo(const OListStream& buf)
int main(int argc, char *argv[])
{
// Buffer storage
- DynamicList storage(8);
+ DynamicList storage(16);
OListStream obuf(std::move(storage));
- obuf << 1002 << " " << "abcd" << " " << "def" << " " << 3.14159 << ";\n";
+
+ obuf.setBlockSize(100);
+
+ printInfo(obuf);
+
+ // Fill with some content
+ for (label i = 0; i < 50; ++i)
+ {
+ obuf<< 1002 << " " << "abcd" << " "
+ << "def" << " " << 3.14159 << ";\n";
+ }
printInfo(obuf);
obuf.rewind();
- obuf << 100;
+ printInfo(obuf);
+
+ for (label i=0; i < 10; ++i)
+ {
+ obuf << "item" << i << "\n";
+ }
printInfo(obuf);
+ obuf.shrink();
+
+ Info<< "after shrink" << nl;
+ printInfo(obuf);
+
+ // Add some more
+ for (label i=10; i < 15; ++i)
+ {
+ obuf << "more" << i << nl;
+ }
+
+ Info<< "appended more" << nl;
+ printInfo(obuf);
+
+ // Overwrite at some position
+ obuf.stdStream().rdbuf()->pubseekpos(0.60 * obuf.size());
+ obuf << "<" << nl << "OVERWRITE" << nl;
+
+ Info<<"after overwrite" << nl;
+ printInfo(obuf);
+
+ Info<< "transfer contents to a List or IListStream" << nl;
+
+ IListStream ibuf(obuf.xfer());
+
+ Info<<"original:";
+ printInfo(obuf);
+
+ Info<<"new input:" << nl;
+ printInfo(ibuf);
+
+ printTokens(ibuf);
+
+ // Create from other storage types
+
+ Info<< nl;
+ {
+ Info<<"create std::move(List)" << endl;
+ List list(16, 'A');
+
+ Info<<"input:";
+ toString(Info, list) << endl;
+
+ OListStream buf1(std::move(list));
+ for (label i = 0; i < 26; ++i)
+ {
+ buf1 << char('A' +i);
+ }
+ for (label i = 0; i < 26; ++i)
+ {
+ buf1 << char('a' +i);
+ }
+
+ Info<<"orig:";
+ toString(Info, list) << endl;
+
+ printInfo(buf1);
+ }
+
+ Info<< nl;
+
+ List written;
+ {
+ Info<<"create List.xfer()" << endl;
+ List list(16, 'B');
+
+ Info<<"input:";
+ toString(Info, list) << endl;
+
+ OListStream buf1(list.xfer());
+ for (label i = 0; i < 26; ++i)
+ {
+ buf1 << char('A' + i);
+ }
+ for (label i = 0; i < 26; ++i)
+ {
+ buf1 << char('a' +i);
+ }
+
+ Info<<"orig:";
+ toString(Info, list) << endl;
+
+ printInfo(buf1);
+
+ // Move back to written
+ written = buf1.xfer();
+
+ printInfo(buf1);
+ }
+ Info<<"'captured' content ";
+ toString(Info, written);
+
+
Info<< "\nEnd\n" << endl;
return 0;
diff --git a/applications/test/UIBufStream/Make/files b/applications/test/UIBufStream/Make/files
deleted file mode 100644
index 611f5337be..0000000000
--- a/applications/test/UIBufStream/Make/files
+++ /dev/null
@@ -1,3 +0,0 @@
-Test-UIBufStream.C
-
-EXE = $(FOAM_USER_APPBIN)/Test-UIBufStream
diff --git a/applications/test/UIBufStream/Make/options b/applications/test/UIBufStream/Make/options
deleted file mode 100644
index 4e772fdf9d..0000000000
--- a/applications/test/UIBufStream/Make/options
+++ /dev/null
@@ -1,2 +0,0 @@
-/* EXE_INC = -I$(LIB_SRC)/finiteVolume/lnInclude */
-/* EXE_LIBS = -lfiniteVolume */
diff --git a/applications/test/UIListStream/Make/files b/applications/test/UIListStream/Make/files
new file mode 100644
index 0000000000..f60abd8967
--- /dev/null
+++ b/applications/test/UIListStream/Make/files
@@ -0,0 +1,3 @@
+Test-UIListStream.C
+
+EXE = $(FOAM_USER_APPBIN)/Test-UIListStream
diff --git a/applications/test/UIListStream/Make/options b/applications/test/UIListStream/Make/options
new file mode 100644
index 0000000000..18e6fe47af
--- /dev/null
+++ b/applications/test/UIListStream/Make/options
@@ -0,0 +1,2 @@
+/* EXE_INC = */
+/* EXE_LIBS = */
diff --git a/applications/test/UIBufStream/Test-UIBufStream.C b/applications/test/UIListStream/Test-UIListStream.C
similarity index 74%
rename from applications/test/UIBufStream/Test-UIBufStream.C
rename to applications/test/UIListStream/Test-UIListStream.C
index f183d623ab..fb0a1f378c 100644
--- a/applications/test/UIBufStream/Test-UIBufStream.C
+++ b/applications/test/UIListStream/Test-UIListStream.C
@@ -25,14 +25,54 @@ Description
\*---------------------------------------------------------------------------*/
-#include "UIBufStream.H"
-#include "UOBufStream.H"
+#include "UListStream.H"
#include "wordList.H"
#include "IOstreams.H"
#include "argList.H"
using namespace Foam;
+Ostream& toString(Ostream& os, const UList& list)
+{
+ os << '"';
+ for (const char c : list)
+ {
+ os << c;
+ }
+ os << '"';
+
+ return os;
+}
+
+
+template
+void printInfo(const BufType& buf)
+{
+ Info<< nl << "=========================" << endl;
+ buf.print(Info);
+ toString(Info, buf.list());
+ Info<< nl << "=========================" << endl;
+}
+
+
+void printTokens(Istream& is)
+{
+ label count = 0;
+ token t;
+ while (is.good())
+ {
+ is >> t;
+ if (t.good())
+ {
+ ++count;
+ Info<<"token: " << t << endl;
+ }
+ }
+
+ Info<< count << " tokens" << endl;
+}
+
+
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
// Main program:
@@ -41,10 +81,10 @@ int main(int argc, char *argv[])
// Buffer storage
DynamicList storage(1000);
- UOBufStream obuf(storage);
+ UOListStream obuf(storage);
obuf << 1002 << " " << "abcd" << " " << "def" << " " << 3.14159 << ";\n";
- Info<<"formatted: " << obuf.size() << " chars" << endl;
+ obuf.print(Info);
// Match size
storage.resize(obuf.size());
@@ -53,31 +93,14 @@ int main(int argc, char *argv[])
// Attach input buffer - could also do without previous resize
- UIBufStream ibuf(storage, storage.size());
+ UIListStream ibuf(storage);
- token t;
-
- while (ibuf.good())
- {
- ibuf >> t;
- if (t.good())
- {
- Info<<"token: " << t << endl;
- }
- }
+ printTokens(ibuf);
Info<< nl << "Repeat..." << endl;
ibuf.rewind();
- while (ibuf.good())
- {
- ibuf >> t;
- if (t.good())
- {
- Info<<"token: " << t << endl;
- }
- }
-
+ printTokens(ibuf);
Info<< "\nEnd\n" << endl;
diff --git a/src/OpenFOAM/Make/files b/src/OpenFOAM/Make/files
index cc59794bae..acf60a63d0 100644
--- a/src/OpenFOAM/Make/files
+++ b/src/OpenFOAM/Make/files
@@ -175,6 +175,9 @@ $(hashes)/base64Layer.C
gzstream = $(Streams)/gzstream
$(gzstream)/gzstream.C
+memstream = $(Streams)/memory
+$(memstream)/ListStream.C
+
Fstreams = $(Streams)/Fstreams
$(Fstreams)/IFstream.C
$(Fstreams)/OFstream.C
diff --git a/src/OpenFOAM/db/IOstreams/StringStreams/StringStream.H b/src/OpenFOAM/db/IOstreams/StringStreams/StringStream.H
index cee86b47bb..ab9f335612 100644
--- a/src/OpenFOAM/db/IOstreams/StringStreams/StringStream.H
+++ b/src/OpenFOAM/db/IOstreams/StringStreams/StringStream.H
@@ -79,11 +79,6 @@ protected:
{}
- //- Destructor
- ~StringStreamAllocator()
- {}
-
-
public:
// Public Member Functions
@@ -112,6 +107,8 @@ class IStringStream
public StringStreamAllocator,
public ISstream
{
+ typedef StringStreamAllocator allocator_type;
+
public:
// Constructors
@@ -125,7 +122,7 @@ public:
const Foam::string& name="input"
)
:
- StringStreamAllocator(buffer),
+ allocator_type(buffer),
ISstream(stream_, name, format, version)
{}
@@ -139,7 +136,7 @@ public:
const Foam::string& name="input"
)
:
- StringStreamAllocator(buffer),
+ allocator_type(buffer),
ISstream(stream_, name, format, version)
{}
@@ -147,28 +144,23 @@ public:
//- Construct as copy of content
IStringStream(const IStringStream& str)
:
- StringStreamAllocator(str.str()),
+ allocator_type(str.str()),
ISstream(stream_, str.name(), str.format(), str.version())
{}
- //- Destructor
- ~IStringStream()
- {}
-
-
// Member Functions
- //- Print description to Ostream
- void print(Ostream& os) const;
-
//- Reset the input buffer and rewind the stream
- void reset(const std::string& s)
+ virtual void reset(const std::string& s)
{
this->str(s);
this->rewind();
}
+ //- Print description to Ostream
+ virtual void print(Ostream& os) const;
+
// Member operators
@@ -192,6 +184,8 @@ class OStringStream
public StringStreamAllocator,
public OSstream
{
+ typedef StringStreamAllocator allocator_type;
+
public:
// Constructors
@@ -203,7 +197,7 @@ public:
versionNumber version=currentVersion
)
:
- StringStreamAllocator(),
+ allocator_type(),
OSstream(stream_, "output", format, version)
{}
@@ -211,16 +205,11 @@ public:
//- Construct as copy of content
OStringStream(const OStringStream& str)
:
- StringStreamAllocator(str.str()),
+ allocator_type(str.str()),
OSstream(stream_, str.name(), str.format(), str.version())
{}
- //- Destructor
- ~OStringStream()
- {}
-
-
// Member Functions
//- Reset the output buffer and rewind the stream
@@ -231,14 +220,14 @@ public:
}
//- Rewind the output stream
- void rewind()
+ virtual void rewind()
{
// pubseekpos() instead of seekp() for symmetry with other classes
stream_.rdbuf()->pubseekpos(0, std::ios_base::out);
}
//- Print description to Ostream
- void print(Ostream& os) const;
+ virtual void print(Ostream& os) const;
};
diff --git a/src/OpenFOAM/db/IOstreams/hashes/OSHA1stream.H b/src/OpenFOAM/db/IOstreams/hashes/OSHA1stream.H
index 414259c795..6b9688b73a 100644
--- a/src/OpenFOAM/db/IOstreams/hashes/OSHA1stream.H
+++ b/src/OpenFOAM/db/IOstreams/hashes/OSHA1stream.H
@@ -112,8 +112,6 @@ public:
// Member Functions
- // Access
-
//- This hides both signatures of std::basic_ios::rdbuf()
sha1buf* rdbuf()
{
@@ -155,11 +153,6 @@ protected:
{}
- //- Destructor
- ~OSHA1streamAllocator()
- {}
-
-
public:
// Member Functions
@@ -223,11 +216,6 @@ public:
{}
- //- Destructor
- ~OSHA1stream()
- {}
-
-
// Member functions
//- Clear the SHA1 calculation
diff --git a/src/OpenFOAM/db/IOstreams/memory/BufStreamAllocator.H b/src/OpenFOAM/db/IOstreams/memory/BufStreamAllocator.H
deleted file mode 100644
index 0696e1a943..0000000000
--- a/src/OpenFOAM/db/IOstreams/memory/BufStreamAllocator.H
+++ /dev/null
@@ -1,266 +0,0 @@
-/*---------------------------------------------------------------------------*\
- ========= |
- \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
- \\ / O peration |
- \\ / A nd | Copyright (C) 2016-2017 OpenCFD Ltd.
- \\/ M anipulation |
--------------------------------------------------------------------------------
-License
- This file is part of OpenFOAM.
-
- OpenFOAM 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.
-
- OpenFOAM 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 OpenFOAM. If not, see .
-
-Class
- Foam::BufStreamAllocator
-
-Description
- Helper for memory buffer streams such as UIBufStream, UOBufStream
-
-\*---------------------------------------------------------------------------*/
-
-#ifndef BufStreamAllocator_H
-#define BufStreamAllocator_H
-
-#include
-#include
-
-// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
-
-namespace Foam
-{
-
-/*---------------------------------------------------------------------------*\
- Class memorybuf Declaration
-\*---------------------------------------------------------------------------*/
-
-//- A streambuf class for using externally allocated memory for its buffer
-class memorybuf
-:
- public std::streambuf
-{
-protected:
-
- // Protected members
-
- //- Set position pointer to relative position
- virtual std::streampos seekoff
- (
- std::streamoff off,
- std::ios_base::seekdir way,
- std::ios_base::openmode which = std::ios_base::in|std::ios_base::out
- )
- {
- const bool testin = which & std::ios_base::in;
- const bool testout = which & std::ios_base::out;
-
- if (way == std::ios_base::beg)
- {
- if (testin)
- {
- setg(eback(), eback(), egptr());
- gbump(off);
- }
- if (testout)
- {
- setp(pbase(), epptr());
- pbump(off);
- }
-
- return off;
- }
-
- if (way == std::ios_base::cur)
- {
- if (testin)
- {
- gbump(off);
- }
- if (testout)
- {
- pbump(off);
- }
- }
- else if (way == std::ios_base::end)
- {
- if (testin)
- {
- gbump(off);
- }
- if (testout)
- {
- pbump(off);
- }
- }
-
- if (testin)
- {
- return gptr() - eback();
- }
- if (testout)
- {
- return pptr() - pbase();
- }
-
- return -1;
- }
-
-
- //- Set position pointer to absolute position
- virtual std::streampos seekpos
- (
- std::streampos pos,
- std::ios_base::openmode which = std::ios_base::in|std::ios_base::out
- )
- {
- return seekoff(pos, std::ios_base::beg, which);
- }
-
-
- //- Get sequence of characters
- virtual std::streamsize xsgetn(char* s, std::streamsize n)
- {
- std::streamsize count = 0;
-
- // some optimization could be possible here
- while (count < n && gptr() < egptr())
- {
- *(s + count++) = *(gptr());
- gbump(1);
- }
-
- return count;
- }
-
-
- //- Put sequence of characters
- virtual std::streamsize xsputn(const char* s, std::streamsize n)
- {
- std::streamsize count = 0;
-
- // some optimization could be possible here
- while (count < n && pptr() < epptr())
- {
- *(pptr()) = *(s + count++);
- pbump(1);
- }
-
- return count;
- }
-
-
-public:
-
- // Constructors
-
- //- Construct for specified buffer
- memorybuf(char* buffer, std::streamsize num)
- {
- setg(buffer, buffer, buffer + num);
- setp(buffer, buffer + num);
- }
-
-};
-
-
-/*---------------------------------------------------------------------------*\
- Class BufStreamAllocator Declaration
-\*---------------------------------------------------------------------------*/
-
-//- An stream/stream-buffer allocator for external buffers
-template
-class BufStreamAllocator
-{
- // Private data
-
- //- Storage
- char *storage_;
-
- //- The number of bytes in the storage
- std::streamsize len_;
-
- //- Reference to the underlying buffer
- memorybuf buf_;
-
-protected:
-
- // Protected data
-
- typedef StreamType stream_type;
-
- //- The stream pointer
- stream_type stream_;
-
-
- // Constructors
-
- //- Construct with buffer and number of bytes
- BufStreamAllocator(char *buffer, size_t nbytes)
- :
- storage_(buffer),
- len_(nbytes),
- buf_(storage_, len_),
- stream_(&buf_)
- {}
-
-
- //- Destructor
- ~BufStreamAllocator()
- {
- // Possible cleanup of storage
- if (Manage && storage_)
- {
- delete storage_;
- storage_ = nullptr;
- }
- }
-
-
- // Protected Member Functions
-
-
- //- Position of the get buffer
- std::streampos tellg() const
- {
- return const_cast(stream_).tellg();
- }
-
- //- Position of the put buffer
- std::streampos tellp() const
- {
- return const_cast(stream_).tellp();
- }
-
-
-public:
-
- // Public Member Functions
-
- //- Move to buffer start, clear errors
- void rewind()
- {
- stream_.rdbuf()->pubseekpos(0);
- stream_.clear(); // for safety, clear any old errors
- }
-};
-
-
-// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
-
-} // End namespace Foam
-
-// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
-
-#endif
-
-// ************************************************************************* //
diff --git a/src/OpenFOAM/db/IOstreams/memory/IListStream.H b/src/OpenFOAM/db/IOstreams/memory/IListStream.H
new file mode 100644
index 0000000000..553a803bc3
--- /dev/null
+++ b/src/OpenFOAM/db/IOstreams/memory/IListStream.H
@@ -0,0 +1,245 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
+ \\/ M anipulation |
+-------------------------------------------------------------------------------
+License
+ This file is part of OpenFOAM.
+
+ OpenFOAM 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.
+
+ OpenFOAM 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 OpenFOAM. If not, see .
+
+Class
+ Foam::IListStream
+
+Description
+ An input stream that reads from a List and manages the List storage.
+ Similar to IStringStream but with a List for its storage instead of
+ as string to allow reuse of List contents without copying.
+
+See Also
+ Foam::OListStream
+ Foam::UIListStream
+ Foam::UOListStream
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef IListStream_H
+#define IListStream_H
+
+#include "List.H"
+#include "UIListStream.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+ Class IListStreamAllocator Declaration
+\*---------------------------------------------------------------------------*/
+
+//- An stream/stream-buffer input allocator for with List storage
+class IListStreamAllocator
+:
+ private List,
+ public UIListStreamAllocator
+{
+protected:
+
+ // Constructors
+
+ //- Construct with an empty list
+ IListStreamAllocator()
+ :
+ List(),
+ UIListStreamAllocator(list_storage())
+ {}
+
+ //- Move construct from an existing List
+ IListStreamAllocator(List&& buffer)
+ :
+ List(std::move(buffer)),
+ UIListStreamAllocator(list_storage())
+ {}
+
+
+ //- Move construct from an existing DynamicList
+ template
+ IListStreamAllocator(DynamicList&& buffer)
+ :
+ List(std::move(buffer)),
+ UIListStreamAllocator(list_storage())
+ {}
+
+ //- Transfer (move) construct
+ IListStreamAllocator(const Xfer>& buffer)
+ :
+ List(buffer),
+ UIListStreamAllocator(list_storage())
+ {}
+
+
+ // Protected Member Functions
+
+ //- Convenience method to address the underlying List storage
+ inline List& list_storage()
+ {
+ return static_cast&>(*this);
+ }
+
+public:
+
+ // Member Functions
+
+ //- The current get position in the buffer
+ using UIListStreamAllocator::size;
+
+ //- Clear storage
+ inline void clearStorage()
+ {
+ list_storage().clear();
+ sync_gbuffer_to_list();
+ }
+
+ //- Transfer contents to the Xfer container as a plain List
+ inline Xfer> xfer()
+ {
+ Xfer> moved = list_storage().xfer();
+
+ // Update buffer pointers for remaining (zero) size list
+ sync_gbuffer_to_list(); // or rewind
+
+ return moved;
+ }
+};
+
+
+/*---------------------------------------------------------------------------*\
+ Class IListStream Declaration
+\*----------------------------------------------d-----------------------------*/
+
+//- An ISstream with internal List storage
+class IListStream
+:
+ public IListStreamAllocator,
+ public ISstream
+{
+ typedef IListStreamAllocator allocator_type;
+
+public:
+
+ // Constructors
+
+ //- Construct with an empty list
+ IListStream
+ (
+ streamFormat format=ASCII,
+ versionNumber version=currentVersion,
+ const Foam::string& name="input"
+ )
+ :
+ allocator_type(),
+ ISstream(stream_, name, format, version)
+ {}
+
+
+ //- Move construct from an existing List
+ IListStream
+ (
+ List&& buffer,
+ streamFormat format=ASCII,
+ versionNumber version=currentVersion,
+ const Foam::string& name="input"
+ )
+ :
+ allocator_type(std::move(buffer)),
+ ISstream(stream_, name, format, version)
+ {}
+
+
+ //- Move construct from an existing DynamicList
+ template
+ IListStream
+ (
+ DynamicList&& buffer,
+ streamFormat format=ASCII,
+ versionNumber version=currentVersion,
+ const Foam::string& name="input"
+ )
+ :
+ allocator_type(std::move(buffer)),
+ ISstream(stream_, name, format, version)
+ {}
+
+
+ //- Transfer (move) construct
+ IListStream
+ (
+ const Xfer>& buffer,
+ streamFormat format=ASCII,
+ versionNumber version=currentVersion,
+ const Foam::string& name="input"
+ )
+ :
+ allocator_type(buffer),
+ ISstream(stream_, name, format, version)
+ {}
+
+
+ // Member functions
+
+ //- The current get position in the buffer
+ using allocator_type::size;
+
+
+ //- Return the current get position in the buffer
+ std::streampos pos() const
+ {
+ return allocator_type::tellg();
+ }
+
+ //- Rewind the stream, clearing any old errors
+ virtual void rewind()
+ {
+ allocator_type::rewind();
+ setGood(); // resynchronize with internal state
+ }
+
+
+ //- Print description to Ostream
+ virtual void print(Ostream& os) const;
+
+
+ // Member operators
+
+ //- A non-const reference to const Istream
+ // Needed for read-constructors where the stream argument is temporary
+ Istream& operator()() const
+ {
+ return const_cast(static_cast(*this));
+ }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/db/IOstreams/memory/ListStream.C b/src/OpenFOAM/db/IOstreams/memory/ListStream.C
new file mode 100644
index 0000000000..0275000177
--- /dev/null
+++ b/src/OpenFOAM/db/IOstreams/memory/ListStream.C
@@ -0,0 +1,72 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
+ \\/ M anipulation |
+-------------------------------------------------------------------------------
+License
+ This file is part of OpenFOAM.
+
+ OpenFOAM 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.
+
+ OpenFOAM 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 OpenFOAM. If not, see .
+
+\*---------------------------------------------------------------------------*/
+
+#include "UListStream.H"
+#include "ListStream.H"
+#include "OCountStream.H"
+
+// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
+
+void Foam::IListStream::print(Ostream& os) const
+{
+ os << "IListStream: ";
+ printBufInfo(os);
+ os << Foam::endl;
+}
+
+
+void Foam::UIListStream::print(Ostream& os) const
+{
+ os << "UIListStream: ";
+ printBufInfo(os);
+ os << Foam::endl;
+}
+
+
+void Foam::OListStream::print(Ostream& os) const
+{
+ os << "OListStream: ";
+ printBufInfo(os);
+ os << Foam::endl;
+}
+
+
+void Foam::UOListStream::print(Ostream& os) const
+{
+ os << "UOListStream: ";
+ printBufInfo(os);
+ os << Foam::endl;
+}
+
+
+void Foam::OCountStream::print(Ostream& os) const
+{
+ os << "OCountStream: ";
+ printBufInfo(os);
+ os << Foam::endl;
+}
+
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/db/IOstreams/memory/ListStream.H b/src/OpenFOAM/db/IOstreams/memory/ListStream.H
new file mode 100644
index 0000000000..6ef7518ca0
--- /dev/null
+++ b/src/OpenFOAM/db/IOstreams/memory/ListStream.H
@@ -0,0 +1,37 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
+ \\/ M anipulation |
+-------------------------------------------------------------------------------
+License
+ This file is part of OpenFOAM.
+
+ OpenFOAM 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.
+
+ OpenFOAM 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 OpenFOAM. If not, see .
+
+Description
+ Input/output streams with managed List storage.
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef ListStream_H
+#define ListStream_H
+
+#include "IListStream.H"
+#include "OListStream.H"
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/db/IOstreams/memory/OCountStream.H b/src/OpenFOAM/db/IOstreams/memory/OCountStream.H
index b3ce64b169..3ae0311667 100644
--- a/src/OpenFOAM/db/IOstreams/memory/OCountStream.H
+++ b/src/OpenFOAM/db/IOstreams/memory/OCountStream.H
@@ -52,50 +52,51 @@ class countstreambuf
// Private data
//- The number of bytes
- std::streamsize n_;
+ std::streamsize size_;
protected:
- // Protected members
- //- Put sequence of characters
- virtual std::streamsize xsputn(const char* s, std::streamsize num)
+ //- Simply handle output counting via overflow
+ virtual int overflow(int c = EOF)
+ {
+ if (c != EOF)
{
- n_ += num;
- return num;
+ ++size_;
}
+ return c;
+ }
-
- //- Set position pointer to absolute position
- // For the counter, any positioning is ignored and it always acts like
- // seekpos(0), which resets the count.
- virtual std::streampos seekpos
- (
- std::streampos sp,
- std::ios_base::openmode which = std::ios_base::in|std::ios_base::out
- )
- {
- n_ = 0;
- return 0;
- }
+ //- Set position pointer to absolute position
+ // For the counter, any positioning is ignored and it always acts like
+ // seekpos(0), which resets the count.
+ virtual std::streampos seekpos
+ (
+ std::streampos,
+ std::ios_base::openmode which = std::ios_base::in|std::ios_base::out
+ )
+ {
+ size_ = 0;
+ return 0;
+ }
public:
// Constructors
- //- Construct null
- countstreambuf()
+ //- Construct null, or with precount size
+ countstreambuf(std::streamsize precount=0)
:
- n_(0)
+ size_(precount)
{}
// Access
- //- Get number of bytes counted
+ //- Number of bytes counted
std::streamsize size() const
{
- return n_;
+ return size_;
}
};
@@ -154,6 +155,62 @@ public:
};
+/*---------------------------------------------------------------------------*\
+ Class OCountStreamAllocator Declaration
+\*---------------------------------------------------------------------------*/
+
+//- An stream/stream-buffer allocator for counting
+class OCountStreamAllocator
+{
+protected:
+
+ // Protected data
+
+ typedef std::ostream stream_type;
+
+ //- The stream buffer
+ countstreambuf buf_;
+
+ //- The output stream
+ stream_type stream_;
+
+
+ // Constructors
+
+ //- Construct null, or with precount size
+ OCountStreamAllocator(std::streamsize precount=0)
+ :
+ buf_(precount),
+ stream_(&buf_)
+ {}
+
+
+ // Protected Member Functions
+
+ void printBufInfo(Ostream& os) const
+ {
+ os << "count=" << buf_.size();
+ }
+
+public:
+
+ // Member Functions
+
+ //- The number of bytes counted
+ std::streamsize size() const
+ {
+ return buf_.size();
+ }
+
+ //- Rewind the stream, reset the count
+ void rewind()
+ {
+ buf_.pubseekpos(0);
+ stream_.clear(); // for safety, clear any old errors
+ }
+};
+
+
/*---------------------------------------------------------------------------*\
Class OCountStream Declaration
\*---------------------------------------------------------------------------*/
@@ -161,17 +218,10 @@ public:
//- An output stream for calculating byte counts
class OCountStream
:
- private ocountstream,
+ public OCountStreamAllocator,
public OSstream
{
-
- // Private Member Functions
-
- //- Disallow default bitwise copy construct
- OCountStream(const OCountStream&) = delete;
-
- //- Disallow default bitwise assignment
- void operator=(const OCountStream&) = delete;
+ typedef OCountStreamAllocator allocator_type;
public:
@@ -184,39 +234,30 @@ public:
versionNumber version=currentVersion
)
:
- ocountstream(),
- OSstream
- (
- static_cast(*this),
- "output",
- format,
- version
- )
+ allocator_type(),
+ OSstream(stream_, "output", format, version)
{}
-
- //- Destructor
- ~OCountStream()
- {}
+ //- Copy construct
+ OCountStream(const OCountStream& os)
+ :
+ allocator_type(os.size()),
+ OSstream(stream_, os.name(), os.format(), os.version())
+ {}
// Member functions
- // Access
-
- //- Return the number of bytes counted
- using ocountstream::size;
-
-
- // Edit
-
//- Rewind the stream, reset the count, clearing any old errors
- void rewind()
+ virtual void rewind()
{
- ocountstream::rewind();
+ allocator_type::rewind();
setGood(); // resynchronize with internal state
}
+ //- Print description to Ostream
+ virtual void print(Ostream& os) const;
+
};
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
diff --git a/src/OpenFOAM/db/IOstreams/memory/OListStream.H b/src/OpenFOAM/db/IOstreams/memory/OListStream.H
index b76b7f6f7f..756394e6fa 100644
--- a/src/OpenFOAM/db/IOstreams/memory/OListStream.H
+++ b/src/OpenFOAM/db/IOstreams/memory/OListStream.H
@@ -25,16 +25,27 @@ Class
Foam::OListStream
Description
- An output stream that writes to a DynamicList.
+ An output stream that writes to a List and manages the List storage.
+ Similar to OStringStream but with a List for its storage instead of
+ as string to allow reuse of List contents without copying.
+
+ The default list size is 512 with a 256 byte block increment.
+ These values can be changed on construction of via the
+ reserve() and setBlockSize() methods.
+
+See Also
+ Foam::IListStream
+ Foam::UOListStream
+ Foam::UIListStream
\*---------------------------------------------------------------------------*/
#ifndef OListStream_H
#define OListStream_H
-#include
#include "DynamicList.H"
#include "OSstream.H"
+#include "memoryStreamBuffer.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@@ -48,206 +59,210 @@ class OListStreamAllocator;
Class OListStreamAllocator Declaration
\*---------------------------------------------------------------------------*/
-//- An stream/stream-buffer allocator for external buffers
+//- An stream/stream-buffer output allocator for lists
class OListStreamAllocator
{
- //- A streambuf adapter to output to a DynamicList
- class olistbuf
+ //- A streambuf adapter to output to a List
+ class listbuf
:
- public std::streambuf
+ public memorybuf::output
{
friend OListStreamAllocator;
- //- Underlying list storage
- DynamicList storage_;
-
-
- //- Adjust buffer pointers to agree with list sizes
- inline void syncBufferPointers()
+ //- Helper for setting the block size.
+ // Small list minimum of 64 bytes.
+ static int min_size(int n)
{
- setp(storage_.data(), storage_.data() + storage_.capacity());
- pbump(storage_.size());
+ return max(64, n);
}
- //- Adjust addressed list size to agree with buffer pointers
- inline void syncListSize()
- {
- storage_.setSize(pptr() - pbase());
- }
+ //- Block size when resizing the list
+ int block_ = 256;
+
+ //- Underlying list storage.
+ // Internally manage like a DynamicList, but the addressable size
+ // is known through the stream pointers.
+ List storage_;
protected:
- // Protected members
-
- //- Set position pointer to relative position
- virtual std::streampos seekoff
- (
- std::streamoff off,
- std::ios_base::seekdir way,
- std::ios_base::openmode which = std::ios_base::out
- )
+ //- Increment capacity directly and
+ // adjust buffer pointers to agree with list dimensions
+ inline void minCapacity
+ (
+ const std::streamsize n,
+ const std::streamsize cur = 0
+ )
+ {
+ const auto newEnd = n + cur;
+ if (newEnd > storage_.size())
{
- const bool testout = which & std::ios_base::out;
+ auto newCapacity =
+ (
+ (storage_.size() + block_)
+ - (storage_.size() % block_)
+ );
- if (way == std::ios_base::beg)
+ while (newCapacity < newEnd)
{
- if (testout)
- {
- setp(pbase(), epptr());
- pbump(off);
- }
-
- return off;
+ newCapacity += block_;
}
- if (way == std::ios_base::cur)
- {
- if (testout)
- {
- pbump(off);
- }
- }
- else if (way == std::ios_base::end)
- {
- if (testout)
- {
- pbump(off);
- }
- }
+ // Info<<"request:" << newEnd
+ // << " cur cap:" << storage_.size()
+ // << " new cap:" << newCapacity
+ // << " pos:" << cur
+ // << " incr:" << incr << endl;
- if (testout)
- {
- return pptr() - pbase();
- }
+ storage_.setSize(newCapacity);
+ sync_pbuffer_to_list();
+ pbump(cur);
+ }
+ }
- return -1;
+ //- Define new increment
+ inline void setBlockSize(const int i)
+ {
+ const auto prev = block_;
+ block_ = min_size(i);
+
+ if (block_ > prev)
+ {
+ minCapacity(0, tellp());
+ }
+ }
+
+ //- Handle overflow
+ virtual int overflow(int c = EOF)
+ {
+ if (c != EOF)
+ {
+ // Need another output block
+ minCapacity(block_, tellp());
+
+ *(pptr()) = c;
+ pbump(1);
+ }
+ return c;
+ }
+
+
+ //- Put sequence of characters
+ virtual std::streamsize xsputn(const char* s, std::streamsize n)
+ {
+ // Enough space so that appends work without problem
+ minCapacity(n, tellp());
+
+ std::streamsize count = 0;
+ while (count < n && pptr() < epptr())
+ {
+ *(pptr()) = *(s + count++);
+ pbump(1);
}
+ return count;
+ }
- //- Set position pointer to absolute position
- virtual std::streampos seekpos
- (
- std::streampos pos,
- std::ios_base::openmode which = std::ios_base::out
- )
- {
- if (which & std::ios_base::out)
- {
- setp(pbase(), epptr());
- pbump(pos);
-
- return pptr() - pbase();
- }
-
- return -1;
- }
-
-
- //- Put sequence of characters
- virtual std::streamsize xsputn(const char* s, std::streamsize n)
- {
- const std::streamsize newlen = n + storage_.size();
-
- if (newlen > storage_.capacity())
- {
- // Either use reserve(), or setCapacity() directly
- // with finer control over growth
- storage_.reserve(newlen);
- syncBufferPointers();
- }
-
- std::streamsize count = 0;
- while (count < n && pptr() < epptr())
- {
- *(pptr()) = *(s + count++);
- pbump(1);
- }
-
- // Synchronize list size with output
- syncListSize();
-
- return count;
- }
+ //- Initialize put buffer
+ void init_pbuffer(const std::streamsize n)
+ {
+ set_pbuffer(storage_);
+ minCapacity(n);
+ }
public:
- // Constructors
+ // Constructors
- //- Construct with an empty list
- olistbuf()
- :
- storage_(1024)
- {
- syncBufferPointers();
- }
+ //- Construct with an empty list, or specified number of reserved bytes
+ listbuf(size_t nbytes = 512)
+ :
+ storage_()
+ {
+ init_pbuffer(min_size(nbytes));
+ }
+
+ //- Move construct content from an existing List
+ listbuf(List&& buffer)
+ :
+ storage_(std::move(buffer))
+ {
+ init_pbuffer(block_);
+ }
+
+ //- Move construct content from an existing DynamicList
+ template
+ listbuf(DynamicList&& buffer)
+ :
+ storage_(std::move(buffer))
+ {
+ init_pbuffer(block_);
+ }
+
+ //- Transfer (move) construct
+ listbuf(const Xfer>& buffer)
+ :
+ storage_(buffer)
+ {
+ init_pbuffer(block_);
+ }
- //- Construct with a specified number of reserved bytes
- olistbuf(size_t nbytes)
- :
- storage_()
- {
- storage_.reserve(std::max(label(nbytes),1024));
- syncBufferPointers();
- }
+ // Member Functions
+ //- Return the current list output capacity
+ inline label capacity() const
+ {
+ return storage_.size();
+ }
- //- Move construct from an existing List
- olistbuf(List&& buffer)
- :
- storage_(std::move(buffer))
- {
- syncBufferPointers();
- }
+ //- Sync put buffer pointers to agree with list dimensions
+ inline void sync_pbuffer_to_list()
+ {
+ set_pbuffer(storage_);
+ }
+ //- Clear storage
+ inline void clearStorage()
+ {
+ storage_.clear();
+ sync_pbuffer_to_list();
+ }
- //- Move construct from an existing DynamicList
- template
- olistbuf(DynamicList&& buffer)
- :
- storage_(std::move(buffer))
- {
- syncBufferPointers();
- }
+ //- Shrink to addressed storage
+ inline void shrink()
+ {
+ const auto cur = tellp();
+ storage_.setSize(cur);
+ sync_pbuffer_to_list();
+ pbump(cur);
+ }
};
-
- // Private data
-
- //- Reference to the underlying buffer
- olistbuf buf_;
-
-
protected:
// Protected data
typedef std::ostream stream_type;
- //- The output stream
+ //- The stream buffer
+ listbuf buf_;
+
+ //- The stream
stream_type stream_;
// Constructors
- //- Construct with an empty list
- OListStreamAllocator()
- :
- buf_(),
- stream_(&buf_)
- {}
-
-
- //- Construct with a specified number of reserved bytes
- OListStreamAllocator(size_t nbytes)
+ //- Construct with an empty list or specified number of reserved bytes
+ OListStreamAllocator(size_t nbytes = 512)
:
buf_(nbytes),
stream_(&buf_)
{}
-
//- Move construct from an existing List
OListStreamAllocator(List&& buffer)
:
@@ -255,7 +270,6 @@ protected:
stream_(&buf_)
{}
-
//- Move construct from an existing DynamicList
template
OListStreamAllocator(DynamicList&& buffer)
@@ -264,71 +278,117 @@ protected:
stream_(&buf_)
{}
+ //- Transfer (move) construct
+ OListStreamAllocator(const Xfer>& buffer)
+ :
+ buf_(buffer),
+ stream_(&buf_)
+ {}
- //- Destructor
- ~OListStreamAllocator()
- {}
+ // Protected Member Functions
+
+ void printBufInfo(Ostream& os) const
+ {
+ os << "pos=" << buf_.tellp()
+ << " capacity=" << buf_.capacity()
+ << " block=" << buf_.block_;
+ }
public:
// Member Functions
- //- Content as a list of characters
- UList list() const
+ //- The current list output capacity
+ inline label capacity() const
+ {
+ return buf_.capacity();
+ }
+
+
+ //- Reserve output space for at least this amount.
+ inline void reserve(const std::streamsize n)
+ {
+ // Also maintain current position when resizing
+ const auto cur = buf_.tellp();
+ if (n > cur)
+ {
+ buf_.minCapacity(n - cur, cur);
+ }
+ }
+
+
+ //- Adjust block size for output
+ inline void setBlockSize(int n)
+ {
+ return buf_.setBlockSize(n);
+ }
+
+
+ //- The current output position in the buffer,
+ // which is also the addressed list size
+ inline label size() const
+ {
+ return buf_.tellp();
+ }
+
+
+ //- Const access to written contents as a list of characters
+ inline const UList list() const
{
return UList
(
const_cast(buf_.storage_.cdata()),
- buf_.storage_.size()
+ buf_.tellp()
);
}
- //- Content as a list of characters
- UList& list()
+ //- Non-const access to written contents as a list of characters
+ inline UList list()
{
- return static_cast&>(buf_.storage_);
- }
-
- //- Return the current list capacity
- inline label capacity() const
- {
- return buf_.storage_.capacity();
+ return UList(buf_.storage_.data(), buf_.tellp());
}
- //- Reserve allocation space for at least this size.
- inline void reserve(const label nElem)
+ //- Transfer contents to the Xfer container as a plain List
+ inline Xfer> xfer()
{
- buf_.storage_.reserve(nElem);
- buf_.syncBufferPointers();
- }
-
-
- //- Return the current output position in the buffer
- // The same as the DynamicList::size()
- std::streampos size() const
- {
- return const_cast(stream_).tellp();
+ buf_.shrink(); // Shrink to addressed area
+ auto lst = buf_.storage_.xfer();
+ buf_.sync_pbuffer_to_list();
+ return lst;
}
//- Move to buffer start, clear errors
void rewind()
{
- buf_.storage_.clear();
- buf_.syncBufferPointers();
+ buf_.pubseekpos(0, std::ios_base::out);
stream_.clear(); // for safety, clear any old errors
}
+
+ //- Shrink to addressed space, should not affect stream.
+ inline void shrink()
+ {
+ buf_.shrink();
+ }
+
+ //- Clear storage
+ void clearStorage()
+ {
+ buf_.clearStorage();
+ stream_.clear(); // for safety, clear any old errors
+ }
+
};
/*---------------------------------------------------------------------------*\
Class OListStream Declaration
-\*----------------------------------------------d-----------------------------*/
+\*---------------------------------------------------------------------------*/
-//- An OSstream attached a DynamicList
+//- An OSstream attached to a List
class OListStream
:
public OListStreamAllocator,
@@ -348,7 +408,7 @@ public:
)
:
allocator_type(),
- OSstream(stream_, "output", format,version)
+ OSstream(stream_, "output", format, version)
{}
@@ -391,16 +451,30 @@ public:
OSstream(stream_, "output", format, version)
{}
-
- //- Destructor
- ~OListStream()
- {}
+ //- Transfer (move) construct
+ OListStream
+ (
+ const Xfer>& buffer,
+ streamFormat format=ASCII,
+ versionNumber version=currentVersion
+ )
+ :
+ allocator_type(buffer),
+ OSstream(stream_, "output", format, version)
+ {}
// Member functions
//- Rewind the stream, clearing any old errors
- using allocator_type::rewind;
+ virtual void rewind()
+ {
+ allocator_type::rewind();
+ setGood(); // resynchronize with internal state
+ }
+
+ //- Print description to Ostream
+ virtual void print(Ostream& os) const;
};
diff --git a/src/OpenFOAM/db/IOstreams/memory/UIBufStream.H b/src/OpenFOAM/db/IOstreams/memory/UIListStream.H
similarity index 52%
rename from src/OpenFOAM/db/IOstreams/memory/UIBufStream.H
rename to src/OpenFOAM/db/IOstreams/memory/UIListStream.H
index e02929f181..e7db211c1d 100644
--- a/src/OpenFOAM/db/IOstreams/memory/UIBufStream.H
+++ b/src/OpenFOAM/db/IOstreams/memory/UIListStream.H
@@ -22,7 +22,7 @@ License
along with OpenFOAM. If not, see .
Class
- Foam::UIBufStream
+ Foam::UIListStream
Description
Similar to IStringStream but using an externally managed buffer for its
@@ -41,7 +41,7 @@ Description
buffer.setSize(nread); // content size
// construct dictionary, or something else
- UIBufStream is(buffer)
+ UIListStream is(buffer)
dictionary dict1(is);
// sometime later
@@ -49,16 +49,23 @@ Description
buffer.setSize(nread); // content size
// without intermediate variable
- dictionary dict2(UIBufStream(buffer)());
+ dictionary dict2(UIListStream(buffer)());
\endcode
+See Also
+ Foam::IListStream
+ Foam::OListStream
+ Foam::UOListStream
+
\*---------------------------------------------------------------------------*/
-#ifndef UIBufStream_H
-#define UIBufStream_H
+#ifndef UIListStream_H
+#define UIListStream_H
-#include "BufStreamAllocator.H"
+#include "FixedList.H"
+#include "UList.H"
#include "ISstream.H"
+#include "memoryStreamBuffer.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@@ -66,22 +73,149 @@ namespace Foam
{
/*---------------------------------------------------------------------------*\
- Class UIBufStream Declaration
+ Class UIListAllocator Declaration
\*---------------------------------------------------------------------------*/
-class UIBufStream
+//- An stream/stream-buffer input allocator for a externally allocated lists
+class UIListStreamAllocator
+{
+ //- A streambuf class for input from UList or equivalent
+ class ulistbuf
+ :
+ public memorybuf::input
+ {
+ friend UIListStreamAllocator;
+
+ //- Underlying list storage
+ UList list_;
+
+ public:
+
+ //- Construct for specified buffer
+ ulistbuf(UList& buffer)
+ :
+ list_(buffer)
+ {
+ set_gbuffer(list_);
+ }
+
+ //- Construct for specified buffer
+ ulistbuf(char* buffer, std::streamsize num)
+ :
+ list_(buffer, num)
+ {
+ set_gbuffer(list_);
+ }
+
+ //- Sync get buffer pointers to agree with list dimensions
+ inline void sync_gbuffer_to_list()
+ {
+ set_gbuffer(list_);
+ }
+ };
+
+protected:
+
+ // Protected data
+
+ typedef std::istream stream_type;
+
+ //- The stream buffer
+ ulistbuf buf_;
+
+ //- The stream
+ stream_type stream_;
+
+
+ // Constructors
+
+ //- Construct with list buffer
+ UIListStreamAllocator(UList& list)
+ :
+ buf_(list),
+ stream_(&buf_)
+ {}
+
+ //- Construct with buffer and number of bytes
+ UIListStreamAllocator(char *buffer, size_t nbytes)
+ :
+ buf_(buffer, nbytes),
+ stream_(&buf_)
+ {}
+
+
+ // Protected Member Functions
+
+ //- Sync get buffer pointers to agree with list dimensions
+ inline void sync_gbuffer_to_list()
+ {
+ buf_.sync_gbuffer_to_list();
+ }
+
+ void printBufInfo(Ostream& os) const
+ {
+ os << "pos=" << buf_.tellg()
+ << " size=" << buf_.list_.size();
+ }
+
+public:
+
+ // Public Member Functions
+
+ //- Const access to available contents as a list of characters
+ inline const UList& list() const
+ {
+ return buf_.list_;
+ }
+
+
+ //- Non-const access to available contents as a list of characters
+ inline UList list()
+ {
+ return buf_.list_;
+ }
+
+
+ //- The list size
+ inline label size() const
+ {
+ return buf_.list_.size();
+ }
+
+
+ //- Position of the get buffer
+ std::streampos tellg() const
+ {
+ return buf_.tellg();
+ }
+
+
+ //- Move to buffer start, clear errors
+ void rewind()
+ {
+ buf_.pubseekpos(0, std::ios_base::in);
+ stream_.clear(); // for safety, clear any old errors
+ }
+};
+
+
+/*---------------------------------------------------------------------------*\
+ Class UIListStream Declaration
+\*---------------------------------------------------------------------------*/
+
+class UIListStream
:
- public BufStreamAllocator,
+ public UIListStreamAllocator,
public ISstream
{
- typedef BufStreamAllocator allocator_type;
+ typedef UIListStreamAllocator allocator_type;
public:
// Constructors
//- Construct using specified buffer and number of bytes
- UIBufStream
+ UIListStream
(
const char* buffer,
size_t nbytes,
@@ -95,8 +229,21 @@ public:
{}
+ //- Construct using data area from a FixedList
+ template
+ UIListStream
+ (
+ const FixedList& buffer,
+ streamFormat format=ASCII,
+ versionNumber version=currentVersion,
+ const Foam::string& name="input"
+ )
+ :
+ UIListStream(buffer.cdata(), FixedSize, format, version, name)
+ {}
+
//- Construct using data area from a List and number of bytes
- UIBufStream
+ UIListStream
(
const UList& buffer,
label size,
@@ -105,13 +252,13 @@ public:
const Foam::string& name="input"
)
:
- UIBufStream(buffer.cdata(), size, format,version,name)
+ UIListStream(buffer.cdata(), size, format, version, name)
{}
//- Construct using data area from a List and its inherent storage size
// Uses addressed size, thus no special treatment for a DynamicList
- UIBufStream
+ UIListStream
(
const UList& buffer,
streamFormat format=ASCII,
@@ -119,15 +266,10 @@ public:
const Foam::string& name="input"
)
:
- UIBufStream(buffer.cdata(), buffer.size(), format,version,name)
+ UIListStream(buffer.cdata(), buffer.size(), format, version, name)
{}
- //- Destructor
- ~UIBufStream()
- {}
-
-
// Member functions
//- Return the current get position in the buffer
@@ -145,6 +287,10 @@ public:
}
+ //- Print description to Ostream
+ virtual void print(Ostream& os) const;
+
+
// Member operators
//- A non-const reference to const Istream
diff --git a/src/OpenFOAM/db/IOstreams/memory/UListStream.H b/src/OpenFOAM/db/IOstreams/memory/UListStream.H
new file mode 100644
index 0000000000..132dc81212
--- /dev/null
+++ b/src/OpenFOAM/db/IOstreams/memory/UListStream.H
@@ -0,0 +1,37 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2017 OpenCFD Ltd.
+ \\/ M anipulation |
+-------------------------------------------------------------------------------
+License
+ This file is part of OpenFOAM.
+
+ OpenFOAM 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.
+
+ OpenFOAM 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 OpenFOAM. If not, see .
+
+Description
+ Input/output streams with externally managed storage.
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef UListStream_H
+#define UListStream_H
+
+#include "UIListStream.H"
+#include "UOListStream.H"
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/db/IOstreams/memory/UOBufStream.H b/src/OpenFOAM/db/IOstreams/memory/UOListStream.H
similarity index 52%
rename from src/OpenFOAM/db/IOstreams/memory/UOBufStream.H
rename to src/OpenFOAM/db/IOstreams/memory/UOListStream.H
index 6a8df54e7a..5500fb5383 100644
--- a/src/OpenFOAM/db/IOstreams/memory/UOBufStream.H
+++ b/src/OpenFOAM/db/IOstreams/memory/UOListStream.H
@@ -22,7 +22,7 @@ License
along with OpenFOAM. If not, see .
Class
- Foam::UOBufStream
+ Foam::UOListStream
Description
Similar to OStringStream but using an externally managed buffer for
@@ -38,7 +38,7 @@ Description
DynamicList buffer(4096); // allocate some large buffer
{
- UOBufStream os(buffer);
+ UOListStream os(buffer);
os << "content1" << " and more content";
buffer.setSize(os.size()); // synchronize sizes
}
@@ -46,12 +46,12 @@ Description
something.write(buffer, buffer.size());
\endcode
- Although the UOBufStream is quite lightweight, there may be cases
+ Although the UOListStream is quite lightweight, there may be cases
where it is preferable to reuse the stream as well.
\code
DynamicList buffer(4096); // allocate some large buffer
- UOBufStream os(buffer);
+ UOListStream os(buffer);
os << "content1" << " and more content";
buffer.setSize(os.size()); // synchronize sizes
@@ -70,41 +70,171 @@ Description
something.write(buffer, os.size());
\endcode
+See Also
+ Foam::IListStream
+ Foam::OListStream
+ Foam::UIListStream
+
\*---------------------------------------------------------------------------*/
-#ifndef UOBufStream_H
-#define UOBufStream_H
+#ifndef UOListStream_H
+#define UOListStream_H
-#include "BufStreamAllocator.H"
+#include "DynamicList.H"
+#include "FixedList.H"
#include "OSstream.H"
+#include "memoryStreamBuffer.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
-// Forward declaration
-template class DynamicList;
+/*---------------------------------------------------------------------------*\
+ Class UOListAllocator Declaration
+\*---------------------------------------------------------------------------*/
+
+//- An stream/stream-buffer allocator for external buffers
+class UOListAllocator
+{
+ //- A streambuf adapter for output to UList or equivalent
+ class ulistbuf
+ :
+ public memorybuf::output
+ {
+ friend UOListAllocator;
+
+ //- Underlying list storage
+ UList list_;
+
+ public:
+
+ // Constructors
+
+ //- Construct for specified buffer
+ ulistbuf(char* buffer, std::streamsize num)
+ :
+ list_(buffer, num)
+ {
+ set_pbuffer(list_);
+ }
+
+
+ // Member Functions
+
+ //- Return the current list output capacity
+ inline label capacity() const
+ {
+ return list_.size();
+ }
+
+ //- Sync put buffer pointers to agree with list dimensions
+ inline void sync_pbuffer_to_list()
+ {
+ set_pbuffer(list_);
+ }
+ };
+
+
+protected:
+
+ // Protected data
+
+ typedef std::ostream stream_type;
+
+ //- The stream buffer
+ ulistbuf buf_;
+
+ //- The stream
+ stream_type stream_;
+
+
+ // Constructors
+
+ //- Construct with buffer and number of bytes
+ UOListAllocator(char *buffer, size_t nbytes)
+ :
+ buf_(buffer, nbytes),
+ stream_(&buf_)
+ {}
+
+
+ // Protected Member Functions
+
+ void printBufInfo(Ostream& os) const
+ {
+ os << "pos=" << buf_.tellp()
+ << " capacity=" << buf_.capacity();
+ }
+
+public:
+
+ // Public Member Functions
+
+ //- The current list output capacity
+ inline label capacity() const
+ {
+ return buf_.capacity();
+ }
+
+
+ //- The current output position in the buffer,
+ // which is also the addressed list size
+ inline label size() const
+ {
+ return buf_.tellp();
+ }
+
+
+ //- Const access to written contents as a list of characters
+ inline const UList list() const
+ {
+ return UList
+ (
+ const_cast(buf_.list_.cdata()),
+ buf_.tellp()
+ );
+ }
+
+
+ //- Non-const access to written contents as a list of characters
+ inline UList list()
+ {
+ return UList
+ (
+ const_cast(buf_.list_.cdata()),
+ buf_.tellp()
+ );
+ }
+
+
+ //- Move to buffer start, clear errors
+ void rewind()
+ {
+ buf_.pubseekpos(0, std::ios_base::out);
+ stream_.clear(); // for safety, clear any old errors
+ }
+};
/*---------------------------------------------------------------------------*\
- Class UOBufStream Declaration
+ Class UOListStream Declaration
\*---------------------------------------------------------------------------*/
//- An OSstream attached to an unallocated external buffer
-class UOBufStream
+class UOListStream
:
- public BufStreamAllocator,
+ public UOListAllocator,
public OSstream
{
- typedef BufStreamAllocator allocator_type;
+ typedef UOListAllocator allocator_type;
public:
// Constructors
//- Construct using specified buffer and number of bytes
- UOBufStream
+ UOListStream
(
char* buffer,
size_t nbytes,
@@ -113,12 +243,12 @@ public:
)
:
allocator_type(buffer, nbytes),
- OSstream(stream_, "output", format,version)
+ OSstream(stream_, "output", format, version)
{}
//- Construct using data area from a List and number of bytes
- UOBufStream
+ UOListStream
(
UList& buffer,
size_t size,
@@ -126,56 +256,58 @@ public:
versionNumber version=currentVersion
)
:
- UOBufStream(buffer.data(), size, format,version)
+ UOListStream(buffer.data(), size, format, version)
{}
+ //- Construct using data area from a FixedList
+ template
+ UOListStream
+ (
+ FixedList& buffer,
+ streamFormat format=ASCII,
+ versionNumber version=currentVersion
+ )
+ :
+ UOListStream(buffer.data(), FixedSize, format, version)
+ {}
//- Construct using data area from a List and its inherent storage size
- UOBufStream
+ UOListStream
(
UList& buffer,
streamFormat format=ASCII,
versionNumber version=currentVersion
)
:
- UOBufStream(buffer.data(), buffer.size(), format,version)
+ UOListStream(buffer.data(), buffer.size(), format, version)
{}
//- Construct using data area from a DynamicList and its capacity
template
- UOBufStream
+ UOListStream
(
DynamicList& buffer,
streamFormat format=ASCII,
versionNumber version=currentVersion
)
:
- UOBufStream(buffer.data(), buffer.capacity(), format,version)
+ UOListStream(buffer.data(), buffer.capacity(), format, version)
{}
- //- Destructor
- ~UOBufStream()
- {}
-
-
// Member functions
- //- Return the current output position in the buffer
- std::streampos size() const
- {
- return allocator_type::tellp();
- }
-
-
//- Rewind the stream, clearing any old errors
- void rewind()
+ virtual void rewind()
{
allocator_type::rewind();
setGood(); // resynchronize with internal state
}
+ //- Print description to Ostream
+ virtual void print(Ostream& os) const;
+
};
diff --git a/src/OpenFOAM/db/IOstreams/memory/memoryStreamBuffer.H b/src/OpenFOAM/db/IOstreams/memory/memoryStreamBuffer.H
new file mode 100644
index 0000000000..d0f412f1a4
--- /dev/null
+++ b/src/OpenFOAM/db/IOstreams/memory/memoryStreamBuffer.H
@@ -0,0 +1,224 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2016-2017 OpenCFD Ltd.
+ \\/ M anipulation |
+-------------------------------------------------------------------------------
+License
+ This file is part of OpenFOAM.
+
+ OpenFOAM 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.
+
+ OpenFOAM 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 OpenFOAM. If not, see .
+
+Class
+ Foam::memorybuf
+
+Description
+ A std::streambuf used for memory buffer streams such as
+ UIListStream, UOListStream, etc.
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef memoryStreamBuffer_H
+#define memoryStreamBuffer_H
+
+#include "UList.H"
+#include
+#include
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+ Class memorybuf Declaration
+\*---------------------------------------------------------------------------*/
+
+//- A streambuf for memory
+class memorybuf
+:
+ public std::streambuf
+{
+protected:
+
+ //- Set position pointer to relative position
+ virtual std::streampos seekoff
+ (
+ std::streamoff off,
+ std::ios_base::seekdir way,
+ std::ios_base::openmode which = std::ios_base::in|std::ios_base::out
+ )
+ {
+ const bool testin = which & std::ios_base::in;
+ const bool testout = which & std::ios_base::out;
+
+ if (way == std::ios_base::beg)
+ {
+ if (testin)
+ {
+ setg(eback(), eback(), egptr());
+ gbump(off);
+ }
+ if (testout)
+ {
+ setp(pbase(), epptr());
+ pbump(off);
+ }
+ }
+ else if (way == std::ios_base::cur)
+ {
+ if (testin)
+ {
+ gbump(off);
+ }
+ if (testout)
+ {
+ pbump(off);
+ }
+ }
+ else if (way == std::ios_base::end)
+ {
+ if (testin)
+ {
+ setg(eback(), eback(), egptr());
+ gbump(egptr() - eback() - off);
+ }
+ if (testout)
+ {
+ setp(pbase(), epptr());
+ pbump(epptr() - pbase() - off);
+ }
+ }
+
+ if (testin)
+ {
+ return (gptr() - eback()); // tellg()
+ }
+ if (testout)
+ {
+ return (pptr() - pbase()); // tellp()
+ }
+
+ return -1;
+ }
+
+
+ //- Set position pointer to absolute position
+ virtual std::streampos seekpos
+ (
+ std::streampos pos,
+ std::ios_base::openmode which = std::ios_base::in|std::ios_base::out
+ )
+ {
+ return seekoff(pos, std::ios_base::beg, which);
+ }
+
+
+public:
+
+ // Forward declarations
+ class input;
+ class output;
+};
+
+
+/*---------------------------------------------------------------------------*\
+ Class memorybuf::input Declaration
+\*---------------------------------------------------------------------------*/
+
+//- An output streambuf for memory access
+class memorybuf::input
+:
+ public memorybuf
+{
+protected:
+
+ //- Get sequence of characters
+ virtual std::streamsize xsgetn(char* s, std::streamsize n)
+ {
+ std::streamsize count = 0;
+
+ while (count < n && gptr() < egptr())
+ {
+ *(s + count++) = *(gptr());
+ gbump(1);
+ }
+
+ return count;
+ }
+
+
+ //- The buffer get position
+ inline std::streamsize tellg() const
+ {
+ return (gptr() - eback());
+ }
+
+ //- Sync get buffer pointers to agree with list dimensions
+ inline void set_gbuffer(UList& list)
+ {
+ setg(list.begin(), list.begin(), list.end());
+ }
+};
+
+
+/*---------------------------------------------------------------------------*\
+ Class memorybuf::output Declaration
+\*---------------------------------------------------------------------------*/
+
+//- An output streambuf for memory access
+class memorybuf::output
+:
+ public memorybuf
+{
+protected:
+
+ //- Put sequence of characters
+ virtual std::streamsize xsputn(const char* s, std::streamsize n)
+ {
+ std::streamsize count = 0;
+ while (count < n && pptr() < epptr())
+ {
+ *(pptr()) = *(s + count++);
+ pbump(1);
+ }
+
+ return count;
+ }
+
+ //- The buffer put position
+ inline std::streamsize tellp() const
+ {
+ return (pptr() - pbase());
+ }
+
+ //- Sync put buffer pointers to agree with list dimensions
+ inline void set_pbuffer(UList& list)
+ {
+ setp(list.begin(), list.end());
+ }
+
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //