summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
Diffstat (limited to 'Swiften/StreamStack')
-rw-r--r--Swiften/StreamStack/UnitTest/StreamStackTest.cpp4
-rw-r--r--Swiften/StreamStack/UnitTest/XMPPLayerTest.cpp7
-rw-r--r--Swiften/StreamStack/XMPPLayer.cpp6
-rw-r--r--Swiften/StreamStack/XMPPLayer.h3
4 files changed, 15 insertions, 5 deletions
diff --git a/Swiften/StreamStack/UnitTest/StreamStackTest.cpp b/Swiften/StreamStack/UnitTest/StreamStackTest.cpp
index d3c0a7c..213948a 100644
--- a/Swiften/StreamStack/UnitTest/StreamStackTest.cpp
+++ b/Swiften/StreamStack/UnitTest/StreamStackTest.cpp
@@ -1,76 +1,77 @@
/*
* Copyright (c) 2010 Remko Tronçon
* Licensed under the GNU General Public License v3.
* See Documentation/Licenses/GPLv3.txt for more information.
*/
#include <Swiften/Base/ByteArray.h>
#include <QA/Checker/IO.h>
#include <vector>
#include <boost/bind.hpp>
#include <boost/smart_ptr.hpp>
#include <cppunit/extensions/HelperMacros.h>
#include <cppunit/extensions/TestFactoryRegistry.h>
#include <Swiften/Base/ByteArray.h>
#include <Swiften/Base/Concat.h>
#include <Swiften/StreamStack/StreamStack.h>
#include <Swiften/StreamStack/LowLayer.h>
#include <Swiften/StreamStack/XMPPLayer.h>
#include <Swiften/StreamStack/StreamLayer.h>
+#include <Swiften/Parser/PlatformXMLParserFactory.h>
#include <Swiften/Parser/PayloadParsers/FullPayloadParserFactoryCollection.h>
#include <Swiften/Serializer/PayloadSerializers/FullPayloadSerializerCollection.h>
using namespace Swift;
class StreamStackTest : public CppUnit::TestFixture {
CPPUNIT_TEST_SUITE(StreamStackTest);
CPPUNIT_TEST(testWriteData_NoIntermediateStreamStack);
CPPUNIT_TEST(testWriteData_OneIntermediateStream);
CPPUNIT_TEST(testWriteData_TwoIntermediateStreamStack);
CPPUNIT_TEST(testReadData_NoIntermediateStreamStack);
CPPUNIT_TEST(testReadData_OneIntermediateStream);
CPPUNIT_TEST(testReadData_TwoIntermediateStreamStack);
CPPUNIT_TEST(testAddLayer_ExistingOnWriteDataSlot);
CPPUNIT_TEST_SUITE_END();
public:
void setUp() {
physicalStream_ = new TestLowLayer();
- xmppStream_ = new XMPPLayer(&parserFactories_, &serializers_, ClientStreamType);
+ xmppStream_ = new XMPPLayer(&parserFactories_, &serializers_, &xmlParserFactory_, ClientStreamType);
elementsReceived_ = 0;
dataWriteReceived_ = 0;
}
void tearDown() {
delete physicalStream_;
delete xmppStream_;
}
void testWriteData_NoIntermediateStreamStack() {
StreamStack testling(xmppStream_, physicalStream_);
xmppStream_->writeData("foo");
CPPUNIT_ASSERT_EQUAL(static_cast<size_t>(1), physicalStream_->data_.size());
CPPUNIT_ASSERT_EQUAL(createSafeByteArray("foo"), physicalStream_->data_[0]);
}
void testWriteData_OneIntermediateStream() {
StreamStack testling(xmppStream_, physicalStream_);
boost::shared_ptr<MyStreamLayer> xStream(new MyStreamLayer("X"));
testling.addLayer(xStream.get());
xmppStream_->writeData("foo");
CPPUNIT_ASSERT_EQUAL(static_cast<size_t>(1), physicalStream_->data_.size());
CPPUNIT_ASSERT_EQUAL(createSafeByteArray("Xfoo"), physicalStream_->data_[0]);
}
void testWriteData_TwoIntermediateStreamStack() {
StreamStack testling(xmppStream_, physicalStream_);
boost::shared_ptr<MyStreamLayer> xStream(new MyStreamLayer("X"));
boost::shared_ptr<MyStreamLayer> yStream(new MyStreamLayer("Y"));
testling.addLayer(xStream.get());
testling.addLayer(yStream.get());
@@ -140,41 +141,42 @@ class StreamStackTest : public CppUnit::TestFixture {
}
virtual void writeData(const SafeByteArray& data) {
writeDataToChildLayer(concat(createSafeByteArray(prepend_), data));
}
virtual void handleDataRead(const SafeByteArray& data) {
writeDataToParentLayer(concat(createSafeByteArray(prepend_), data));
}
private:
std::string prepend_;
};
class TestLowLayer : public LowLayer {
public:
TestLowLayer() {
}
virtual void writeData(const SafeByteArray& data) {
data_.push_back(data);
}
void onDataRead(const SafeByteArray& data) {
writeDataToParentLayer(data);
}
std::vector<SafeByteArray> data_;
};
private:
FullPayloadParserFactoryCollection parserFactories_;
FullPayloadSerializerCollection serializers_;
TestLowLayer* physicalStream_;
+ PlatformXMLParserFactory xmlParserFactory_;
XMPPLayer* xmppStream_;
int elementsReceived_;
int dataWriteReceived_;
};
CPPUNIT_TEST_SUITE_REGISTRATION(StreamStackTest);
diff --git a/Swiften/StreamStack/UnitTest/XMPPLayerTest.cpp b/Swiften/StreamStack/UnitTest/XMPPLayerTest.cpp
index bb0ce61..8123c00 100644
--- a/Swiften/StreamStack/UnitTest/XMPPLayerTest.cpp
+++ b/Swiften/StreamStack/UnitTest/XMPPLayerTest.cpp
@@ -1,70 +1,71 @@
/*
* Copyright (c) 2010 Remko Tronçon
* Licensed under the GNU General Public License v3.
* See Documentation/Licenses/GPLv3.txt for more information.
*/
#include <vector>
#include <boost/bind.hpp>
#include <cppunit/extensions/HelperMacros.h>
#include <cppunit/extensions/TestFactoryRegistry.h>
#include <Swiften/Elements/ProtocolHeader.h>
#include <Swiften/Elements/Presence.h>
#include <Swiften/Base/ByteArray.h>
#include <Swiften/StreamStack/XMPPLayer.h>
#include <Swiften/StreamStack/LowLayer.h>
+#include <Swiften/Parser/PlatformXMLParserFactory.h>
#include <Swiften/Parser/PayloadParsers/FullPayloadParserFactoryCollection.h>
#include <Swiften/Serializer/PayloadSerializers/FullPayloadSerializerCollection.h>
using namespace Swift;
class XMPPLayerTest : public CppUnit::TestFixture {
CPPUNIT_TEST_SUITE(XMPPLayerTest);
CPPUNIT_TEST(testParseData_Error);
CPPUNIT_TEST(testResetParser);
CPPUNIT_TEST(testResetParser_FromSlot);
CPPUNIT_TEST(testWriteHeader);
CPPUNIT_TEST(testWriteElement);
CPPUNIT_TEST(testWriteFooter);
CPPUNIT_TEST_SUITE_END();
public:
void setUp() {
lowLayer_ = new DummyLowLayer();
- testling_ = new XMPPLayerExposed(&parserFactories_, &serializers_, ClientStreamType);
+ testling_ = new XMPPLayerExposed(&parserFactories_, &serializers_, &xmlParserFactory_, ClientStreamType);
testling_->setChildLayer(lowLayer_);
elementsReceived_ = 0;
errorReceived_ = 0;
}
void tearDown() {
delete testling_;
delete lowLayer_;
}
void testParseData_Error() {
testling_->onError.connect(boost::bind(&XMPPLayerTest::handleError, this));
testling_->handleDataRead(createSafeByteArray("<iq>"));
CPPUNIT_ASSERT_EQUAL(1, errorReceived_);
}
void testResetParser() {
testling_->onElement.connect(boost::bind(&XMPPLayerTest::handleElement, this, _1));
testling_->onError.connect(boost::bind(&XMPPLayerTest::handleError, this));
testling_->handleDataRead(createSafeByteArray("<stream:stream to=\"example.com\" xmlns=\"jabber:client\" xmlns:stream=\"http://etherx.jabber.org/streams\" >"));
testling_->resetParser();
testling_->handleDataRead(createSafeByteArray("<stream:stream to=\"example.com\" xmlns=\"jabber:client\" xmlns:stream=\"http://etherx.jabber.org/streams\" >"));
testling_->handleDataRead(createSafeByteArray("<presence/>"));
CPPUNIT_ASSERT_EQUAL(1, elementsReceived_);
CPPUNIT_ASSERT_EQUAL(0, errorReceived_);
}
void testResetParser_FromSlot() {
testling_->onElement.connect(boost::bind(&XMPPLayerTest::handleElementAndReset, this, _1));
testling_->handleDataRead(createSafeByteArray("<stream:stream to=\"example.com\" xmlns=\"jabber:client\" xmlns:stream=\"http://etherx.jabber.org/streams\" ><presence/>"));
testling_->handleDataRead(createSafeByteArray("<stream:stream to=\"example.com\" xmlns=\"jabber:client\" xmlns:stream=\"http://etherx.jabber.org/streams\" ><presence/>"));
@@ -80,59 +81,61 @@ class XMPPLayerTest : public CppUnit::TestFixture {
CPPUNIT_ASSERT_EQUAL(std::string("<?xml version=\"1.0\"?><stream:stream xmlns=\"jabber:client\" xmlns:stream=\"http://etherx.jabber.org/streams\" to=\"example.com\" version=\"1.0\">"), lowLayer_->writtenData);
}
void testWriteElement() {
testling_->writeElement(boost::shared_ptr<Presence>(new Presence()));
CPPUNIT_ASSERT_EQUAL(std::string("<presence/>"), lowLayer_->writtenData);
}
void testWriteFooter() {
testling_->writeFooter();
CPPUNIT_ASSERT_EQUAL(std::string("</stream:stream>"), lowLayer_->writtenData);
}
void handleElement(boost::shared_ptr<Element>) {
++elementsReceived_;
}
void handleElementAndReset(boost::shared_ptr<Element>) {
++elementsReceived_;
testling_->resetParser();
}
void handleError() {
++errorReceived_;
}
private:
class XMPPLayerExposed : public XMPPLayer {
public:
XMPPLayerExposed(
PayloadParserFactoryCollection* payloadParserFactories,
PayloadSerializerCollection* payloadSerializers,
- StreamType streamType) : XMPPLayer(payloadParserFactories, payloadSerializers, streamType) {}
+ XMLParserFactory* xmlParserFactory,
+ StreamType streamType) : XMPPLayer(payloadParserFactories, payloadSerializers, xmlParserFactory, streamType) {}
using XMPPLayer::handleDataRead;
using HighLayer::setChildLayer;
};
class DummyLowLayer : public LowLayer {
public:
virtual void writeData(const SafeByteArray& data) {
writtenData += byteArrayToString(ByteArray(data.begin(), data.end()));
}
std::string writtenData;
};
FullPayloadParserFactoryCollection parserFactories_;
FullPayloadSerializerCollection serializers_;
DummyLowLayer* lowLayer_;
XMPPLayerExposed* testling_;
+ PlatformXMLParserFactory xmlParserFactory_;
int elementsReceived_;
int errorReceived_;
};
CPPUNIT_TEST_SUITE_REGISTRATION(XMPPLayerTest);
diff --git a/Swiften/StreamStack/XMPPLayer.cpp b/Swiften/StreamStack/XMPPLayer.cpp
index 1dcd84f..94afcf9 100644
--- a/Swiften/StreamStack/XMPPLayer.cpp
+++ b/Swiften/StreamStack/XMPPLayer.cpp
@@ -1,95 +1,97 @@
/*
* Copyright (c) 2010 Remko Tronçon
* Licensed under the GNU General Public License v3.
* See Documentation/Licenses/GPLv3.txt for more information.
*/
#include <Swiften/StreamStack/XMPPLayer.h>
#include <Swiften/Parser/XMPPParser.h>
#include <Swiften/Serializer/XMPPSerializer.h>
#include <Swiften/Elements/ProtocolHeader.h>
namespace Swift {
XMPPLayer::XMPPLayer(
PayloadParserFactoryCollection* payloadParserFactories,
PayloadSerializerCollection* payloadSerializers,
+ XMLParserFactory* xmlParserFactory,
StreamType streamType) :
payloadParserFactories_(payloadParserFactories),
payloadSerializers_(payloadSerializers),
+ xmlParserFactory_(xmlParserFactory),
resetParserAfterParse_(false),
inParser_(false) {
- xmppParser_ = new XMPPParser(this, payloadParserFactories_);
+ xmppParser_ = new XMPPParser(this, payloadParserFactories_, xmlParserFactory);
xmppSerializer_ = new XMPPSerializer(payloadSerializers_, streamType);
}
XMPPLayer::~XMPPLayer() {
delete xmppSerializer_;
delete xmppParser_;
}
void XMPPLayer::writeHeader(const ProtocolHeader& header) {
writeDataInternal(createSafeByteArray(xmppSerializer_->serializeHeader(header)));
}
void XMPPLayer::writeFooter() {
writeDataInternal(createSafeByteArray(xmppSerializer_->serializeFooter()));
}
void XMPPLayer::writeElement(boost::shared_ptr<Element> element) {
writeDataInternal(xmppSerializer_->serializeElement(element));
}
void XMPPLayer::writeData(const std::string& data) {
writeDataInternal(createSafeByteArray(data));
}
void XMPPLayer::writeDataInternal(const SafeByteArray& data) {
onWriteData(data);
writeDataToChildLayer(data);
}
void XMPPLayer::handleDataRead(const SafeByteArray& data) {
onDataRead(data);
inParser_ = true;
// FIXME: Converting to unsafe string. Should be ok, since we don't take passwords
// from the stream in clients. If servers start using this, and require safe storage,
// we need to fix this.
if (!xmppParser_->parse(byteArrayToString(ByteArray(data.begin(), data.end())))) {
inParser_ = false;
onError();
return;
}
inParser_ = false;
if (resetParserAfterParse_) {
doResetParser();
}
}
void XMPPLayer::doResetParser() {
delete xmppParser_;
- xmppParser_ = new XMPPParser(this, payloadParserFactories_);
+ xmppParser_ = new XMPPParser(this, payloadParserFactories_, xmlParserFactory_);
resetParserAfterParse_ = false;
}
void XMPPLayer::handleStreamStart(const ProtocolHeader& header) {
onStreamStart(header);
}
void XMPPLayer::handleElement(boost::shared_ptr<Element> stanza) {
onElement(stanza);
}
void XMPPLayer::handleStreamEnd() {
}
void XMPPLayer::resetParser() {
if (inParser_) {
resetParserAfterParse_ = true;
}
else {
doResetParser();
}
}
}
diff --git a/Swiften/StreamStack/XMPPLayer.h b/Swiften/StreamStack/XMPPLayer.h
index 54bdd42..9be00b2 100644
--- a/Swiften/StreamStack/XMPPLayer.h
+++ b/Swiften/StreamStack/XMPPLayer.h
@@ -1,67 +1,70 @@
/*
* Copyright (c) 2010 Remko Tronçon
* Licensed under the GNU General Public License v3.
* See Documentation/Licenses/GPLv3.txt for more information.
*/
#pragma once
#include <boost/shared_ptr.hpp>
#include <Swiften/Base/boost_bsignals.h>
#include <boost/noncopyable.hpp>
#include <Swiften/StreamStack/HighLayer.h>
#include <Swiften/Base/SafeByteArray.h>
#include <Swiften/Elements/Element.h>
#include <Swiften/Elements/StreamType.h>
#include <Swiften/Parser/XMPPParserClient.h>
namespace Swift {
class ProtocolHeader;
class XMPPParser;
class PayloadParserFactoryCollection;
class XMPPSerializer;
class PayloadSerializerCollection;
+ class XMLParserFactory;
class XMPPLayer : public XMPPParserClient, public HighLayer, boost::noncopyable {
public:
XMPPLayer(
PayloadParserFactoryCollection* payloadParserFactories,
PayloadSerializerCollection* payloadSerializers,
+ XMLParserFactory* xmlParserFactory,
StreamType streamType);
~XMPPLayer();
void writeHeader(const ProtocolHeader& header);
void writeFooter();
void writeElement(boost::shared_ptr<Element>);
void writeData(const std::string& data);
void resetParser();
protected:
void handleDataRead(const SafeByteArray& data);
void writeDataInternal(const SafeByteArray& data);
public:
boost::signal<void (const ProtocolHeader&)> onStreamStart;
boost::signal<void (boost::shared_ptr<Element>)> onElement;
boost::signal<void (const SafeByteArray&)> onWriteData;
boost::signal<void (const SafeByteArray&)> onDataRead;
boost::signal<void ()> onError;
private:
void handleStreamStart(const ProtocolHeader&);
void handleElement(boost::shared_ptr<Element>);
void handleStreamEnd();
void doResetParser();
private:
PayloadParserFactoryCollection* payloadParserFactories_;
XMPPParser* xmppParser_;
PayloadSerializerCollection* payloadSerializers_;
+ XMLParserFactory* xmlParserFactory_;
XMPPSerializer* xmppSerializer_;
bool resetParserAfterParse_;
bool inParser_;
};
}