Exemplo n.º 1
0
int CIcqProto::OnPreBuildContactMenu(WPARAM hContact, LPARAM)
{
	if (hContact == NULL)
		return 0;

	if (icqOnline()) {
		BOOL bCtrlPressed = (GetKeyState(VK_CONTROL)&0x8000 ) != 0;

		DWORD dwUin = getContactUin(hContact);

		Menu_ShowItem(g_hContactMenuItems[ICMI_AUTH_REQUEST],
			dwUin && (bCtrlPressed || (getByte(hContact, "Auth", 0) && getWord(hContact, DBSETTING_SERVLIST_ID, 0))));
		Menu_ShowItem(g_hContactMenuItems[ICMI_AUTH_GRANT], dwUin && (bCtrlPressed || getByte(hContact, "Grant", 0)));
		Menu_ShowItem(g_hContactMenuItems[ICMI_AUTH_REVOKE],
			dwUin && (bCtrlPressed || (getByte("PrivacyItems", 0) && !getByte(hContact, "Grant", 0))));
		Menu_ShowItem(g_hContactMenuItems[ICMI_ADD_TO_SERVLIST],
			m_bSsiEnabled && !getWord(hContact, DBSETTING_SERVLIST_ID, 0) &&
			!getWord(hContact, DBSETTING_SERVLIST_IGNORE, 0) &&
			!db_get_b(hContact, "CList", "NotOnList", 0));
	}

	Menu_ShowItem(g_hContactMenuItems[ICMI_OPEN_PROFILE],getContactUin(hContact) != 0);
	BYTE bXStatus = getContactXStatus(hContact);

	Menu_ShowItem(g_hContactMenuItems[ICMI_XSTATUS_DETAILS], m_bHideXStatusUI ? 0 : bXStatus != 0);
	if (bXStatus && !m_bHideXStatusUI) {
		if (bXStatus > 0 && bXStatus <= XSTATUS_COUNT)
			Menu_ModifyItem(g_hContactMenuItems[ICMI_XSTATUS_DETAILS], NULL, getXStatusIcon(bXStatus, LR_SHARED));
		else
			Menu_ModifyItem(g_hContactMenuItems[ICMI_XSTATUS_DETAILS], NULL, Skin_LoadIcon(SKINICON_OTHER_SMALLDOT));
	}

	return 0;
}
Exemplo n.º 2
0
// Returns TRUE if user was queued
// Returns FALSE if the list was full
BOOL CIcqProto::icq_QueueUser(MCONTACT hContact)
{
	if ( !infoUpdateMutex )
		return FALSE;

	if (nInfoUserCount < LISTSIZE)
	{
		int i, nChecked = 0, nFirstFree = -1;
		BOOL bFound = FALSE;

		infoUpdateMutex->Enter();

		// Check if in list
		for (i = 0; (i<LISTSIZE && nChecked < nInfoUserCount); i++)
		{
			if (m_infoUpdateList[i].hContact)
			{
				nChecked++;
				if (m_infoUpdateList[i].hContact == hContact)
				{
					bFound = TRUE;
					break;
				}
			}
			else if (nFirstFree == -1)
			{
				nFirstFree = i;
			}
		}
		if (nFirstFree == -1)
			nFirstFree = i;

		// Add to list
		if (!bFound)
		{
			DWORD dwUin = getContactUin(hContact);

			if (dwUin)
			{
				m_infoUpdateList[nFirstFree].dwUin = dwUin;
				m_infoUpdateList[nFirstFree].hContact = hContact;
				m_infoUpdateList[nFirstFree].queued = time(NULL);
				nInfoUserCount++;
#ifdef _DEBUG
				debugLogA("Queued user %u, place %u, count %u", dwUin, nFirstFree, nInfoUserCount);
#endif
				// Notify worker thread
				if (hInfoQueueEvent && bInfoUpdateEnabled)
					SetEvent(hInfoQueueEvent);
			}
		}

		infoUpdateMutex->Leave();

		return TRUE;
	}

	return FALSE;
}
Exemplo n.º 3
0
INT_PTR CIcqProto::OpenWebProfile(WPARAM wParam, LPARAM lParam)
{
	HANDLE hContact = (HANDLE)wParam;
	DWORD dwUin = getContactUin(hContact);
	char url[256];
	mir_snprintf(url, sizeof(url), "http://www.icq.com/people/%d",dwUin);
	return CallService(MS_UTILS_OPENURL, 1, (LPARAM)url);
}
Exemplo n.º 4
0
int CIcqProto::OnPreBuildContactMenu(WPARAM wParam, LPARAM)
{
	HANDLE hContact = (HANDLE)wParam;
	if (hContact == NULL)
		return 0;

	if (icqOnline())
	{
		BOOL bCtrlPressed = (GetKeyState(VK_CONTROL)&0x8000 ) != 0;

		DWORD dwUin = getContactUin(hContact);


		sttEnableMenuItem(g_hContactMenuItems[ICMI_AUTH_REQUEST], 
			dwUin && (bCtrlPressed || (getSettingByte((HANDLE)wParam, "Auth", 0) && getSettingWord((HANDLE)wParam, DBSETTING_SERVLIST_ID, 0))));
		sttEnableMenuItem(g_hContactMenuItems[ICMI_AUTH_GRANT], dwUin && (bCtrlPressed || getSettingByte((HANDLE)wParam, "Grant", 0)));
		sttEnableMenuItem(g_hContactMenuItems[ICMI_AUTH_REVOKE], 
			dwUin && (bCtrlPressed || (getSettingByte(NULL, "PrivacyItems", 0) && !getSettingByte((HANDLE)wParam, "Grant", 0))));
		sttEnableMenuItem(g_hContactMenuItems[ICMI_ADD_TO_SERVLIST], 
			m_bSsiEnabled && !getSettingWord((HANDLE)wParam, DBSETTING_SERVLIST_ID, 0) && 
			!getSettingWord((HANDLE)wParam, DBSETTING_SERVLIST_IGNORE, 0) &&
			!DBGetContactSettingByte(hContact, "CList", "NotOnList", 0));
	}
	
	sttEnableMenuItem(g_hContactMenuItems[ICMI_OPEN_PROFILE],getContactUin(hContact) != 0);
	BYTE bXStatus = getContactXStatus((HANDLE)wParam);
	
	sttEnableMenuItem(g_hContactMenuItems[ICMI_XSTATUS_DETAILS], m_bHideXStatusUI ? 0 : bXStatus != 0);
	if (bXStatus && !m_bHideXStatusUI) {
		CLISTMENUITEM clmi = {0};

		clmi.cbSize = sizeof(clmi);
		clmi.flags = CMIM_ICON;

		if (bXStatus > 0 && bXStatus <= XSTATUS_COUNT)
			clmi.hIcon = getXStatusIcon(bXStatus, LR_SHARED);
		else
			clmi.hIcon = LoadSkinnedIcon(SKINICON_OTHER_SMALLDOT);
		CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)g_hContactMenuItems[ICMI_XSTATUS_DETAILS], (LPARAM)&clmi);
	}

	return 0;
}
Exemplo n.º 5
0
void CIcqProto::handleLocationFam(BYTE *pBuffer, WORD wBufferLength, snac_header *pSnacHeader)
{
	switch (pSnacHeader->wSubtype) {

	case ICQ_LOCATION_RIGHTS_REPLY: // Reply to CLI_REQLOCATION
		NetLog_Server("Server sent SNAC(x02,x03) - SRV_LOCATION_RIGHTS_REPLY");
		break;

	case ICQ_LOCATION_USR_INFO_REPLY: // AIM user info reply
		handleLocationUserInfoReply(pBuffer, wBufferLength, pSnacHeader->dwRef);
		break;

	case ICQ_ERROR:
		{ 
			WORD wError;
			HANDLE hCookieContact;
			cookie_fam15_data *pCookieData;


			if (wBufferLength >= 2)
				unpackWord(&pBuffer, &wError);
			else 
				wError = 0;

			if (wError == 4)
			{
				if (FindCookie(pSnacHeader->dwRef, &hCookieContact, (void**)&pCookieData) && !getContactUin(hCookieContact) && pCookieData->bRequestType == REQUESTTYPE_PROFILE)
				{
					BroadcastAck(hCookieContact, ACKTYPE_GETINFO, ACKRESULT_FAILED, (HANDLE)1 ,0);

					ReleaseCookie(pSnacHeader->dwRef);
				}
			}

			LogFamilyError(ICQ_LOCATION_FAMILY, wError);
			break;
		}

	default:
		NetLog_Server("Warning: Ignoring SNAC(x%02x,x%02x) - Unknown SNAC (Flags: %u, Ref: %u)", ICQ_LOCATION_FAMILY, pSnacHeader->wSubtype, pSnacHeader->wFlags, pSnacHeader->dwRef);
		break;
	}
}
Exemplo n.º 6
0
// Returns TRUE if user was queued
// Returns FALSE if the list was full
BOOL CIcqProto::icq_QueueUser(MCONTACT hContact)
{
	if (!hInfoQueueEvent)
		return FALSE;

	if (nInfoUserCount >= LISTSIZE)
		return FALSE;

	int i, nChecked = 0, nFirstFree = -1;

	mir_cslock l(infoUpdateMutex);

	// Check if in list
	for (i = 0; (i < LISTSIZE && nChecked < nInfoUserCount); i++) {
		if (m_infoUpdateList[i].hContact) {
			nChecked++;
			if (m_infoUpdateList[i].hContact == hContact)
				return TRUE;
		}
		else if (nFirstFree == -1)
			nFirstFree = i;
	}
	if (nFirstFree == -1)
		nFirstFree = i;

	// Add to list
	DWORD dwUin = getContactUin(hContact);
	if (dwUin) {
		m_infoUpdateList[nFirstFree].dwUin = dwUin;
		m_infoUpdateList[nFirstFree].hContact = hContact;
		m_infoUpdateList[nFirstFree].queued = time(NULL);
		nInfoUserCount++;

		debugLogA("Queued user %u, place %u, count %u", dwUin, nFirstFree, nInfoUserCount);

		// Notify worker thread
		if (hInfoQueueEvent && bInfoUpdateEnabled)
			SetEvent(hInfoQueueEvent);
	}

	return TRUE;
}
Exemplo n.º 7
0
INT_PTR CIcqProto::OpenWebProfile(WPARAM hContact, LPARAM)
{
	Utils_OpenUrl(CMStringA(FORMAT, "http://www.icq.com/people/%d", getContactUin(hContact)));
	return 0;
}
Exemplo n.º 8
0
void CIcqProto::parseDirectoryUserDetailsData(MCONTACT hContact, oscar_tlv_chain *cDetails, DWORD dwCookie, cookie_directory_data *pCookieData, WORD wReplySubType)
{
	oscar_tlv *pTLV;
	WORD wRecordCount;

	if (pCookieData->bRequestType == DIRECTORYREQUEST_INFOMULTI && !hContact)
	{
		DWORD dwUin = 0;
		char *szUid = cDetails->getString(0x32, 1);
		if (!szUid) 
		{
			debugLogA("Error: Received unrecognized data from the directory");
			return;
		}

		if (IsStringUIN(szUid))
			dwUin = atoi(szUid);

		hContact = HContactFromUID(dwUin, szUid, NULL);
		if (hContact == INVALID_CONTACT_ID)
		{
			debugLogA("Error: Received details for unknown contact \"%s\"", szUid);
			SAFE_FREE(&szUid);
			return;
		}
#ifdef _DEBUG
		else
			debugLogA("Received user info for %s from directory", szUid);
#endif
		SAFE_FREE(&szUid);
	}
#ifdef _DEBUG
  else
	{
		char *szUid = cDetails->getString(0x32, 1);

    if (!hContact)
			debugLogA("Received owner user info from directory");
		else
			debugLogA("Received user info for %s from directory", szUid);
		SAFE_FREE(&szUid);
	}
#endif

	pTLV = cDetails->getTLV(0x50, 1);
	if (pTLV && pTLV->wLen > 0)
		writeDbInfoSettingTLVStringUtf(hContact, "e-mail",  cDetails, 0x50); // Verified e-mail
	else
		writeDbInfoSettingTLVStringUtf(hContact, "e-mail",  cDetails, 0x55); // Pending e-mail

	writeDbInfoSettingTLVStringUtf(hContact, "FirstName", cDetails, 0x64);
	writeDbInfoSettingTLVStringUtf(hContact, "LastName",  cDetails, 0x6E);
	writeDbInfoSettingTLVStringUtf(hContact, "Nick",      cDetails, 0x78);
	// Home Address
	parseUserInfoRecord(hContact, cDetails->getTLV(0x96, 1), rAddress, SIZEOF(rAddress), 1);
	// Origin Address
	parseUserInfoRecord(hContact, cDetails->getTLV(0xA0, 1), rOriginAddress, SIZEOF(rOriginAddress), 1);
	// Phones
	pTLV = cDetails->getTLV(0xC8, 1);
	if (pTLV && pTLV->wLen >= 2)
	{
		BYTE *pRecords = pTLV->pData;
		unpackWord(&pRecords, &wRecordCount);
		oscar_tlv_record_list *cPhones = readIntoTLVRecordList(&pRecords, pTLV->wLen - 2, wRecordCount);
		if (cPhones)
		{
			oscar_tlv_chain *cPhone;
			cPhone = cPhones->getRecordByTLV(0x6E, 1);
			writeDbInfoSettingTLVStringUtf(hContact, "Phone", cPhone, 0x64);
			cPhone = cPhones->getRecordByTLV(0x6E, 2);
			writeDbInfoSettingTLVStringUtf(hContact, "CompanyPhone", cPhone, 0x64);
			cPhone = cPhones->getRecordByTLV(0x6E, 3);
			writeDbInfoSettingTLVStringUtf(hContact, "Cellular", cPhone, 0x64);
			cPhone = cPhones->getRecordByTLV(0x6E, 4);
			writeDbInfoSettingTLVStringUtf(hContact, "Fax", cPhone, 0x64);
			cPhone = cPhones->getRecordByTLV(0x6E, 5);
			writeDbInfoSettingTLVStringUtf(hContact, "CompanyFax", cPhone, 0x64);

			disposeRecordList(&cPhones);
		}
		else
		{ // Remove old data when phones not available
			delSetting(hContact, "Phone");
			delSetting(hContact, "CompanyPhone");
			delSetting(hContact, "Cellular");
			delSetting(hContact, "Fax");
			delSetting(hContact, "CompanyFax");
		}
	}
	else
	{ // Remove old data when phones not available
		delSetting(hContact, "Phone");
		delSetting(hContact, "CompanyPhone");
		delSetting(hContact, "Cellular");
		delSetting(hContact, "Fax");
		delSetting(hContact, "CompanyFax");
	}
	// Emails
	parseUserInfoRecord(hContact, cDetails->getTLV(0x8C, 1), rEmail, SIZEOF(rEmail), 4);

	writeDbInfoSettingTLVByte(hContact, "Timezone", cDetails, 0x17C);
	// Company
	parseUserInfoRecord(hContact, cDetails->getTLV(0x118, 1), rCompany, SIZEOF(rCompany), 1);
	// Education
	parseUserInfoRecord(hContact, cDetails->getTLV(0x10E, 1), rEducation, SIZEOF(rEducation), 1);

	switch (cDetails->getNumber(0x82, 1))
	{
	case 1: 
		setByte(hContact, "Gender", 'F');
		break;
	case 2:
		setByte(hContact, "Gender", 'M');
		break;
	default:
		delSetting(hContact, "Gender");
	}

	writeDbInfoSettingTLVStringUtf(hContact, "Homepage", cDetails, 0xFA);
	writeDbInfoSettingTLVDate(hContact, "BirthYear", "BirthMonth", "BirthDay", cDetails, 0x1A4);

	writeDbInfoSettingTLVByte(hContact, "Language1", cDetails, 0xAA);
	writeDbInfoSettingTLVByte(hContact, "Language2", cDetails, 0xB4);
	writeDbInfoSettingTLVByte(hContact, "Language3", cDetails, 0xBE);

	writeDbInfoSettingTLVByte(hContact, "MaritalStatus", cDetails, 0x12C);
	// Interests
	parseUserInfoRecord(hContact, cDetails->getTLV(0x122, 1), rInterest, SIZEOF(rInterest), 4);

	writeDbInfoSettingTLVStringUtf(hContact, "About", cDetails, 0x186);

//	if (hContact)
//		writeDbInfoSettingTLVStringUtf(hContact, DBSETTING_STATUS_NOTE, cDetails, 0x226);
//	else
	if (!hContact)
	{ // Owner contact needs special processing, in the database is current status note for the client
		// We just received the last status note set on directory, if it differs call SetStatusNote() to 
		// ensure the directory will be updated (it should be in process anyway)
		char *szClientStatusNote = getSettingStringUtf(hContact, DBSETTING_STATUS_NOTE, NULL);
		char *szDirectoryStatusNote = cDetails->getString(0x226, 1);

		if (strcmpnull(szClientStatusNote, szDirectoryStatusNote))
			SetStatusNote(szClientStatusNote, 1000, TRUE);

		// Release memory
		SAFE_FREE(&szDirectoryStatusNote);
		SAFE_FREE(&szClientStatusNote);
	}

	writeDbInfoSettingTLVByte(hContact, "PrivacyLevel", cDetails, 0x1F9);

	if (!hContact)
	{
		setByte(hContact, "Auth", !cDetails->getByte(0x19A, 1));
		writeDbInfoSettingTLVByte(hContact, "WebAware", cDetails, 0x212);
		writeDbInfoSettingTLVByte(hContact, "AllowSpam", cDetails, 0x1EA);
	}

	writeDbInfoSettingTLVWord(hContact, "InfoCP", cDetails, 0x1C2);

	if (hContact)
	{ // Handle deprecated setting (Age & Birthdate are not separate fields anymore)
		int nAge = calcAgeFromBirthDate(cDetails->getDouble(0x1A4, 1));

		if (nAge)
			setWord(hContact, "Age", nAge);
		else
			delSetting(hContact, "Age");
	}
	else // we do not need to calculate age for owner
		delSetting(hContact, "Age");

	{ // Save user info last update time and privacy token
		double dInfoTime;
		BYTE pbEmptyMetaToken[0x10] = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
		int bHasMetaToken = FALSE;

		// Check if the details arrived with privacy token!
		if ((pTLV = cDetails->getTLV(0x3C, 1)) && pTLV->wLen == 0x10 && memcmp(pTLV->pData, pbEmptyMetaToken, 0x10))
			bHasMetaToken = TRUE;

		// !Important, we need to save the MDir server-item time - it can be newer than the one from the directory
		if ((dInfoTime = getSettingDouble(hContact, DBSETTING_METAINFO_TIME, 0)) > 0)
			setSettingDouble(hContact, DBSETTING_METAINFO_SAVED, dInfoTime);
		else if (bHasMetaToken || !hContact)
			writeDbInfoSettingTLVDouble(hContact, DBSETTING_METAINFO_SAVED, cDetails, 0x1CC);
		else
			setDword(hContact, DBSETTING_METAINFO_SAVED, time(NULL));
	}

	if (wReplySubType == META_DIRECTORY_RESPONSE)
		if (pCookieData->bRequestType == DIRECTORYREQUEST_INFOUSER)
			ProtoBroadcastAck(hContact, ACKTYPE_GETINFO, ACKRESULT_SUCCESS, (HANDLE)1 ,0);

	// Remove user from info update queue. Removing is fast so we always call this
	// even if it is likely that the user is not queued at all.
	if (hContact)
		icq_DequeueUser(getContactUin(hContact));
}