Beispiel #1
0
bool CJabberProto::OnIncomingNote(const TCHAR *szFrom, HXML hXml)
{
	if (!m_options.AcceptNotes)
		return false;

	if (!szFrom || !hXml) return true;
	CNoteItem *pItem = new CNoteItem(hXml, (TCHAR *)szFrom);
	if (!pItem->IsNotEmpty())
	{
		delete pItem;
		return true;
	}

	if (m_options.AutosaveNotes && HContactFromJID(szFrom))
	{
		ProcessIncomingNote(pItem, true);
		return false;
	}

	CLISTEVENT cle = {0};
	char szService[256];
	mir_snprintf( szService, sizeof(szService),"%s%s", m_szModuleName, JS_INCOMING_NOTE_EVENT );
	cle.cbSize = sizeof(CLISTEVENT);
	cle.hIcon = (HICON)LoadIconEx("notes");
	cle.flags = CLEF_PROTOCOLGLOBAL|CLEF_TCHAR;
	cle.hDbEvent = (HANDLE)("test");
	cle.lParam = (LPARAM)pItem;
	cle.pszService = szService;
	cle.ptszTooltip = TranslateT("Incoming note");
	CallService(MS_CLIST_ADDEVENT, 0, (LPARAM)&cle);
	
	return true;
}
Beispiel #2
0
void CJabberProto::OnIqResultGetCollection(HXML iqNode, CJabberIqInfo*)
{
	if ( mir_tstrcmp( xmlGetAttrValue(iqNode, _T("type")), _T("result")))
		return;

	HXML chatNode = xmlGetChild(iqNode, "chat");
	if (!chatNode || mir_tstrcmp( xmlGetAttrValue(chatNode, _T("xmlns")), JABBER_FEAT_ARCHIVE))
		return;

	const TCHAR* start = xmlGetAttrValue(chatNode, _T("start"));
	const TCHAR* with  = xmlGetAttrValue(chatNode, _T("with"));
	if (!start || !with)
		return;

	MCONTACT hContact = HContactFromJID(with);
	time_t tmStart = str2time(start);
	if (hContact == 0 || tmStart == 0)
		return;

	_tzset();

	for (int nodeIdx = 0; ; nodeIdx++) {
		HXML itemNode = xmlGetChild(chatNode, nodeIdx);
		if (!itemNode)
			break;

		int from;
		const TCHAR *itemName = xmlGetName(itemNode);
		if (!mir_tstrcmp(itemName, _T("to")))
			from = DBEF_SENT;
		else if (!mir_tstrcmp(itemName, _T("from")))
			from = 0;
		else
			continue;

		HXML body = xmlGetChild(itemNode, "body");
		if (!body)
			continue;

		const TCHAR *tszBody = xmlGetText(body);
		const TCHAR *tszSecs = xmlGetAttrValue(itemNode, _T("secs"));
		if (!tszBody || !tszSecs)
			continue;

		ptrA szEventText( mir_utf8encodeT(tszBody));

		DBEVENTINFO dbei = { sizeof(DBEVENTINFO) };
		dbei.eventType = EVENTTYPE_MESSAGE;
		dbei.szModule = m_szModuleName;
		dbei.cbBlob = (DWORD)strlen(szEventText);
		dbei.flags = DBEF_READ + DBEF_UTF + from;
		dbei.pBlob = (PBYTE)(char*)szEventText;
		dbei.timestamp = tmStart + _ttol(tszSecs) - timezone;
		if (!IsDuplicateEvent(hContact, dbei))
			db_event_add(hContact, &dbei);
	}
}
Beispiel #3
0
void CJabberProto::MenuUpdateSrmmIcon(JABBER_LIST_ITEM *item)
{
    if (item->list != LIST_ROSTER)
        return;

    MCONTACT hContact = HContactFromJID(item->jid);
    if (!hContact)
        return;

    StatusIconData sid = { sizeof(sid) };
    sid.szModule = m_szModuleName;
    sid.flags = item->arResources.getCount() ? 0 : MBF_DISABLED;
    Srmm_ModifyIcon(hContact, &sid);
}
Beispiel #4
0
void CJabberProto::UpdateMirVer(JABBER_LIST_ITEM *item)
{
	MCONTACT hContact = HContactFromJID(item->jid);
	if (!hContact)
		return;

	debugLog(_T("JabberUpdateMirVer: for jid %s"), item->jid);

	pResourceStatus p(NULL);
	if (item->resourceMode == RSMODE_LASTSEEN)
		p = item->m_pLastSeenResource;
	else if (item->resourceMode == RSMODE_MANUAL)
		p = item->m_pManualResource;

	if (p)
		UpdateMirVer(hContact, p);
}
Beispiel #5
0
void CJabberProto::OnIqResultGetCollectionList(HXML iqNode, CJabberIqInfo*)
{
	const TCHAR *to = xmlGetAttrValue(iqNode, _T("to"));
	if (to == NULL || mir_tstrcmp( xmlGetAttrValue(iqNode, _T("type")), _T("result")))
		return;

	HXML list = xmlGetChild(iqNode, "list");
	if (!list || mir_tstrcmp( xmlGetAttrValue(list, _T("xmlns")), JABBER_FEAT_ARCHIVE))
		return;

	MCONTACT hContact = NULL;
	time_t tmLast = 0;

	for (int nodeIdx = 1; ; nodeIdx++) {
		HXML itemNode = xmlGetNthChild(list, _T("chat"), nodeIdx);
		if (!itemNode)
			break;

		const TCHAR* start = xmlGetAttrValue(itemNode, _T("start"));
		const TCHAR* with  = xmlGetAttrValue(itemNode, _T("with"));
		if (!start || !with)
			continue;

		if (hContact == NULL) {
			if ((hContact = HContactFromJID(with)) == NULL)
				continue;

			tmLast = getDword(hContact, "LastCollection", 0);
		}

		m_ThreadInfo->send(
			XmlNodeIq( AddIQ(&CJabberProto::OnIqResultGetCollection, JABBER_IQ_TYPE_GET))
				<< XCHILDNS( _T("retrieve"), JABBER_FEAT_ARCHIVE) << XATTR(_T("with"), with) << XATTR(_T("start"), start));

		time_t tmThis = str2time(start);
		if ( tmThis > tmLast) {
			tmLast = tmThis;
			setDword(hContact, "LastCollection", tmLast+1);
		}
	}
}
INT_PTR __cdecl CJabberProto::JabberServiceParseXmppURI(WPARAM, LPARAM lParam)
{
	TCHAR *arg = (TCHAR *)lParam;
	if (arg == NULL)
		return 1;

	// skip leading prefix
	TCHAR szUri[ 1024 ];
	_tcsncpy_s(szUri, SIZEOF(szUri), arg, _TRUNCATE);
	TCHAR *szJid = _tcschr(szUri, _T(':'));
	if (szJid == NULL)
		return 1;

	// skip //
	for (++szJid; *szJid == _T('/'); ++szJid);

	// empty jid?
	if (!*szJid)
		return 1;

	// command code
	TCHAR *szCommand = szJid;
	szCommand = _tcschr(szCommand, _T('?'));
	if (szCommand)
		*(szCommand++) = 0;

	// parameters
	TCHAR *szSecondParam = szCommand ? _tcschr(szCommand, _T(';')) : NULL;
	if (szSecondParam)
		*(szSecondParam++) = 0;

	// no command or message command
	if (!szCommand || (szCommand && !_tcsicmp(szCommand, _T("message")))) {
		// message
		if (!ServiceExists(MS_MSG_SENDMESSAGEW))
			return 1;

		TCHAR *szMsgBody = NULL;
		HANDLE hContact = HContactFromJID(szJid, TRUE);
		if (hContact == NULL)
			hContact = DBCreateContact(szJid, szJid, TRUE, TRUE);
		if (hContact == NULL)
			return 1;

		if (szSecondParam) { //there are parameters to message
			szMsgBody = _tcsstr(szSecondParam, _T("body="));
			if (szMsgBody) {
				szMsgBody += 5;
				TCHAR *szDelim = _tcschr(szMsgBody, _T(';'));
				if (szDelim)
					szDelim = 0;
				JabberHttpUrlDecode(szMsgBody);
			}
		}

		CallService(MS_MSG_SENDMESSAGEW, (WPARAM)hContact, (LPARAM)szMsgBody);
		return 0;
	}
	
	if (!_tcsicmp(szCommand, _T("roster"))) {
		if (!HContactFromJID(szJid)) {
			JABBER_SEARCH_RESULT jsr = { 0 };
			jsr.hdr.cbSize = sizeof(JABBER_SEARCH_RESULT);
			jsr.hdr.flags = PSR_TCHAR;
			jsr.hdr.nick = szJid;
			jsr.hdr.id = szJid;
			_tcsncpy(jsr.jid, szJid, SIZEOF(jsr.jid) - 1);

			ADDCONTACTSTRUCT acs;
			acs.handleType = HANDLE_SEARCHRESULT;
			acs.szProto = m_szModuleName;
			acs.psr = &jsr.hdr;
			CallService(MS_ADDCONTACT_SHOW, 0, (LPARAM)&acs);
		}
		return 0;
	}
	
	// chat join invitation
	if (!_tcsicmp(szCommand, _T("join"))) {
		GroupchatJoinRoomByJid(NULL, szJid);
		return 0;
	}
	
	// service discovery request
	if (!_tcsicmp(szCommand, _T("disco"))) {
		OnMenuHandleServiceDiscovery(0, (LPARAM)szJid);
		return 0;
	}
	
	// ad-hoc commands
	if (!_tcsicmp(szCommand, _T("command"))) {
		if (szSecondParam) {
			if (!_tcsnicmp(szSecondParam, _T("node="), 5)) {
				szSecondParam += 5;
				if (!*szSecondParam)
					szSecondParam = NULL;
			}
			else szSecondParam = NULL;
		}
		CJabberAdhocStartupParams* pStartupParams = new CJabberAdhocStartupParams(this, szJid, szSecondParam);
		ContactMenuRunCommands(0, (LPARAM)pStartupParams);
		return 0;
	}
	
	// send file
	if (!_tcsicmp(szCommand, _T("sendfile"))) {
		if (!ServiceExists(MS_FILE_SENDFILE))
			return 1;

		HANDLE hContact = HContactFromJID(szJid, TRUE);
		if (hContact == NULL)
			hContact = DBCreateContact(szJid, szJid, TRUE, TRUE);
		if (hContact == NULL)
			return 1;
		CallService(MS_FILE_SENDFILE, (WPARAM)hContact, (LPARAM)NULL);
		return 0;
	}

	return 1; /* parse failed */
}
Beispiel #7
0
BOOL CJabberProto::OnRosterPushRequest(HXML, CJabberIqInfo *pInfo)
{
	HXML queryNode = pInfo->GetChildNode();

	// RFC 3921 #7.2 Business Rules
	if (pInfo->GetFrom()) {
		TCHAR *szFrom = JabberPrepareJid(pInfo->GetFrom());
		if (!szFrom)
			return TRUE;

		TCHAR *szTo = JabberPrepareJid(m_ThreadInfo->fullJID);
		if (!szTo) {
			mir_free(szFrom);
			return TRUE;
		}

		TCHAR *pDelimiter = _tcschr(szFrom, _T('/'));
		if (pDelimiter) *pDelimiter = 0;

		pDelimiter = _tcschr(szTo, _T('/'));
		if (pDelimiter) *pDelimiter = 0;

		BOOL bRetVal = mir_tstrcmp(szFrom, szTo) == 0;

		mir_free(szFrom);
		mir_free(szTo);

		// invalid JID
		if (!bRetVal) {
			debugLog(_T("<iq/> attempt to hack via roster push from %s"), pInfo->GetFrom());
			return TRUE;
		}
	}

	JABBER_LIST_ITEM *item;
	MCONTACT hContact = NULL;
	const TCHAR *jid, *str;

	debugLogA("<iq/> Got roster push, query has %d children", XmlGetChildCount(queryNode));
	for (int i = 0;; i++) {
		HXML itemNode = XmlGetChild(queryNode, i);
		if (!itemNode)
			break;

		if (mir_tstrcmp(XmlGetName(itemNode), _T("item")) != 0)
			continue;
		if ((jid = XmlGetAttrValue(itemNode, _T("jid"))) == NULL)
			continue;
		if ((str = XmlGetAttrValue(itemNode, _T("subscription"))) == NULL)
			continue;

		// we will not add new account when subscription=remove
		if (!mir_tstrcmp(str, _T("to")) || !mir_tstrcmp(str, _T("both")) || !mir_tstrcmp(str, _T("from")) || !mir_tstrcmp(str, _T("none"))) {
			const TCHAR *name = XmlGetAttrValue(itemNode, _T("name"));
			ptrT nick((name != NULL) ? mir_tstrdup(name) : JabberNickFromJID(jid));
			if (nick != NULL) {
				if ((item = ListAdd(LIST_ROSTER, jid)) != NULL) {
					replaceStrT(item->nick, nick);

					HXML groupNode = XmlGetChild(itemNode, "group");
					replaceStrT(item->group, XmlGetText(groupNode));

					if ((hContact = HContactFromJID(jid, 0)) == NULL) {
						// Received roster has a new JID.
						// Add the jid (with empty resource) to Miranda contact list.
						hContact = DBCreateContact(jid, nick, FALSE, FALSE);
					}
					else setTString(hContact, "jid", jid);

					if (name != NULL) {
						ptrT tszNick(getTStringA(hContact, "Nick"));
						if (tszNick != NULL) {
							if (mir_tstrcmp(nick, tszNick) != 0)
								db_set_ts(hContact, "CList", "MyHandle", nick);
							else
								db_unset(hContact, "CList", "MyHandle");
						}
						else db_set_ts(hContact, "CList", "MyHandle", nick);
					}
					else db_unset(hContact, "CList", "MyHandle");

					if (!m_options.IgnoreRosterGroups) {
						if (item->group != NULL) {
							Clist_CreateGroup(0, item->group);
							db_set_ts(hContact, "CList", "Group", item->group);
						}
						else db_unset(hContact, "CList", "Group");
					}
				}
			}
		}

		if ((item = ListGetItemPtr(LIST_ROSTER, jid)) != NULL) {
			if (!mir_tstrcmp(str, _T("both"))) item->subscription = SUB_BOTH;
			else if (!mir_tstrcmp(str, _T("to"))) item->subscription = SUB_TO;
			else if (!mir_tstrcmp(str, _T("from"))) item->subscription = SUB_FROM;
			else item->subscription = SUB_NONE;
			debugLog(_T("Roster push for jid=%s, set subscription to %s"), jid, str);
			// subscription = remove is to remove from roster list
			// but we will just set the contact to offline and not actually
			// remove, so that history will be retained.
			if (!mir_tstrcmp(str, _T("remove"))) {
				if ((hContact = HContactFromJID(jid)) != NULL) {
					SetContactOfflineStatus(hContact);
					ListRemove(LIST_ROSTER, jid);
				}
			}
			else if (isChatRoom(hContact))
				db_unset(hContact, "CList", "Hidden");
			else
				UpdateSubscriptionInfo(hContact, item);
		}
	}

	UI_SAFE_NOTIFY(m_pDlgServiceDiscovery, WM_JABBER_TRANSPORT_REFRESH);
	RebuildInfoFrame();
	return TRUE;
}
Beispiel #8
0
MCONTACT CJabberProto::ContactFromJID(LPCTSTR jid)
{
	if (jid == NULL) return NULL;
	return HContactFromJID(jid);
}
Beispiel #9
0
MCONTACT CJabberProto::ContactFromJID(LPCTSTR jid)
{
	return HContactFromJID(jid);
}