diff options
| author | Bob Jamison <ishmalius@gmail.com> | 2006-04-12 13:25:21 +0000 |
|---|---|---|
| committer | ishmal <ishmal@users.sourceforge.net> | 2006-04-12 13:25:21 +0000 |
| commit | 6fd9af13a8614a4b95e8be1518e745915ef8bb56 (patch) | |
| tree | bf94fa5f7c3a7b2f581f3e7cf2522bf7c2d4b6c9 /src/dom/io | |
| parent | Removed file/folder for ishmal (diff) | |
| download | inkscape-6fd9af13a8614a4b95e8be1518e745915ef8bb56.tar.gz inkscape-6fd9af13a8614a4b95e8be1518e745915ef8bb56.zip | |
Add new rearranged /dom directory
(bzr r479)
Diffstat (limited to 'src/dom/io')
| -rw-r--r-- | src/dom/io/base64stream.cpp | 339 | ||||
| -rw-r--r-- | src/dom/io/base64stream.h | 146 | ||||
| -rw-r--r-- | src/dom/io/bufferstream.cpp | 166 | ||||
| -rw-r--r-- | src/dom/io/bufferstream.h | 133 | ||||
| -rw-r--r-- | src/dom/io/domstream.cpp | 878 | ||||
| -rw-r--r-- | src/dom/io/domstream.h | 680 | ||||
| -rw-r--r-- | src/dom/io/gzipstream.cpp | 245 | ||||
| -rw-r--r-- | src/dom/io/gzipstream.h | 125 | ||||
| -rw-r--r-- | src/dom/io/httpclient.cpp | 167 | ||||
| -rw-r--r-- | src/dom/io/httpclient.h | 115 | ||||
| -rw-r--r-- | src/dom/io/socket.cpp | 618 | ||||
| -rw-r--r-- | src/dom/io/socket.h | 112 | ||||
| -rw-r--r-- | src/dom/io/stringstream.cpp | 158 | ||||
| -rw-r--r-- | src/dom/io/stringstream.h | 129 | ||||
| -rw-r--r-- | src/dom/io/uristream.cpp | 502 | ||||
| -rw-r--r-- | src/dom/io/uristream.h | 213 |
16 files changed, 4726 insertions, 0 deletions
diff --git a/src/dom/io/base64stream.cpp b/src/dom/io/base64stream.cpp new file mode 100644 index 000000000..880ad5a8e --- /dev/null +++ b/src/dom/io/base64stream.cpp @@ -0,0 +1,339 @@ +/**
+ * Phoebe DOM Implementation.
+ *
+ * Base64-enabled input and output streams
+ *
+ * This class allows easy encoding and decoding
+ * of Base64 data with a stream interface, hiding
+ * the implementation from the user.
+ *
+ * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html
+ *
+ * Authors:
+ * Bob Jamison
+ *
+ * Copyright (C) 2006 Bob Jamison
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+
+
+#include "base64stream.h"
+
+
+namespace org
+{
+namespace w3c
+{
+namespace dom
+{
+namespace io
+{
+
+
+//#########################################################################
+//# B A S E 6 4 I N P U T S T R E A M
+//#########################################################################
+
+static int base64decode[] =
+{
+/*00*/ -1, -1, -1, -1, -1, -1, -1, -1,
+/*08*/ -1, -1, -1, -1, -1, -1, -1, -1,
+/*10*/ -1, -1, -1, -1, -1, -1, -1, -1,
+/*18*/ -1, -1, -1, -1, -1, -1, -1, -1,
+/*20*/ -1, -1, -1, -1, -1, -1, -1, -1,
+/*28*/ -1, -1, -1, 62, -1, -1, -1, 63,
+/*30*/ 52, 53, 54, 55, 56, 57, 58, 59,
+/*38*/ 60, 61, -1, -1, -1, -1, -1, -1,
+/*40*/ -1, 0, 1, 2, 3, 4, 5, 6,
+/*48*/ 7, 8, 9, 10, 11, 12, 13, 14,
+/*50*/ 15, 16, 17, 18, 19, 20, 21, 22,
+/*58*/ 23, 24, 25, -1, -1, -1, -1, -1,
+/*60*/ -1, 26, 27, 28, 29, 30, 31, 32,
+/*68*/ 33, 34, 35, 36, 37, 38, 39, 40,
+/*70*/ 41, 42, 43, 44, 45, 46, 47, 48,
+/*78*/ 49, 50, 51, -1, -1, -1, -1, -1
+};
+
+
+/**
+ *
+ */
+Base64InputStream::Base64InputStream(InputStream &sourceStream)
+ : BasicInputStream(sourceStream)
+{
+ outCount = 0;
+ padCount = 0;
+ closed = false;
+ done = false;
+}
+
+/**
+ *
+ */
+Base64InputStream::~Base64InputStream()
+{
+ close();
+}
+
+/**
+ * Returns the number of bytes that can be read (or skipped over) from
+ * this input stream without blocking by the next caller of a method for
+ * this input stream.
+ */
+int Base64InputStream::available()
+{
+ if (closed )
+ return 0;
+ int len = source.available() * 2 / 3;
+ return len;
+}
+
+
+/**
+ * Closes this input stream and releases any system resources
+ * associated with the stream.
+ */
+void Base64InputStream::close()
+{
+ if (closed)
+ return;
+ source.close();
+ closed = true;
+}
+
+/**
+ * Reads the next byte of data from the input stream. -1 if EOF
+ */
+int Base64InputStream::get()
+{
+ if (closed)
+ return -1;
+
+ if (outCount - padCount > 0)
+ {
+ return outBytes[3-(outCount--)];
+ }
+
+ if (done)
+ return -1;
+
+ int inBytes[4];
+ int inCount = 0;
+ while (inCount < 4)
+ {
+ int ch = source.get();
+ if (ch < 0)
+ {
+ while (inCount < 4) //pad if needed
+ {
+ inBytes[inCount++] = 0;
+ padCount++;
+ }
+ done = true;
+ break;
+ }
+ if (isspace(ch)) //ascii whitespace
+ {
+ //nothing
+ }
+ else if (ch == '=') //padding
+ {
+ inBytes[inCount++] = 0;
+ padCount++;
+ }
+ else
+ {
+ int byteVal = base64decode[ch & 0x7f];
+ //printf("char:%c %d\n", ch, byteVal);
+ if (byteVal < 0)
+ {
+ //Bad lookup value
+ }
+ inBytes[inCount++] = byteVal;
+ }
+ }
+
+ outBytes[0] = ((inBytes[0]<<2) & 0xfc) | ((inBytes[1]>>4) & 0x03);
+ outBytes[1] = ((inBytes[1]<<4) & 0xf0) | ((inBytes[2]>>2) & 0x0f);
+ outBytes[2] = ((inBytes[2]<<6) & 0xc0) | ((inBytes[3] ) & 0x3f);
+
+ outCount = 3;
+
+ //try again
+ if (outCount - padCount > 0)
+ {
+ return outBytes[3-(outCount--)];
+ }
+
+ return -1;
+
+}
+
+
+//#########################################################################
+//# B A S E 6 4 O U T P U T S T R E A M
+//#########################################################################
+
+static char *base64encode =
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+
+/**
+ *
+ */
+Base64OutputStream::Base64OutputStream(OutputStream &destinationStream)
+ : BasicOutputStream(destinationStream)
+{
+ column = 0;
+ columnWidth = 72;
+ outBuf = 0L;
+ bitCount = 0;
+}
+
+/**
+ *
+ */
+Base64OutputStream::~Base64OutputStream()
+{
+ close();
+}
+
+/**
+ * Closes this output stream and releases any system resources
+ * associated with this stream.
+ */
+void Base64OutputStream::close()
+{
+ if (closed)
+ return;
+
+ //get any last bytes (1 or 2) out of the buffer
+ if (bitCount == 16)
+ {
+ outBuf <<= 2; //pad to make 18 bits
+
+ int indx = (int)((outBuf & 0x0003f000L) >> 12);
+ int obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ indx = (int)((outBuf & 0x00000fc0L) >> 6);
+ obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ indx = (int)((outBuf & 0x0000003fL) );
+ obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ putCh('=');
+ }
+ else if (bitCount == 8)
+ {
+ outBuf <<= 4; //pad to make 12 bits
+
+ int indx = (int)((outBuf & 0x00000fc0L) >> 6);
+ int obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ indx = (int)((outBuf & 0x0000003fL) );
+ obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ putCh('=');
+ putCh('=');
+ }
+
+ if (columnWidth > 0) //if <=0, no newlines
+ destination.put('\n');
+
+ destination.close();
+ closed = true;
+}
+
+/**
+ * Flushes this output stream and forces any buffered output
+ * bytes to be written out.
+ */
+void Base64OutputStream::flush()
+{
+ if (closed)
+ return;
+ //dont flush here. do it on close()
+ destination.flush();
+}
+
+/**
+ * Private. Put a char to the output stream, checking for line length
+ */
+void Base64OutputStream::putCh(int ch)
+{
+ destination.put(ch);
+ column++;
+ if (columnWidth > 0 && column >= columnWidth)
+ {
+ destination.put('\n');
+ column = 0;
+ }
+}
+
+
+/**
+ * Writes the specified byte to this output stream.
+ */
+void Base64OutputStream::put(int ch)
+{
+ if (closed)
+ {
+ //probably throw an exception here
+ return;
+ }
+
+ outBuf <<= 8;
+ outBuf |= (ch & 0xff);
+ bitCount += 8;
+ if (bitCount >= 24)
+ {
+ int indx = (int)((outBuf & 0x00fc0000L) >> 18);
+ int obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ indx = (int)((outBuf & 0x0003f000L) >> 12);
+ obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ indx = (int)((outBuf & 0x00000fc0L) >> 6);
+ obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ indx = (int)((outBuf & 0x0000003fL) );
+ obyte = (int)base64encode[indx & 63];
+ putCh(obyte);
+
+ bitCount = 0;
+ outBuf = 0L;
+ }
+}
+
+
+
+} //namespace io
+} //namespace dom
+} //namespace w3c
+} //namespace org
+
+
+//#########################################################################
+//# E N D O F F I L E
+//#########################################################################
diff --git a/src/dom/io/base64stream.h b/src/dom/io/base64stream.h new file mode 100644 index 000000000..6fc94d34f --- /dev/null +++ b/src/dom/io/base64stream.h @@ -0,0 +1,146 @@ +#ifndef __DOM_IO_BASE64STREAM_H__
+#define __DOM_IO_BASE64STREAM_H__
+
+/**
+ * Phoebe DOM Implementation.
+ *
+ * Base64-enabled input and output streams
+ *
+ * This class allows easy encoding and decoding
+ * of Base64 data with a stream interface, hiding
+ * the implementation from the user.
+ *
+ * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html
+ *
+ * Authors:
+ * Bob Jamison
+ *
+ * Copyright (C) 2006 Bob Jamison
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+
+
+#include "domstream.h"
+
+
+namespace org
+{
+namespace w3c
+{
+namespace dom
+{
+namespace io
+{
+
+
+
+//#########################################################################
+//# B A S E 6 4 I N P U T S T R E A M
+//#########################################################################
+
+/**
+ * This class is for decoding a Base-64 encoded InputStream source
+ *
+ */
+class Base64InputStream : public BasicInputStream
+{
+
+public:
+
+ Base64InputStream(InputStream &sourceStream);
+
+ virtual ~Base64InputStream();
+
+ virtual int available();
+
+ virtual void close();
+
+ virtual int get();
+
+private:
+
+ int outBytes[3];
+
+ int outCount;
+
+ int padCount;
+
+ bool done;
+
+}; // class Base64InputStream
+
+
+
+
+//#########################################################################
+//# B A S E 6 4 O U T P U T S T R E A M
+//#########################################################################
+
+/**
+ * This class is for Base-64 encoding data going to the
+ * destination OutputStream
+ *
+ */
+class Base64OutputStream : public BasicOutputStream
+{
+
+public:
+
+ Base64OutputStream(OutputStream &destinationStream);
+
+ virtual ~Base64OutputStream();
+
+ virtual void close();
+
+ virtual void flush();
+
+ virtual void put(int ch);
+
+ /**
+ * Sets the maximum line length for base64 output. If
+ * set to <=0, then there will be no line breaks;
+ */
+ virtual void setColumnWidth(int val)
+ { columnWidth = val; }
+
+private:
+
+ void putCh(int ch);
+
+ int column;
+
+ int columnWidth;
+
+ unsigned long outBuf;
+
+ int bitCount;
+
+}; // class Base64OutputStream
+
+
+
+
+
+
+
+} //namespace io
+} //namespace dom
+} //namespace w3c
+} //namespace org
+
+
+#endif /* __INKSCAPE_IO_BASE64STREAM_H__ */
diff --git a/src/dom/io/bufferstream.cpp b/src/dom/io/bufferstream.cpp new file mode 100644 index 000000000..4664b07e9 --- /dev/null +++ b/src/dom/io/bufferstream.cpp @@ -0,0 +1,166 @@ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2006 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * This class provided buffered endpoints for input and output. + */ + +#include "bufferstream.h" + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + + +//######################################################################### +//# B U F F E R I N P U T S T R E A M +//######################################################################### + + +/** + * + */ +BufferInputStream::BufferInputStream( + const std::vector<unsigned char> &sourceBuffer) + : buffer(sourceBuffer) +{ + position = 0; + closed = false; +} + +/** + * + */ +BufferInputStream::~BufferInputStream() +{ + +} + +/** + * Returns the number of bytes that can be read (or skipped over) from + * this input stream without blocking by the next caller of a method for + * this input stream. + */ +int BufferInputStream::available() +{ + if (closed) + return -1; + return buffer.size() - position; +} + + +/** + * Closes this input stream and releases any system resources + * associated with the stream. + */ +void BufferInputStream::close() +{ + closed = true; +} + +/** + * Reads the next byte of data from the input stream. -1 if EOF + */ +int BufferInputStream::get() +{ + if (closed) + return -1; + if (position >= (int)buffer.size()) + return -1; + int ch = (int) buffer[position++]; + return ch; +} + + + + +//######################################################################### +//# B U F F E R O U T P U T S T R E A M +//######################################################################### + +/** + * + */ +BufferOutputStream::BufferOutputStream() +{ + closed = false; +} + +/** + * + */ +BufferOutputStream::~BufferOutputStream() +{ +} + +/** + * Closes this output stream and releases any system resources + * associated with this stream. + */ +void BufferOutputStream::close() +{ + closed = true; +} + +/** + * Flushes this output stream and forces any buffered output + * bytes to be written out. + */ +void BufferOutputStream::flush() +{ + //nothing to do +} + +/** + * Writes the specified byte to this output stream. + */ +void BufferOutputStream::put(XMLCh ch) +{ + if (closed) + return; + buffer.push_back(ch); +} + + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + +//######################################################################### +//# E N D O F F I L E +//######################################################################### diff --git a/src/dom/io/bufferstream.h b/src/dom/io/bufferstream.h new file mode 100644 index 000000000..a8f7ea319 --- /dev/null +++ b/src/dom/io/bufferstream.h @@ -0,0 +1,133 @@ +#ifndef __BUFFERSTREAM_H__ +#define __BUFFERSTREAM_H__ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2006 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + + +#include "domstream.h" + + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + +//######################################################################### +//# S T R I N G I N P U T S T R E A M +//######################################################################### + +/** + * This class is for reading character from a DOMString + * + */ +class BufferInputStream : public InputStream +{ + +public: + + BufferInputStream(const std::vector<unsigned char> &sourceBuffer); + + virtual ~BufferInputStream(); + + virtual int available(); + + virtual void close(); + + virtual int get(); + +private: + + const std::vector<unsigned char> &buffer; + + long position; + + bool closed; + +}; // class BufferInputStream + + + + +//######################################################################### +//# B U F F E R O U T P U T S T R E A M +//######################################################################### + +/** + * This class is for sending a stream to a character buffer + * + */ +class BufferOutputStream : public OutputStream +{ + +public: + + BufferOutputStream(); + + virtual ~BufferOutputStream(); + + virtual void close(); + + virtual void flush(); + + virtual void put(XMLCh ch); + + virtual std::vector<unsigned char> &getBuffer() + { return buffer; } + + virtual void clear() + { buffer.clear(); } + +private: + + std::vector<unsigned char> buffer; + + bool closed; + + +}; // class BufferOutputStream + + + + + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + + + +#endif /* __BUFFERSTREAM_H__ */ diff --git a/src/dom/io/domstream.cpp b/src/dom/io/domstream.cpp new file mode 100644 index 000000000..63257062f --- /dev/null +++ b/src/dom/io/domstream.cpp @@ -0,0 +1,878 @@ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2005 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * Our base input/output stream classes. These are is directly + * inherited from iostreams, and includes any extra + * functionality that we might need. + * + * Authors: + * Bob Jamison <rjamison@titan.com> + * + * Copyright (C) 2004 Inkscape.org + * + * Released under GNU GPL, read the file 'COPYING' for more information + */ + +#include <stdarg.h> + +#include "domstream.h" +#include "charclass.h" + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + +//######################################################################### +//# U T I L I T Y +//######################################################################### + +void pipeStream(InputStream &source, OutputStream &dest) +{ + for (;;) + { + int ch = source.get(); + if (ch<0) + break; + dest.put(ch); + } + dest.flush(); +} + +//######################################################################### +//# B A S I C I N P U T S T R E A M +//######################################################################### + + +/** + * + */ +BasicInputStream::BasicInputStream(const InputStream &sourceStream) + : source((InputStream &)sourceStream) +{ + closed = false; +} + +/** + * Returns the number of bytes that can be read (or skipped over) from + * this input stream without blocking by the next caller of a method for + * this input stream. + */ +int BasicInputStream::available() +{ + if (closed) + return 0; + return source.available(); +} + + +/** + * Closes this input stream and releases any system resources + * associated with the stream. + */ +void BasicInputStream::close() +{ + if (closed) + return; + source.close(); + closed = true; +} + +/** + * Reads the next byte of data from the input stream. -1 if EOF + */ +int BasicInputStream::get() +{ + if (closed) + return -1; + return source.get(); +} + + + +//######################################################################### +//# B A S I C O U T P U T S T R E A M +//######################################################################### + +/** + * + */ +BasicOutputStream::BasicOutputStream(const OutputStream &destinationStream) + : destination((OutputStream &)destinationStream) +{ + closed = false; +} + +/** + * Closes this output stream and releases any system resources + * associated with this stream. + */ +void BasicOutputStream::close() +{ + if (closed) + return; + destination.close(); + closed = true; +} + +/** + * Flushes this output stream and forces any buffered output + * bytes to be written out. + */ +void BasicOutputStream::flush() +{ + if (closed) + return; + destination.flush(); +} + +/** + * Writes the specified byte to this output stream. + */ +void BasicOutputStream::put(XMLCh ch) +{ + if (closed) + return; + destination.put(ch); +} + + + +//######################################################################### +//# B A S I C R E A D E R +//######################################################################### + + +/** + * + */ +BasicReader::BasicReader(Reader &sourceReader) +{ + source = &sourceReader; +} + +/** + * Returns the number of bytes that can be read (or skipped over) from + * this reader without blocking by the next caller of a method for + * this reader. + */ +int BasicReader::available() +{ + if (source) + return source->available(); + else + return 0; +} + + +/** + * Closes this reader and releases any system resources + * associated with the reader. + */ +void BasicReader::close() +{ + if (source) + source->close(); +} + +/** + * Reads the next byte of data from the reader. + */ +int BasicReader::get() +{ + if (source) + return source->get(); + else + return -1; +} + + + + + + +/** + * Reads a line of data from the reader. + */ +DOMString BasicReader::readLine() +{ + DOMString str; + while (available() > 0) + { + XMLCh ch = get(); + if (ch == '\n') + break; + str.push_back(ch); + } + return str; +} + +/** + * Reads a line of data from the reader. + */ +DOMString BasicReader::readWord() +{ + DOMString str; + while (available() > 0) + { + XMLCh ch = get(); + if (isWhitespace(ch)) + break; + str.push_back(ch); + } + return str; +} + + +static bool getLong(DOMString &str, long *val) +{ + const char *begin = str.c_str(); + char *end; + long ival = strtol(begin, &end, 10); + if (str == end) + return false; + *val = ival; + return true; +} + +static bool getULong(const DOMString &str, unsigned long *val) +{ + DOMString tmp = str; + char *begin = (char *)tmp.c_str(); + char *end; + unsigned long ival = strtoul(begin, &end, 10); + if (begin == end) + return false; + *val = ival; + return true; +} + +static bool getDouble(const DOMString &str, double *val) +{ + DOMString tmp = str; + const char *begin = tmp.c_str(); + char *end; + double ival = strtod(begin, &end); + if (begin == end) + return false; + *val = ival; + return true; +} + + + + +/** + * + */ +Reader &BasicReader::readBool (bool& val ) +{ + DOMString buf = readWord(); + if (buf == "true") + val = true; + else + val = false; + return *this; +} + +/** + * + */ +Reader &BasicReader::readShort (short& val ) +{ + DOMString buf = readWord(); + long ival; + if (getLong(buf, &ival)) + val = (short) ival; + return *this; +} + +/** + * + */ +Reader &BasicReader::readUnsignedShort (unsigned short& val ) +{ + DOMString buf = readWord(); + unsigned long ival; + if (getULong(buf, &ival)) + val = (unsigned short) ival; + return *this; +} + +/** + * + */ +Reader &BasicReader::readInt (int& val ) +{ + DOMString buf = readWord(); + long ival; + if (getLong(buf, &ival)) + val = (int) ival; + return *this; +} + +/** + * + */ +Reader &BasicReader::readUnsignedInt (unsigned int& val ) +{ + DOMString buf = readWord(); + unsigned long ival; + if (getULong(buf, &ival)) + val = (unsigned int) ival; + return *this; +} + +/** + * + */ +Reader &BasicReader::readLong (long& val ) +{ + DOMString buf = readWord(); + long ival; + if (getLong(buf, &ival)) + val = ival; + return *this; +} + +/** + * + */ +Reader &BasicReader::readUnsignedLong (unsigned long& val ) +{ + DOMString buf = readWord(); + unsigned long ival; + if (getULong(buf, &ival)) + val = ival; + return *this; +} + +/** + * + */ +Reader &BasicReader::readFloat (float& val ) +{ + DOMString buf = readWord(); + double ival; + if (getDouble(buf, &ival)) + val = (float)ival; + return *this; +} + +/** + * + */ +Reader &BasicReader::readDouble (double& val ) +{ + DOMString buf = readWord(); + double ival; + if (getDouble(buf, &ival)) + val = ival; + return *this; +} + + + +//######################################################################### +//# I N P U T S T R E A M R E A D E R +//######################################################################### + + +InputStreamReader::InputStreamReader(const InputStream &inputStreamSource) + : inputStream((InputStream &)inputStreamSource) +{ +} + + + +/** + * Close the underlying OutputStream + */ +void InputStreamReader::close() +{ + inputStream.close(); +} + +/** + * Flush the underlying OutputStream + */ +int InputStreamReader::available() +{ + return inputStream.available(); +} + +/** + * Overloaded to receive its bytes from an InputStream + * rather than a Reader + */ +int InputStreamReader::get() +{ + //Do we need conversions here? + int ch = (XMLCh)inputStream.get(); + return ch; +} + + + +//######################################################################### +//# S T D R E A D E R +//######################################################################### + + +/** + * + */ +StdReader::StdReader() +{ + inputStream = new StdInputStream(); +} + +/** + * + */ +StdReader::~StdReader() +{ + delete inputStream; +} + + + +/** + * Close the underlying OutputStream + */ +void StdReader::close() +{ + inputStream->close(); +} + +/** + * Flush the underlying OutputStream + */ +int StdReader::available() +{ + return inputStream->available(); +} + +/** + * Overloaded to receive its bytes from an InputStream + * rather than a Reader + */ +int StdReader::get() +{ + //Do we need conversions here? + XMLCh ch = (XMLCh)inputStream->get(); + return ch; +} + + + + + +//######################################################################### +//# B A S I C W R I T E R +//######################################################################### + +/** + * + */ +BasicWriter::BasicWriter(const Writer &destinationWriter) +{ + destination = (Writer *)&destinationWriter; +} + +/** + * Closes this writer and releases any system resources + * associated with this writer. + */ +void BasicWriter::close() +{ + if (destination) + destination->close(); +} + +/** + * Flushes this output stream and forces any buffered output + * bytes to be written out. + */ +void BasicWriter::flush() +{ + if (destination) + destination->flush(); +} + +/** + * Writes the specified byte to this output writer. + */ +void BasicWriter::put(XMLCh ch) +{ + if (destination) + destination->put(ch); +} + +/** + * Provide printf()-like formatting + */ +Writer &BasicWriter::printf(char *fmt, ...) +{ + va_list args; + va_start(args, fmt); + //replace this wish vsnprintf() + char buf[256]; + vsnprintf(buf, 255, fmt, args); + va_end(args); + if (buf) { + writeString(buf); + //free(buf); + } + return *this; +} +/** + * Writes the specified character to this output writer. + */ +Writer &BasicWriter::writeChar(char ch) +{ + XMLCh uch = ch; + put(uch); + return *this; +} + + +/** + * Writes the specified standard string to this output writer. + */ +Writer &BasicWriter::writeString(const DOMString &str) +{ + for (int i=0; i< (int)str.size(); i++) + put(str[i]); + return *this; +} + + +/** + * + */ +Writer &BasicWriter::writeBool (bool val ) +{ + if (val) + writeString("true"); + else + writeString("false"); + return *this; +} + + +/** + * + */ +Writer &BasicWriter::writeShort (short val ) +{ + char buf[32]; + snprintf(buf, 31, "%d", val); + writeString(buf); + return *this; +} + + + +/** + * + */ +Writer &BasicWriter::writeUnsignedShort (unsigned short val ) +{ + char buf[32]; + snprintf(buf, 31, "%u", val); + writeString(buf); + return *this; +} + +/** + * + */ +Writer &BasicWriter::writeInt (int val) +{ + char buf[32]; + snprintf(buf, 31, "%d", val); + writeString(buf); + return *this; +} + +/** + * + */ +Writer &BasicWriter::writeUnsignedInt (unsigned int val) +{ + char buf[32]; + snprintf(buf, 31, "%u", val); + writeString(buf); + return *this; +} + +/** + * + */ +Writer &BasicWriter::writeLong (long val) +{ + char buf[32]; + snprintf(buf, 31, "%ld", val); + writeString(buf); + return *this; +} + +/** + * + */ +Writer &BasicWriter::writeUnsignedLong(unsigned long val) +{ + char buf[32]; + snprintf(buf, 31, "%lu", val); + writeString(buf); + return *this; +} + +/** + * + */ +Writer &BasicWriter::writeFloat(float val) +{ + char buf[32]; + snprintf(buf, 31, "%8.3f", val); + writeString(buf); + return *this; +} + +/** + * + */ +Writer &BasicWriter::writeDouble(double val) +{ + char buf[32]; + snprintf(buf, 31, "%8.3f", val); + writeString(buf); + return *this; +} + + + + +//######################################################################### +//# O U T P U T S T R E A M W R I T E R +//######################################################################### + + +OutputStreamWriter::OutputStreamWriter(OutputStream &outputStreamDest) + : outputStream(outputStreamDest) +{ +} + + + +/** + * Close the underlying OutputStream + */ +void OutputStreamWriter::close() +{ + flush(); + outputStream.close(); +} + +/** + * Flush the underlying OutputStream + */ +void OutputStreamWriter::flush() +{ + outputStream.flush(); +} + +/** + * Overloaded to redirect the output chars from the next Writer + * in the chain to an OutputStream instead. + */ +void OutputStreamWriter::put(XMLCh ch) +{ + //Do we need conversions here? + int intCh = (int) ch; + outputStream.put(intCh); +} + +//######################################################################### +//# S T D W R I T E R +//######################################################################### + + +/** + * + */ +StdWriter::StdWriter() +{ + outputStream = new StdOutputStream(); +} + + +/** + * + */ +StdWriter::~StdWriter() +{ + delete outputStream; +} + + + +/** + * Close the underlying OutputStream + */ +void StdWriter::close() +{ + flush(); + outputStream->close(); +} + +/** + * Flush the underlying OutputStream + */ +void StdWriter::flush() +{ + outputStream->flush(); +} + +/** + * Overloaded to redirect the output chars from the next Writer + * in the chain to an OutputStream instead. + */ +void StdWriter::put(XMLCh ch) +{ + //Do we need conversions here? + int intCh = (int) ch; + outputStream->put(intCh); +} + + + + + + + + + + + + +//############################################### +//# O P E R A T O R S +//############################################### +//# Normally these would be in the .h, but we +//# just want to be absolutely certain that these +//# are never multiply defined. Easy to maintain, +//# though. Just occasionally copy/paste these +//# into the .h , and replace the {} with a ; +//############################################### + + + + +Reader& operator>> (Reader &reader, bool& val ) + { return reader.readBool(val); } + +Reader& operator>> (Reader &reader, short &val) + { return reader.readShort(val); } + +Reader& operator>> (Reader &reader, unsigned short &val) + { return reader.readUnsignedShort(val); } + +Reader& operator>> (Reader &reader, int &val) + { return reader.readInt(val); } + +Reader& operator>> (Reader &reader, unsigned int &val) + { return reader.readUnsignedInt(val); } + +Reader& operator>> (Reader &reader, long &val) + { return reader.readLong(val); } + +Reader& operator>> (Reader &reader, unsigned long &val) + { return reader.readUnsignedLong(val); } + +Reader& operator>> (Reader &reader, float &val) + { return reader.readFloat(val); } + +Reader& operator>> (Reader &reader, double &val) + { return reader.readDouble(val); } + + + + +Writer& operator<< (Writer &writer, char val) + { return writer.writeChar(val); } + +Writer& operator<< (Writer &writer, const DOMString &val) + { return writer.writeString(val); } + +Writer& operator<< (Writer &writer, bool val) + { return writer.writeBool(val); } + +Writer& operator<< (Writer &writer, short val) + { return writer.writeShort(val); } + +Writer& operator<< (Writer &writer, unsigned short val) + { return writer.writeUnsignedShort(val); } + +Writer& operator<< (Writer &writer, int val) + { return writer.writeInt(val); } + +Writer& operator<< (Writer &writer, unsigned int val) + { return writer.writeUnsignedInt(val); } + +Writer& operator<< (Writer &writer, long val) + { return writer.writeLong(val); } + +Writer& operator<< (Writer &writer, unsigned long val) + { return writer.writeUnsignedLong(val); } + +Writer& operator<< (Writer &writer, float val) + { return writer.writeFloat(val); } + +Writer& operator<< (Writer &writer, double val) + { return writer.writeDouble(val); } + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + + +//######################################################################### +//# E N D O F F I L E +//######################################################################### diff --git a/src/dom/io/domstream.h b/src/dom/io/domstream.h new file mode 100644 index 000000000..af43d0a51 --- /dev/null +++ b/src/dom/io/domstream.h @@ -0,0 +1,680 @@ +#ifndef __DOMSTREAM_H__ +#define __DOMSTREAM_H__ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2005 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + + + +#include "dom.h" + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + + +class StreamException +{ +public: + + StreamException(const DOMString &theReason) throw() + { reason = theReason; } + ~StreamException() throw() + { } + char const *what() + { return reason.c_str(); } + +private: + + DOMString reason; + +}; + +//######################################################################### +//# I N P U T S T R E A M +//######################################################################### + +/** + * This interface is the base of all input stream classes. Users who wish + * to make an InputStream that is part of a chain should inherit from + * BasicInputStream. Inherit from this class to make a source endpoint, + * such as a URI or buffer. + * + */ +class InputStream +{ + +public: + + /** + * Constructor. + */ + InputStream() {} + + /** + * Destructor + */ + virtual ~InputStream() {} + + /** + * Return the number of bytes that are currently available + * to be read + */ + virtual int available() = 0; + + /** + * Do whatever it takes to 'close' this input stream + * The most likely implementation of this method will be + * for endpoints that use a resource for their data. + */ + virtual void close() = 0; + + /** + * Read one byte from this input stream. This is a blocking + * call. If no data is currently available, this call will + * not return until it exists. If the user does not want + * their code to block, then the usual solution is: + * if (available() > 0) + * myChar = get(); + * This call returns -1 on end-of-file. + */ + virtual int get() = 0; + +}; // class InputStream + + + + +/** + * This is the class that most users should inherit, to provide + * their own streams. + * + */ +class BasicInputStream : public InputStream +{ + +public: + + BasicInputStream(const InputStream &sourceStream); + + virtual ~BasicInputStream() {} + + virtual int available(); + + virtual void close(); + + virtual int get(); + +protected: + + bool closed; + + InputStream &source; + +private: + + +}; // class BasicInputStream + + + +/** + * Convenience class for reading from standard input + */ +class StdInputStream : public InputStream +{ +public: + + int available() + { return 0; } + + void close() + { /* do nothing */ } + + int get() + { return getchar(); } + +}; + + + + + + +//######################################################################### +//# O U T P U T S T R E A M +//######################################################################### + +/** + * This interface is the base of all input stream classes. Users who wish + * to make an OutputStream that is part of a chain should inherit from + * BasicOutputStream. Inherit from this class to make a destination endpoint, + * such as a URI or buffer. + */ +class OutputStream +{ + +public: + + /** + * Constructor. + */ + OutputStream() {} + + /** + * Destructor + */ + virtual ~OutputStream() {} + + /** + * This call should + * 1. flush itself + * 2. close itself + * 3. close the destination stream + */ + virtual void close() = 0; + + /** + * This call should push any pending data it might have to + * the destination stream. It should NOT call flush() on + * the destination stream. + */ + virtual void flush() = 0; + + /** + * Send one byte to the destination stream. + */ + virtual void put(XMLCh ch) = 0; + + +}; // class OutputStream + + +/** + * This is the class that most users should inherit, to provide + * their own output streams. + */ +class BasicOutputStream : public OutputStream +{ + +public: + + BasicOutputStream(const OutputStream &destinationStream); + + virtual ~BasicOutputStream() {} + + virtual void close(); + + virtual void flush(); + + virtual void put(XMLCh ch); + +protected: + + bool closed; + + OutputStream &destination; + + +}; // class BasicOutputStream + + + +/** + * Convenience class for writing to standard output + */ +class StdOutputStream : public OutputStream +{ +public: + + void close() + { } + + void flush() + { } + + void put(XMLCh ch) + { putchar(ch); } + +}; + + + + +//######################################################################### +//# R E A D E R +//######################################################################### + + +/** + * This interface and its descendants are for unicode character-oriented input + * + */ +class Reader +{ + +public: + + /** + * Constructor. + */ + Reader() {} + + /** + * Destructor + */ + virtual ~Reader() {} + + + virtual int available() = 0; + + virtual void close() = 0; + + virtual int get() = 0; + + virtual DOMString readLine() = 0; + + virtual DOMString readWord() = 0; + + /* Input formatting */ + virtual Reader& readBool (bool& val ) = 0; + + virtual Reader& readShort (short &val) = 0; + + virtual Reader& readUnsignedShort (unsigned short &val) = 0; + + virtual Reader& readInt (int &val) = 0; + + virtual Reader& readUnsignedInt (unsigned int &val) = 0; + + virtual Reader& readLong (long &val) = 0; + + virtual Reader& readUnsignedLong (unsigned long &val) = 0; + + virtual Reader& readFloat (float &val) = 0; + + virtual Reader& readDouble (double &val) = 0; + +}; // interface Reader + + + +/** + * This class and its descendants are for unicode character-oriented input + * + */ +class BasicReader : public Reader +{ + +public: + + BasicReader(Reader &sourceStream); + + virtual ~BasicReader() {} + + virtual int available(); + + virtual void close(); + + virtual int get(); + + virtual DOMString readLine(); + + virtual DOMString readWord(); + + /* Input formatting */ + virtual Reader& readBool (bool& val ); + + virtual Reader& readShort (short &val) ; + + virtual Reader& readUnsignedShort (unsigned short &val) ; + + virtual Reader& readInt (int &val) ; + + virtual Reader& readUnsignedInt (unsigned int &val) ; + + virtual Reader& readLong (long &val) ; + + virtual Reader& readUnsignedLong (unsigned long &val) ; + + virtual Reader& readFloat (float &val) ; + + virtual Reader& readDouble (double &val) ; + +protected: + + Reader *source; + + BasicReader() + { source = NULL; } + +private: + +}; // class BasicReader + + + +Reader& operator>> (Reader &reader, bool& val ); + +Reader& operator>> (Reader &reader, short &val); + +Reader& operator>> (Reader &reader, unsigned short &val); + +Reader& operator>> (Reader &reader, int &val); + +Reader& operator>> (Reader &reader, unsigned int &val); + +Reader& operator>> (Reader &reader, long &val); + +Reader& operator>> (Reader &reader, unsigned long &val); + +Reader& operator>> (Reader &reader, float &val); + +Reader& operator>> (Reader &reader, double &val); + + + + +/** + * Class for placing a Reader on an open InputStream + * + */ +class InputStreamReader : public BasicReader +{ +public: + + InputStreamReader(const InputStream &inputStreamSource); + + /*Overload these 3 for your implementation*/ + virtual int available(); + + virtual void close(); + + virtual int get(); + + +private: + + InputStream &inputStream; + + +}; + +/** + * Convenience class for reading formatted from standard input + * + */ +class StdReader : public BasicReader +{ +public: + + StdReader(); + + ~StdReader(); + + /*Overload these 3 for your implementation*/ + virtual int available(); + + virtual void close(); + + virtual int get(); + + +private: + + InputStream *inputStream; + + +}; + + + + + +//######################################################################### +//# W R I T E R +//######################################################################### + +/** + * This interface and its descendants are for unicode character-oriented output + * + */ +class Writer +{ + +public: + + /** + * Constructor. + */ + Writer() {} + + /** + * Destructor + */ + virtual ~Writer() {} + + virtual void close() = 0; + + virtual void flush() = 0; + + virtual void put(XMLCh ch) = 0; + + /* Formatted output */ + virtual Writer& printf(char *fmt, ...) = 0; + + virtual Writer& writeChar(char val) = 0; + + virtual Writer& writeString(const DOMString &val) = 0; + + virtual Writer& writeBool (bool val ) = 0; + + virtual Writer& writeShort (short val ) = 0; + + virtual Writer& writeUnsignedShort (unsigned short val ) = 0; + + virtual Writer& writeInt (int val ) = 0; + + virtual Writer& writeUnsignedInt (unsigned int val ) = 0; + + virtual Writer& writeLong (long val ) = 0; + + virtual Writer& writeUnsignedLong (unsigned long val ) = 0; + + virtual Writer& writeFloat (float val ) = 0; + + virtual Writer& writeDouble (double val ) = 0; + + + +}; // interface Writer + + +/** + * This class and its descendants are for unicode character-oriented output + * + */ +class BasicWriter : public Writer +{ + +public: + + BasicWriter(const Writer &destinationWriter); + + virtual ~BasicWriter() {} + + /*Overload these 3 for your implementation*/ + virtual void close(); + + virtual void flush(); + + virtual void put(XMLCh ch); + + + + /* Formatted output */ + virtual Writer &printf(char *fmt, ...); + + virtual Writer& writeChar(char val); + + virtual Writer& writeString(const DOMString &val); + + virtual Writer& writeBool (bool val ); + + virtual Writer& writeShort (short val ); + + virtual Writer& writeUnsignedShort (unsigned short val ); + + virtual Writer& writeInt (int val ); + + virtual Writer& writeUnsignedInt (unsigned int val ); + + virtual Writer& writeLong (long val ); + + virtual Writer& writeUnsignedLong (unsigned long val ); + + virtual Writer& writeFloat (float val ); + + virtual Writer& writeDouble (double val ); + + +protected: + + Writer *destination; + + BasicWriter() + { destination = NULL; } + +private: + +}; // class BasicWriter + + + +Writer& operator<< (Writer &writer, char val); + +Writer& operator<< (Writer &writer, const DOMString &val); + +Writer& operator<< (Writer &writer, bool val); + +Writer& operator<< (Writer &writer, short val); + +Writer& operator<< (Writer &writer, unsigned short val); + +Writer& operator<< (Writer &writer, int val); + +Writer& operator<< (Writer &writer, unsigned int val); + +Writer& operator<< (Writer &writer, long val); + +Writer& operator<< (Writer &writer, unsigned long val); + +Writer& operator<< (Writer &writer, float val); + +Writer& operator<< (Writer &writer, double val); + + + + +/** + * Class for placing a Writer on an open OutputStream + * + */ +class OutputStreamWriter : public BasicWriter +{ +public: + + OutputStreamWriter(OutputStream &outputStreamDest); + + /*Overload these 3 for your implementation*/ + virtual void close(); + + virtual void flush(); + + virtual void put(XMLCh ch); + + +private: + + OutputStream &outputStream; + + +}; + + +/** + * Convenience class for writing to standard output + */ +class StdWriter : public BasicWriter +{ +public: + StdWriter(); + + ~StdWriter(); + + + virtual void close(); + + + virtual void flush(); + + + virtual void put(XMLCh ch); + + +private: + + OutputStream *outputStream; + +}; + +//######################################################################### +//# U T I L I T Y +//######################################################################### + +void pipeStream(InputStream &source, OutputStream &dest); + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + + +#endif /* __DOMSTREAM_H__ */ + +//######################################################################### +//# E N D O F F I L E +//######################################################################### diff --git a/src/dom/io/gzipstream.cpp b/src/dom/io/gzipstream.cpp new file mode 100644 index 000000000..628adaa7a --- /dev/null +++ b/src/dom/io/gzipstream.cpp @@ -0,0 +1,245 @@ +/**
+ * Zlib-enabled input and output streams
+ *
+ * This is a thin wrapper of libz calls, in order
+ * to provide a simple interface to our developers
+ * for gzip input and output.
+ *
+ * Authors:
+ * Bob Jamison
+ *
+ * Copyright (C) 2006 Bob Jamison
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+
+
+#include "gzipstream.h"
+
+#include "util/ziptool.h"
+
+
+namespace org
+{
+namespace w3c
+{
+namespace dom
+{
+namespace io
+{
+
+
+//#########################################################################
+//# G Z I P I N P U T S T R E A M
+//#########################################################################
+
+/**
+ *
+ */
+GzipInputStream::GzipInputStream(InputStream &sourceStream)
+ : BasicInputStream(sourceStream)
+{
+ loaded = false;
+ bufPos = 0;
+}
+
+/**
+ *
+ */
+GzipInputStream::~GzipInputStream()
+{
+ close();
+}
+
+/**
+ * Returns the number of bytes that can be read (or skipped over) from
+ * this input stream without blocking by the next caller of a method for
+ * this input stream.
+ */
+int GzipInputStream::available()
+{
+ if (closed)
+ return 0;
+ if (!loaded)
+ if (!load())
+ return 0;
+ return (int) buffer.size();
+}
+
+
+/**
+ * Closes this input stream and releases any system resources
+ * associated with the stream.
+ */
+void GzipInputStream::close()
+{
+ if (closed)
+ return;
+
+ closed = true;
+}
+
+/**
+ * Reads the next byte of data from the input stream. -1 if EOF
+ */
+int GzipInputStream::get()
+{
+ if (closed)
+ return -1;
+
+ if (!loaded)
+ if (!load())
+ return -1;
+
+ if (bufPos >= buffer.size())
+ return -1;
+ int ch = (int) buffer[bufPos++];
+
+ return ch;
+}
+
+/**
+ * Processes input. Fills read buffer.
+ */
+bool GzipInputStream::load()
+{
+ if (closed)
+ return false;
+
+ if (loaded)
+ return true;
+
+ std::vector<unsigned char> compBuf;
+ while (true)
+ {
+ int ch = source.get();
+ if (ch < 0)
+ break;
+ compBuf.push_back(ch);
+ }
+ GzipFile gz;
+ if (!gz.readBuffer(compBuf))
+ {
+ return -1;
+ }
+ buffer = gz.getData();
+ bufPos = 0;
+ loaded = true;
+ return true;
+}
+
+
+
+
+
+
+//#########################################################################
+//# G Z I P O U T P U T S T R E A M
+//#########################################################################
+
+/**
+ *
+ */
+GzipOutputStream::GzipOutputStream(OutputStream &destinationStream)
+ : BasicOutputStream(destinationStream)
+{
+
+ closed = false;
+}
+
+/**
+ *
+ */
+GzipOutputStream::~GzipOutputStream()
+{
+ close();
+}
+
+/**
+ * Closes this output stream and releases any system resources
+ * associated with this stream.
+ */
+void GzipOutputStream::close()
+{
+ if (closed)
+ return;
+
+ flush();
+
+ closed = true;
+}
+
+/**
+ * Flushes this output stream and forces any buffered output
+ * bytes to be written out.
+ */
+void GzipOutputStream::flush()
+{
+ if (closed || buffer.size()<1)
+ return;
+
+ std::vector<unsigned char> compBuf;
+ GzipFile gz;
+
+ gz.writeBuffer(buffer);
+
+ std::vector<unsigned char>::iterator iter;
+ for (iter=compBuf.begin() ; iter!=compBuf.end() ; iter++)
+ {
+ int ch = (int) *iter;
+ destination.put(ch);
+ }
+
+ buffer.clear();
+
+ //printf("done\n");
+
+}
+
+
+
+/**
+ * Writes the specified byte to this output stream.
+ */
+void GzipOutputStream::put(int ch)
+{
+ if (closed)
+ {
+ //probably throw an exception here
+ return;
+ }
+
+ //Add char to buffer
+ buffer.push_back(ch);
+
+}
+
+
+
+} // namespace io
+} // namespace dom
+} // namespace w3c
+} // namespace org
+
+
+
+
+//#########################################################################
+//# E N D O F F I L E
+//#########################################################################
+
+
+
diff --git a/src/dom/io/gzipstream.h b/src/dom/io/gzipstream.h new file mode 100644 index 000000000..ed7462488 --- /dev/null +++ b/src/dom/io/gzipstream.h @@ -0,0 +1,125 @@ +#ifndef __GZIPSTREAM_H__
+#define __GZIPSTREAM_H__
+/**
+ * Zlib-enabled input and output streams
+ *
+ * This provides a simple mechanism for reading and
+ * writing Gzip files. We use our own 'ZipTool' class
+ * to accomplish this, avoiding a zlib dependency.
+ *
+ * Authors:
+ * Bob Jamison
+ *
+ * Copyright (C) 2006 Bob Jamison
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+
+
+
+#include "domstream.h"
+
+namespace org
+{
+namespace w3c
+{
+namespace dom
+{
+namespace io
+{
+
+//#########################################################################
+//# G Z I P I N P U T S T R E A M
+//#########################################################################
+
+/**
+ * This class is for deflating a gzip-compressed InputStream source
+ *
+ */
+class GzipInputStream : public BasicInputStream
+{
+
+public:
+
+ GzipInputStream(InputStream &sourceStream);
+
+ virtual ~GzipInputStream();
+
+ virtual int available();
+
+ virtual void close();
+
+ virtual int get();
+
+private:
+
+ bool load();
+
+ bool loaded;
+
+ std::vector<unsigned char> buffer;
+ unsigned int bufPos;
+
+
+}; // class GzipInputStream
+
+
+
+
+//#########################################################################
+//# G Z I P O U T P U T S T R E A M
+//#########################################################################
+
+/**
+ * This class is for gzip-compressing data going to the
+ * destination OutputStream
+ *
+ */
+class GzipOutputStream : public BasicOutputStream
+{
+
+public:
+
+ GzipOutputStream(OutputStream &destinationStream);
+
+ virtual ~GzipOutputStream();
+
+ virtual void close();
+
+ virtual void flush();
+
+ virtual void put(int ch);
+
+private:
+
+ std::vector<unsigned char> buffer;
+
+
+}; // class GzipOutputStream
+
+
+
+
+
+
+
+} // namespace io
+} // namespace dom
+} // namespace w3c
+} // namespace org
+
+
+#endif /* __GZIPSTREAM_H__ */
diff --git a/src/dom/io/httpclient.cpp b/src/dom/io/httpclient.cpp new file mode 100644 index 000000000..b81e9aedf --- /dev/null +++ b/src/dom/io/httpclient.cpp @@ -0,0 +1,167 @@ +/**
+ * Phoebe DOM Implementation.
+ *
+ * This is a C++ approximation of the W3C DOM model, which follows
+ * fairly closely the specifications in the various .idl files, copies of
+ * which are provided for reference. Most important is this one:
+ *
+ * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html
+ *
+ * Authors:
+ * Bob Jamison
+ *
+ * Copyright (C) 2006 Bob Jamison
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+
+
+#include "httpclient.h"
+
+namespace org
+{
+namespace w3c
+{
+namespace dom
+{
+namespace io
+{
+
+
+
+
+/**
+ *
+ */
+HttpClient::HttpClient()
+{
+}
+
+
+/**
+ *
+ */
+HttpClient::~HttpClient()
+{
+}
+
+
+/**
+ *
+ */
+bool HttpClient::openGet(const URI &uri)
+{
+
+ socket.disconnect();
+
+ if (uri.getScheme() == URI::SCHEME_HTTP)
+ socket.enableSSL(false);
+ else if (uri.getScheme() == URI::SCHEME_HTTPS)
+ socket.enableSSL(true);
+ else
+ {
+ printf("Bad proto scheme:%d\n", uri.getScheme());
+ return false;
+ }
+
+ DOMString host = uri.getHost();
+ int port = uri.getPort();
+ DOMString path = uri.getPath();
+ if (path.size() == 0)
+ path = "/";
+
+ //printf("host:%s port:%d, path:%s\n", host.c_str(), port, path.c_str());
+
+ if (!socket.connect(host, port))
+ {
+ return false;
+ }
+
+ DOMString msg = "GET ";
+ msg.append(path);
+ msg.append(" HTTP/1.0\r\n\r\n");
+ //printf("msg:'%s'\n", msg.c_str());
+
+ //# Make the request
+ if (!socket.write(msg))
+ {
+ return false;
+ }
+
+ //# Read the HTTP headers
+ while (true)
+ {
+ if (!socket.readLine(msg))
+ return false;
+ printf("header:'%s'\n", msg.c_str());
+ if (msg.size() < 1)
+ break;
+ }
+
+ return true;
+}
+
+
+/**
+ *
+ */
+int HttpClient::read()
+{
+ int ret = socket.read();
+ return ret;
+}
+
+/**
+ *
+ */
+bool HttpClient::write(int ch)
+{
+ if (!socket.write(ch))
+ return false;
+ return true;
+}
+
+/**
+ *
+ */
+bool HttpClient::write(const DOMString &msg)
+{
+ if (!socket.write(msg))
+ return false;
+ return true;
+}
+
+/**
+ *
+ */
+bool HttpClient::close()
+{
+ socket.disconnect();
+ return true;
+}
+
+
+
+} //namespace io
+} //namespace dom
+} //namespace w3c
+} //namespace org
+
+
+//#########################################################################
+//# E N D O F F I L E
+//#########################################################################
+
diff --git a/src/dom/io/httpclient.h b/src/dom/io/httpclient.h new file mode 100644 index 000000000..9f4d238f9 --- /dev/null +++ b/src/dom/io/httpclient.h @@ -0,0 +1,115 @@ +#ifndef __HTTPCLIENT_H__
+#define __HTTPCLIENT_H__
+/**
+ * Phoebe DOM Implementation.
+ *
+ * This is a C++ approximation of the W3C DOM model, which follows
+ * fairly closely the specifications in the various .idl files, copies of
+ * which are provided for reference. Most important is this one:
+ *
+ * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html
+ *
+ * Authors:
+ * Bob Jamison
+ *
+ * Copyright (C) 2006 Bob Jamison
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+
+
+#include "dom.h"
+#include "uri.h"
+#include "socket.h"
+
+namespace org
+{
+namespace w3c
+{
+namespace dom
+{
+namespace io
+{
+
+
+
+
+
+
+class HttpClient
+{
+
+public:
+
+ /**
+ *
+ */
+ HttpClient();
+
+ /**
+ *
+ */
+ virtual ~HttpClient();
+
+ /**
+ *
+ */
+ bool openGet(const URI &uri);
+
+ /**
+ *
+ */
+ int read();
+
+ /**
+ *
+ */
+ bool write(int ch);
+
+ /**
+ *
+ */
+ bool write(const DOMString &msg);
+
+ /**
+ *
+ */
+ bool close();
+
+
+private:
+
+
+ TcpSocket socket;
+
+};
+
+
+
+
+} //namespace io
+} //namespace dom
+} //namespace w3c
+} //namespace org
+
+
+#endif /* __HTTPCLIENT_H__ */
+
+
+//#########################################################################
+//# E N D O F F I L E
+//#########################################################################
+
diff --git a/src/dom/io/socket.cpp b/src/dom/io/socket.cpp new file mode 100644 index 000000000..fbcc8e4ac --- /dev/null +++ b/src/dom/io/socket.cpp @@ -0,0 +1,618 @@ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2005 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "socket.h" +#include "util/thread.h" + +#ifdef __WIN32__ +#include <windows.h> +#endif + + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + +static void mybzero(void *s, size_t n) +{ + unsigned char *p = (unsigned char *)s; + while (n > 0) + { + *p++ = (unsigned char)0; + n--; + } +} + +static void mybcopy(void *src, void *dest, size_t n) +{ + unsigned char *p = (unsigned char *)dest; + unsigned char *q = (unsigned char *)src; + while (n > 0) + { + *p++ = *q++; + n--; + } +} + + + +//######################################################################### +//# T C P C O N N E C T I O N +//######################################################################### + +TcpSocket::TcpSocket() +{ + init(); +} + + +TcpSocket::TcpSocket(const DOMString &hostnameArg, int port) +{ + init(); + hostname = hostnameArg; + portno = port; +} + + +#ifdef HAVE_SSL + +static void cryptoLockCallback(int mode, int type, const char *file, int line) +{ + //printf("########### LOCK\n"); + static int modes[CRYPTO_NUM_LOCKS]; /* = {0, 0, ... } */ + const char *errstr = NULL; + + int rw = mode & (CRYPTO_READ|CRYPTO_WRITE); + if (!((rw == CRYPTO_READ) || (rw == CRYPTO_WRITE))) + { + errstr = "invalid mode"; + goto err; + } + + if (type < 0 || type >= CRYPTO_NUM_LOCKS) + { + errstr = "type out of bounds"; + goto err; + } + + if (mode & CRYPTO_LOCK) + { + if (modes[type]) + { + errstr = "already locked"; + /* must not happen in a single-threaded program + * (would deadlock) + */ + goto err; + } + + modes[type] = rw; + } + else if (mode & CRYPTO_UNLOCK) + { + if (!modes[type]) + { + errstr = "not locked"; + goto err; + } + + if (modes[type] != rw) + { + errstr = (rw == CRYPTO_READ) ? + "CRYPTO_r_unlock on write lock" : + "CRYPTO_w_unlock on read lock"; + } + + modes[type] = 0; + } + else + { + errstr = "invalid mode"; + goto err; + } + + err: + if (errstr) + { + /* we cannot use bio_err here */ + fprintf(stderr, "openssl (lock_dbg_cb): %s (mode=%d, type=%d) at %s:%d\n", + errstr, mode, type, file, line); + } +} + +static unsigned long cryptoIdCallback() +{ +#ifdef __WIN32__ + unsigned long ret = (unsigned long) GetCurrentThreadId(); +#else + unsigned long ret = (unsigned long) pthread_self(); +#endif + return ret; +} + +#endif + + +TcpSocket::TcpSocket(const TcpSocket &other) +{ + init(); + sock = other.sock; + hostname = other.hostname; + portno = other.portno; +} + +static bool tcp_socket_inited = false; + +void TcpSocket::init() +{ + if (!tcp_socket_inited) + { +#ifdef __WIN32__ + WORD wVersionRequested = MAKEWORD( 2, 2 ); + WSADATA wsaData; + WSAStartup( wVersionRequested, &wsaData ); +#endif +#ifdef HAVE_SSL + sslStream = NULL; + sslContext = NULL; + CRYPTO_set_locking_callback(cryptoLockCallback); + CRYPTO_set_id_callback(cryptoIdCallback); + SSL_library_init(); + SSL_load_error_strings(); +#endif + tcp_socket_inited = true; + } + sock = -1; + connected = false; + hostname = ""; + portno = -1; + sslEnabled = false; + receiveTimeout = 0; +} + +TcpSocket::~TcpSocket() +{ + disconnect(); +} + +bool TcpSocket::isConnected() +{ + if (!connected || sock < 0) + return false; + return true; +} + +void TcpSocket::enableSSL(bool val) +{ + sslEnabled = val; +} + + +bool TcpSocket::connect(const DOMString &hostnameArg, int portnoArg) +{ + hostname = hostnameArg; + portno = portnoArg; + return connect(); +} + + + +#ifdef HAVE_SSL +/* +static int password_cb(char *buf, int bufLen, int rwflag, void *userdata) +{ + char *password = "password"; + if (bufLen < (int)(strlen(password)+1)) + return 0; + + strcpy(buf,password); + int ret = strlen(password); + return ret; +} + +static void infoCallback(const SSL *ssl, int where, int ret) +{ + switch (where) + { + case SSL_CB_ALERT: + { + printf("## %d SSL ALERT: %s\n", where, SSL_alert_desc_string_long(ret)); + break; + } + default: + { + printf("## %d SSL: %s\n", where, SSL_state_string_long(ssl)); + break; + } + } +} +*/ +#endif + + +bool TcpSocket::startTls() +{ +#ifdef HAVE_SSL + sslStream = NULL; + sslContext = NULL; + + //SSL_METHOD *meth = SSLv23_method(); + //SSL_METHOD *meth = SSLv3_client_method(); + SSL_METHOD *meth = TLSv1_client_method(); + sslContext = SSL_CTX_new(meth); + //SSL_CTX_set_info_callback(sslContext, infoCallback); + +#if 0 + char *keyFile = "client.pem"; + char *caList = "root.pem"; + /* Load our keys and certificates*/ + if (!(SSL_CTX_use_certificate_chain_file(sslContext, keyFile))) + { + fprintf(stderr, "Can't read certificate file\n"); + disconnect(); + return false; + } + + SSL_CTX_set_default_passwd_cb(sslContext, password_cb); + + if (!(SSL_CTX_use_PrivateKey_file(sslContext, keyFile, SSL_FILETYPE_PEM))) + { + fprintf(stderr, "Can't read key file\n"); + disconnect(); + return false; + } + + /* Load the CAs we trust*/ + if (!(SSL_CTX_load_verify_locations(sslContext, caList, 0))) + { + fprintf(stderr, "Can't read CA list\n"); + disconnect(); + return false; + } +#endif + + /* Connect the SSL socket */ + sslStream = SSL_new(sslContext); + SSL_set_fd(sslStream, sock); + + if (SSL_connect(sslStream)<=0) + { + fprintf(stderr, "SSL connect error\n"); + disconnect(); + return false; + } + + sslEnabled = true; +#endif /*HAVE_SSL*/ + return true; +} + + +bool TcpSocket::connect() +{ + if (hostname.size()<1) + { + printf("open: null hostname\n"); + return false; + } + + if (portno<1) + { + printf("open: bad port number\n"); + return false; + } + + sock = socket(PF_INET, SOCK_STREAM, 0); + if (sock < 0) + { + printf("open: error creating socket\n"); + return false; + } + + char *c_hostname = (char *)hostname.c_str(); + struct hostent *server = gethostbyname(c_hostname); + if (!server) + { + printf("open: could not locate host '%s'\n", c_hostname); + return false; + } + + struct sockaddr_in serv_addr; + mybzero((char *) &serv_addr, sizeof(serv_addr)); + serv_addr.sin_family = AF_INET; + mybcopy((char *)server->h_addr, (char *)&serv_addr.sin_addr.s_addr, + server->h_length); + serv_addr.sin_port = htons(portno); + + int ret = ::connect(sock, (const sockaddr *)&serv_addr, sizeof(serv_addr)); + if (ret < 0) + { + printf("open: could not connect to host '%s'\n", c_hostname); + return false; + } + + if (sslEnabled) + { + if (!startTls()) + return false; + } + connected = true; + return true; +} + +bool TcpSocket::disconnect() +{ + bool ret = true; + connected = false; +#ifdef HAVE_SSL + if (sslEnabled) + { + if (sslStream) + { + int r = SSL_shutdown(sslStream); + switch(r) + { + case 1: + break; /* Success */ + case 0: + case -1: + default: + //printf("Shutdown failed"); + ret = false; + } + SSL_free(sslStream); + } + if (sslContext) + SSL_CTX_free(sslContext); + } + sslStream = NULL; + sslContext = NULL; +#endif /*HAVE_SSL*/ + +#ifdef __WIN32__ + closesocket(sock); +#else + ::close(sock); +#endif + sock = -1; + sslEnabled = false; + + return ret; +} + + + +bool TcpSocket::setReceiveTimeout(unsigned long millis) +{ + receiveTimeout = millis; + return true; +} + +/** + * For normal sockets, return the number of bytes waiting to be received. + * For SSL, just return >0 when something is ready to be read. + */ +long TcpSocket::available() +{ + if (!isConnected()) + return -1; + + long count = 0; +#ifdef __WIN32__ + if (ioctlsocket(sock, FIONREAD, (unsigned long *)&count) != 0) + return -1; +#else + if (ioctl(sock, FIONREAD, &count) != 0) + return -1; +#endif + if (count<=0 && sslEnabled) + { +#ifdef HAVE_SSL + return SSL_pending(sslStream); +#endif + } + return count; +} + + + +bool TcpSocket::write(int ch) +{ + if (!isConnected()) + { + printf("write: socket closed\n"); + return false; + } + unsigned char c = (unsigned char)ch; + + if (sslEnabled) + { +#ifdef HAVE_SSL + int r = SSL_write(sslStream, &c, 1); + if (r<=0) + { + switch(SSL_get_error(sslStream, r)) + { + default: + printf("SSL write problem"); + return -1; + } + } +#endif + } + else + { + if (send(sock, (const char *)&c, 1, 0) < 0) + //if (send(sock, &c, 1, 0) < 0) + { + printf("write: could not send data\n"); + return false; + } + } + return true; +} + +bool TcpSocket::write(const DOMString &strArg) +{ + DOMString str = strArg; + + if (!isConnected()) + { + printf("write(str): socket closed\n"); + return false; + } + int len = str.size(); + + if (sslEnabled) + { +#ifdef HAVE_SSL + int r = SSL_write(sslStream, (unsigned char *)str.c_str(), len); + if (r<=0) + { + switch(SSL_get_error(sslStream, r)) + { + default: + printf("SSL write problem"); + return -1; + } + } +#endif + } + else + { + if (send(sock, str.c_str(), len, 0) < 0) + //if (send(sock, &c, 1, 0) < 0) + { + printf("write: could not send data\n"); + return false; + } + } + return true; +} + +int TcpSocket::read() +{ + if (!isConnected()) + return -1; + + //We'll use this loop for timeouts, so that SSL and plain sockets + //will behave the same way + if (receiveTimeout > 0) + { + unsigned long tim = 0; + while (true) + { + int avail = available(); + if (avail > 0) + break; + if (tim >= receiveTimeout) + return -2; + org::w3c::dom::util::Thread::sleep(20); + tim += 20; + } + } + + //check again + if (!isConnected()) + return -1; + + unsigned char ch; + if (sslEnabled) + { +#ifdef HAVE_SSL + if (!sslStream) + return -1; + int r = SSL_read(sslStream, &ch, 1); + unsigned long err = SSL_get_error(sslStream, r); + switch (err) + { + case SSL_ERROR_NONE: + break; + case SSL_ERROR_ZERO_RETURN: + return -1; + case SSL_ERROR_SYSCALL: + printf("SSL read problem(syscall) %s\n", + ERR_error_string(ERR_get_error(), NULL)); + return -1; + default: + printf("SSL read problem %s\n", + ERR_error_string(ERR_get_error(), NULL)); + return -1; + } +#endif + } + else + { + int ret = recv(sock, (char *)&ch, 1, 0); + if (ret <= 0) + { + if (ret<0) + printf("read: could not receive data\n"); + disconnect(); + return -1; + } + } + return (int)ch; +} + +bool TcpSocket::readLine(DOMString &result) +{ + result = ""; + + while (isConnected()) + { + int ch = read(); + if (ch<0) + return true; + else if (ch=='\r') //we want canonical Net '\r\n' , so skip this + {} + else if (ch=='\n') + return true; + else + result.push_back((char)ch); + } + + return true; +} + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + + +//######################################################################### +//# E N D O F F I L E +//######################################################################### + diff --git a/src/dom/io/socket.h b/src/dom/io/socket.h new file mode 100644 index 000000000..5383d9bab --- /dev/null +++ b/src/dom/io/socket.h @@ -0,0 +1,112 @@ +#ifndef __DOM_SOCKET_H__ +#define __DOM_SOCKET_H__ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2005 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "dom.h" + + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + +class TcpSocket +{ +public: + + TcpSocket(); + + TcpSocket(const DOMString &hostname, int port); + + TcpSocket(const TcpSocket &other); + + virtual ~TcpSocket(); + + bool isConnected(); + + void enableSSL(bool val); + + bool connect(const DOMString &hostname, int portno); + + bool startTls(); + + bool connect(); + + bool disconnect(); + + bool setReceiveTimeout(unsigned long millis); + + long available(); + + bool write(int ch); + + bool write(const DOMString &str); + + int read(); + + bool readLine(DOMString &result); + +private: + + void init(); + + DOMString hostname; + int portno; + int sock; + bool connected; + + bool sslEnabled; + + unsigned long receiveTimeout; + +#ifdef HAVE_SSL + SSL_CTX *sslContext; + SSL *sslStream; +#endif + +}; + + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + +#endif /* __DOM_SOCKET_H__ */ +//######################################################################### +//# E N D O F F I L E +//######################################################################### + diff --git a/src/dom/io/stringstream.cpp b/src/dom/io/stringstream.cpp new file mode 100644 index 000000000..93fb0c0b5 --- /dev/null +++ b/src/dom/io/stringstream.cpp @@ -0,0 +1,158 @@ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2005 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * Our base String stream classes. We implement these to + * be based on DOMString + * + */ + + +#include "stringstream.h" + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + + +//######################################################################### +//# S T R I N G I N P U T S T R E A M +//######################################################################### + + +/** + * + */ +StringInputStream::StringInputStream(const DOMString &sourceString) + : buffer((DOMString &)sourceString) +{ + position = 0; +} + +/** + * + */ +StringInputStream::~StringInputStream() +{ + +} + +/** + * Returns the number of bytes that can be read (or skipped over) from + * this input stream without blocking by the next caller of a method for + * this input stream. + */ +int StringInputStream::available() +{ + return buffer.size() - position; +} + + +/** + * Closes this input stream and releases any system resources + * associated with the stream. + */ +void StringInputStream::close() +{ +} + +/** + * Reads the next byte of data from the input stream. -1 if EOF + */ +int StringInputStream::get() +{ + if (position >= (int)buffer.size()) + return -1; + int ch = (int) buffer[position++]; + return ch; +} + + + + +//######################################################################### +//# S T R I N G O U T P U T S T R E A M +//######################################################################### + +/** + * + */ +StringOutputStream::StringOutputStream() +{ +} + +/** + * + */ +StringOutputStream::~StringOutputStream() +{ +} + +/** + * Closes this output stream and releases any system resources + * associated with this stream. + */ +void StringOutputStream::close() +{ +} + +/** + * Flushes this output stream and forces any buffered output + * bytes to be written out. + */ +void StringOutputStream::flush() +{ + //nothing to do +} + +/** + * Writes the specified byte to this output stream. + */ +void StringOutputStream::put(XMLCh ch) +{ + buffer.push_back(ch); +} + + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + +//######################################################################### +//# E N D O F F I L E +//######################################################################### diff --git a/src/dom/io/stringstream.h b/src/dom/io/stringstream.h new file mode 100644 index 000000000..8bb4e76b1 --- /dev/null +++ b/src/dom/io/stringstream.h @@ -0,0 +1,129 @@ +#ifndef __STRINGSTREAM_H__ +#define __STRINGSTREAM_H__ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2006 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + + +#include "domstream.h" + + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + +//######################################################################### +//# S T R I N G I N P U T S T R E A M +//######################################################################### + +/** + * This class is for reading character from a DOMString + * + */ +class StringInputStream : public InputStream +{ + +public: + + StringInputStream(const DOMString &sourceString); + + virtual ~StringInputStream(); + + virtual int available(); + + virtual void close(); + + virtual int get(); + +private: + + DOMString &buffer; + + long position; + +}; // class StringInputStream + + + + +//######################################################################### +//# S T R I N G O U T P U T S T R E A M +//######################################################################### + +/** + * This class is for sending a stream to a DOMString + * + */ +class StringOutputStream : public OutputStream +{ + +public: + + StringOutputStream(); + + virtual ~StringOutputStream(); + + virtual void close(); + + virtual void flush(); + + virtual void put(XMLCh ch); + + virtual DOMString &getString() + { return buffer; } + + virtual void clear() + { buffer = ""; } + +private: + + DOMString buffer; + + +}; // class StringOutputStream + + + + + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + + + +#endif /* __STRINGSTREAM_H__ */ diff --git a/src/dom/io/uristream.cpp b/src/dom/io/uristream.cpp new file mode 100644 index 000000000..a12fe9522 --- /dev/null +++ b/src/dom/io/uristream.cpp @@ -0,0 +1,502 @@ +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2005 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * Our base String stream classes. We implement these to + * be based on DOMString + * + * Authors: + * Bob Jamison <rjamison@titan.com> + * + * Copyright (C) 2004 Inkscape.org + * + * Released under GNU GPL, read the file 'COPYING' for more information + */ + + +#include "uristream.h" + + + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + + +//######################################################################### +//# U R I I N P U T S T R E A M / R E A D E R +//######################################################################### + + +/** + * + */ +UriInputStream::UriInputStream(const URI &source) + throw (StreamException): uri((URI &)source) +{ + init(); +} + +/** + * + */ +void UriInputStream::init() throw (StreamException) +{ + //get information from uri + scheme = uri.getScheme(); + + //printf("in scheme:'%d'\n", scheme); + DOMString path = uri.getPath(); + //printf("in path:'%s'\n", path.c_str()); + + switch (scheme) + { + + case URI::SCHEME_FILE: + { + inf = fopen(path.c_str(), "rb"); + if (!inf) + { + DOMString err = "UriInputStream cannot open file "; + err.append(path); + throw StreamException(err); + } + break; + } + + case URI::SCHEME_DATA: + { + data = (unsigned char *) uri.getPath().c_str(); + //printf("in data:'%s'\n", data); + dataPos = 0; + dataLen = strlen((const char *)data); + break; + } + + case URI::SCHEME_HTTP: + case URI::SCHEME_HTTPS: + { + if (!httpClient.openGet(uri)) + { + DOMString err = "UriInputStream cannot open URL "; + err.append(uri.toString()); + throw StreamException(err); + } + break; + } + + } + + closed = false; +} + + + + + +/** + * + */ +UriInputStream::~UriInputStream() throw(StreamException) +{ + close(); +} + +/** + * Returns the number of bytes that can be read (or skipped over) from + * this input stream without blocking by the next caller of a method for + * this input stream. + */ +int UriInputStream::available() throw(StreamException) +{ + return 0; +} + + +/** + * Closes this input stream and releases any system resources + * associated with the stream. + */ +void UriInputStream::close() throw(StreamException) +{ + if (closed) + return; + + switch (scheme) + { + + case URI::SCHEME_FILE: + { + if (!inf) + return; + fflush(inf); + fclose(inf); + inf=NULL; + break; + } + + case URI::SCHEME_DATA: + { + //do nothing + break; + } + + case URI::SCHEME_HTTP: + case URI::SCHEME_HTTPS: + { + httpClient.close(); + break; + } + + }//switch + + closed = true; +} + +/** + * Reads the next byte of data from the input stream. -1 if EOF + */ +int UriInputStream::get() throw(StreamException) +{ + int retVal = -1; + if (closed) + { + return -1; + } + + switch (scheme) + { + + case URI::SCHEME_FILE: + { + if (!inf || feof(inf)) + { + retVal = -1; + } + else + { + retVal = fgetc(inf); + } + break; + } + + case URI::SCHEME_DATA: + { + if (dataPos >= dataLen) + { + retVal = -1; + } + else + { + retVal = data[dataPos++]; + } + break; + } + + case URI::SCHEME_HTTP: + case URI::SCHEME_HTTPS: + { + retVal = httpClient.read(); + break; + } + + }//switch + + return retVal; +} + + + + + + +/** + * + */ +UriReader::UriReader(const URI &uri) throw (StreamException) +{ + inputStream = new UriInputStream(uri); +} + +/** + * + */ +UriReader::~UriReader() throw (StreamException) +{ + delete inputStream; +} + +/** + * + */ +int UriReader::available() throw(StreamException) +{ + return inputStream->available(); +} + +/** + * + */ +void UriReader::close() throw(StreamException) +{ + inputStream->close(); +} + +/** + * + */ +int UriReader::get() throw(StreamException) +{ + int ch = (int)inputStream->get(); + return ch; +} + + +//######################################################################### +//# U R I O U T P U T S T R E A M / W R I T E R +//######################################################################### + +/** + * + */ +UriOutputStream::UriOutputStream(const URI &destination) + throw (StreamException): closed(false), + ownsFile(true), + outf(NULL), + uri((URI &)destination) +{ + init(); +} + + +/** + * + */ +void UriOutputStream::init() throw(StreamException) +{ + //get information from uri + scheme = uri.getScheme(); + + //printf("out schemestr:'%s' scheme:'%d'\n", schemestr, scheme); + char *cpath = NULL; + + switch (scheme) + { + + case URI::SCHEME_FILE: + { + cpath = (char *) uri.getPath().c_str(); + //printf("out path:'%s'\n", cpath); + outf = fopen(cpath, "wb"); + if (!outf) + { + DOMString err = "UriOutputStream cannot open file "; + err += cpath; + throw StreamException(err); + } + break; + } + + case URI::SCHEME_DATA: + { + data = "data:"; + break; + } + + }//switch +} + +/** + * + */ +UriOutputStream::~UriOutputStream() throw(StreamException) +{ + close(); +} + +/** + * Closes this output stream and releases any system resources + * associated with this stream. + */ +void UriOutputStream::close() throw(StreamException) +{ + if (closed) + return; + + switch (scheme) + { + + case URI::SCHEME_FILE: + { + if (!outf) + return; + fflush(outf); + if ( ownsFile ) + fclose(outf); + outf=NULL; + break; + } + + case URI::SCHEME_DATA: + { + uri = URI(data.c_str()); + break; + } + + }//switch + + closed = true; +} + +/** + * Flushes this output stream and forces any buffered output + * bytes to be written out. + */ +void UriOutputStream::flush() throw(StreamException) +{ + if (closed) + return; + + switch (scheme) + { + + case URI::SCHEME_FILE: + { + if (!outf) + return; + fflush(outf); + break; + } + + case URI::SCHEME_DATA: + { + //nothing + break; + } + + }//switch + +} + +/** + * Writes the specified byte to this output stream. + */ +void UriOutputStream::put(XMLCh ch) throw(StreamException) +{ + if (closed) + return; + + switch (scheme) + { + + case URI::SCHEME_FILE: + { + if (!outf) + return; + unsigned char uch = (unsigned char)(ch & 0xff); + fputc(uch, outf); + //fwrite(uch, 1, 1, outf); + break; + } + + case URI::SCHEME_DATA: + { + data.push_back(ch); + break; + } + + }//switch + +} + + + + + +/** + * + */ +UriWriter::UriWriter(const URI &uri) + throw (StreamException) +{ + outputStream = new UriOutputStream(uri); +} + +/** + * + */ +UriWriter::~UriWriter() throw (StreamException) +{ + delete outputStream; +} + +/** + * + */ +void UriWriter::close() throw(StreamException) +{ + outputStream->close(); +} + +/** + * + */ +void UriWriter::flush() throw(StreamException) +{ + outputStream->flush(); +} + +/** + * + */ +void UriWriter::put(XMLCh ch) throw(StreamException) +{ + int ich = (int)ch; + outputStream->put(ich); +} + + + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + + +//######################################################################### +//# E N D O F F I L E +//######################################################################### diff --git a/src/dom/io/uristream.h b/src/dom/io/uristream.h new file mode 100644 index 000000000..892ac5c68 --- /dev/null +++ b/src/dom/io/uristream.h @@ -0,0 +1,213 @@ +#ifndef __URISTREAM_H__ +#define __URISTREAM_H__ + +/** + * Phoebe DOM Implementation. + * + * This is a C++ approximation of the W3C DOM model, which follows + * fairly closely the specifications in the various .idl files, copies of + * which are provided for reference. Most important is this one: + * + * http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/idl-definitions.html + * + * Authors: + * Bob Jamison + * + * Copyright (C) 2005 Bob Jamison + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * This should be the only way that we provide sources/sinks + * to any input/output stream. + * + */ + + +#include "uri.h" +#include "domstream.h" +#include "httpclient.h" + + +namespace org +{ +namespace w3c +{ +namespace dom +{ +namespace io +{ + + +//######################################################################### +//# U R I I N P U T S T R E A M / R E A D E R +//######################################################################### + +/** + * This class is for receiving a stream of data from a resource + * defined in a URI + */ +class UriInputStream : public InputStream +{ + +public: + + UriInputStream(const URI &source) throw(StreamException); + + virtual ~UriInputStream() throw(StreamException); + + virtual int available() throw(StreamException); + + virtual void close() throw(StreamException); + + virtual int get() throw(StreamException); + +private: + + void init() throw(StreamException);//common code called by constructor + + bool closed; + + FILE *inf; //for file: uris + unsigned char *data; //for data: uris + int dataPos; // current read position in data field + int dataLen; // length of data buffer + + URI uri; + + int scheme; + + HttpClient httpClient; + +}; // class UriInputStream + + + + +/** + * This class is for receiving a stream of formatted data from a resource + * defined in a URI + */ +class UriReader : public Reader +{ + +public: + + UriReader(const URI &source) throw(StreamException); + + virtual ~UriReader() throw(StreamException); + + virtual int available() throw(StreamException); + + virtual void close() throw(StreamException); + + virtual int get() throw(StreamException); + +private: + + UriInputStream *inputStream; + +}; // class UriReader + + + +//######################################################################### +//# U R I O U T P U T S T R E A M / W R I T E R +//######################################################################### + +/** + * This class is for sending a stream to a destination resource + * defined in a URI + * + */ +class UriOutputStream : public OutputStream +{ + +public: + + UriOutputStream(const URI &destination) throw(StreamException); + + virtual ~UriOutputStream() throw(StreamException); + + virtual void close() throw(StreamException); + + virtual void flush() throw(StreamException); + + virtual void put(XMLCh ch) throw(StreamException); + +private: + + void init() throw(StreamException); //common code called by constructor + + bool closed; + bool ownsFile; + + FILE *outf; //for file: uris + DOMString data; //for data: uris + + URI uri; + + int scheme; + + HttpClient httpClient; + +}; // class UriOutputStream + + + + + +/** + * This class is for sending a stream of formatted data to a resource + * defined in a URI + */ +class UriWriter : public Writer +{ + +public: + + UriWriter(const URI &source) throw(StreamException); + + virtual ~UriWriter() throw(StreamException); + + virtual void close() throw(StreamException); + + virtual void flush() throw(StreamException); + + virtual void put(XMLCh ch) throw(StreamException); + +private: + + UriOutputStream *outputStream; + +}; // class UriReader + + + + + + +} //namespace io +} //namespace dom +} //namespace w3c +} //namespace org + +/*######################################################################### +## E N D O F F I L E +#########################################################################*/ + + +#endif /* __URISTREAM_H__ */ |
