コード例 #1
0
ファイル: XMPPStream.cpp プロジェクト: nob13/schneeflocke
static bool hasMechanism (const String & name, const XMLChunk & features) {
	XMLChunk mechanisms = features.getChild ("mechanisms");
	if (mechanisms.error()) return false;
	String nameUppered (name);
	boost::algorithm::to_upper(nameUppered);
	typedef std::vector<const XMLChunk*> Vec;
	Vec elements = mechanisms.getChildren("mechanism");
	for (Vec::const_iterator i = elements.begin(); i != elements.end(); i++) {
		const XMLChunk * chunk (*i);
		String text = chunk->text();
		boost::algorithm::to_upper (text);
		if (text == nameUppered) return true;
	}
	return false;
}
コード例 #2
0
ファイル: XMPPStream.cpp プロジェクト: nob13/schneeflocke
void XMPPStream::onAuthReply (const XMLChunk & chunk) {
	if (chunk.name() == "success"){
		finishOp (XMO_Authenticate, NoError);
		return;
	}
	finishOp (XMO_Authenticate, error::AuthError);
}
コード例 #3
0
ファイル: XMPPStream.cpp プロジェクト: nob13/schneeflocke
void XMPPStream::onStartTlsReply (const XMLChunk & chunk) {
	if (chunk.name() == "proceed"){
		finishOp (XMO_RequestTls, NoError);
		return;
	}
	Log (LogWarning) << LOGID << "Could not request TLS: " << chunk << std::endl;
	finishOp (XMO_RequestTls, error::NotSupported);
}
コード例 #4
0
ファイル: XMPPStream.cpp プロジェクト: nob13/schneeflocke
void XMPPStream::onResourceBind (Error e, const xmpp::Iq & iq, const XMLChunk & chunk, const XMPPStream::BindCallback & originalCallback) {
	String jid = chunk.getChild ("bind").getChild("jid").text();
	if (jid.empty() && !e){
		Log (LogWarning) << LOGID << "Could not bind, got no JID" << std::endl;
	}
	if (!e) {
		Log (LogInfo) << LOGID << "Bound resource to " << mFullJid << std::endl;
		mFullJid = jid;
	}
	notify (originalCallback, e, jid);
}
コード例 #5
0
int testNodeBuildAndParse () {
	BoshNodeBuilder builder;
	builder.addAttribute("hello", "world");
	builder.addAttribute("and", "anotherone");
	builder.addContent (sf::createByteArrayPtr ("<bla>Hi dude</bla>"));
	builder.addContent (sf::createByteArrayPtr ("<bli></bli>"));
	String s = builder.toString();
	printf ("Serialized code: %s\n", s.c_str());

	BoshNodeParser parser;
	Error e = parser.parse(s);
	tcheck1(!e);

	tcheck1(parser.attribute("hello") == "world");
	tcheck1(parser.attribute("and") == "anotherone");
	String back = parser.content();
	XMLChunk chunk = xml::parseDocument(back.c_str(), back.length());
	tcheck1 (chunk.getChild("bla").text() == "Hi dude");
	tcheck1 (chunk.getHasChild("bli"));
	return 0;
}
コード例 #6
0
/// Tries to build an XMLChunk of just opening Element
static Error fillElement (const char * start, size_t len, XMLChunk * dest) {
	assert (dest);
	String prep (start, start + len);

	if (prep.length() < 2) return error::BadDeserialization;
	if (prep.substr (prep.length() - 2) == "/>") return error::BadDeserialization;
	if (prep[0] != '<') return error::BadDeserialization;
	size_t np = findWhiteSpace (prep);
	String name;
	if (np == prep.npos){
		// no attributes
		name = prep.substr (1, prep.length() - 2);
	} else {
		name = prep.substr (1, np - 1);
	}
	prep += "</" + name + ">";
	XMLChunk chunk = xml::parseDocument(prep.c_str(), prep.length());
	if (chunk.error() || chunk.children().size() != 1) return error::BadDeserialization;
	*dest = chunk.children()[0];
	return NoError;
}
コード例 #7
0
void XMLStreamDecoder::handleData () {
	State before = mState;
	while (true) {
		if (mState != before && mStateChange) {
			mStateChange ();
		}
		before = mState;
		if (mState == XS_Closed || mState == XS_Error) return;

		skipWhiteSpaces (mInputBuffer);

		switch (mState) {
		case XS_Start:{
			int code = xml::xmlBeginning(mInputBuffer);
			if (code == 0) return;
			if (code < 0) {
				mErrorText = "Invalid XML Begin";
				mError = error::BadDeserialization;
				mState = XS_Error;
				continue;
			}
			// we have enough
			mInputBuffer.l_truncate(code);
			mState = XS_ReadXmlBegin;
			continue;
		}
		case XS_ReadXmlBegin: {
			int code = xml::fullTag (mInputBuffer);
			if (code < 0) {
				mErrorText = "Invalid Start Element";
				mError = error::BadDeserialization;
				mState = XS_Error;
				continue;
			}
			if (code == 0) return;
			// we have enough
			Error e = fillElement (mInputBuffer.const_c_array(), code, &mOpener);
			if (e) {
				mError = e;
				mErrorText = "Invalid Start element";
				mState = XS_Error;
				continue;
			}
			mInputBuffer.l_truncate(code);
			mState = XS_ReadOpener;
			continue;
		}
		case XS_ReadOpener:{
			int code = xml::fullTag (mInputBuffer);
			if (code < 0) {
				mErrorText = "InvalidElement";
				mError = error::BadDeserialization;
				mState = XS_Error;
				continue;
			}
			if (code == 0) return;
			if (mInputBuffer[0] == '<' && mInputBuffer[1] == '/') {
				mInputBuffer.l_truncate(code);
				mState = XS_Closed;
				continue;
			}
			code = xml::completionDetection(mInputBuffer);
			if (code < 0) {
				mErrorText = "Invalid Element";
				mError = error::BadDeserialization;
				mState = XS_Error;
				continue;
			}
			if (code ==  0) return;
			XMLChunk chunk = xml::parseDocument(mInputBuffer.const_c_array(), code);
			if (chunk.error() || chunk.children().size() != 1){
				mErrorText = "Invalid Element";
				mError = error::BadDeserialization;
				mState = XS_Error;
				continue;
			}
			if (mChunkRead){
				mChunkRead (chunk.children()[0]);
			}
			mInputBuffer.l_truncate(code);
			continue;
		}
		default:
			assert (!"Should not come here!");
			return;
		}
	}
}
コード例 #8
0
ファイル: XMPPStream.cpp プロジェクト: nob13/schneeflocke
void XMPPStream::onXmlChunkRead (const XMLChunk & chunk) {
	if (mNextChunkHandler){
		mNextChunkHandler (chunk);
		mNextChunkHandler.clear();
		return;
	}

	if (chunk.name() == "stream:features") {
		if (mReceivedFeatures) {
			Log (LogWarning) << LOGID << "Double receive features!" << std::endl;
		}
		mFeatures         = chunk;
		mReceivedFeatures = true;
		finishOp (XMO_WaitFeatures, NoError);
		return;
	} else
	if (chunk.name() == "iq") {
		xmpp::Iq iq;
		bool suc = iq.decode(chunk);
		if (!suc) {
			Log (LogWarning) << LOGID << "Could not decode " << chunk << std::endl;
			return;
		}
		String id = chunk.getAttribute("id");
		if (id.empty()){
			Log (LogWarning) << LOGID << "Received empty id in iq" << std::endl;
		}

		OpenIqMap::iterator i = mOpenIqs.find (id);
		if (i != mOpenIqs.end()){
			IqResultCallback cb = i->second;
			mOpenIqs.erase(i); // make this behaviour selectable?
			if (cb){
				notifyAsync (cb, NoError, iq, chunk);
			} else {
				Log (LogInfo) << LOGID << "Ignoring iq reply as there is no callback set (id=" << iq.id << ")" << std::endl;
			}
		} else {
			if (mIncomingIq) {
				notifyAsync (mIncomingIq, iq, chunk);
			} else {
				Log (LogWarning) << LOGID << "No iq handler set!" << std::endl;
			}
		}
	} else
	if (chunk.name() == "message") {
		xmpp::Message m;
		bool suc = m.decode(chunk);
		if (!suc) {
			Log (LogWarning) << LOGID << "Could not decode message " << chunk << std::endl;
			return;
		}
		notifyAsync (mIncomingMessage, m, chunk);
	} else
	if (chunk.name() == "presence") {
		xmpp::PresenceInfo p;
		bool suc = p.decode(chunk);
		if (!suc) {
			Log (LogWarning) << LOGID << "Could not decode presence " << chunk << std::endl;
			return;
		}
		notifyAsync (mIncomingPresence, p, chunk);
	} else
	if (chunk.name() == "stream:error"){
		String text = chunk.getChild("text").text();
		if (mIncomingStreamError){
			notifyAsync (mIncomingStreamError, text, chunk);
		} else {
			Log (LogWarning) << LOGID << "Discarding incoming stream error, no delegate " << text << std::endl;
		}
	} else {
		Log (LogWarning) << LOGID << "Unknown chunk type " << chunk << std::endl;
	}
}