bool CMapiMessage::EnsureHeader(CMapiMessageHeaders::SpecialHeader special, ULONG mapiTag) { if (m_headers.Value(special)) return true; LPSPropValue pVal = CMapiApi::GetMapiProperty(m_lpMsg, mapiTag); bool success = false; if (pVal) { if (PROP_TYPE(pVal->ulPropTag) == PT_STRING8) { if (pVal->Value.lpszA && strlen(pVal->Value.lpszA)) { m_headers.SetValue(special, pVal->Value.lpszA); success = true; } } else if (PROP_TYPE(pVal->ulPropTag) == PT_UNICODE) { if (pVal->Value.lpszW && wcslen(pVal->Value.lpszW)) { m_headers.SetValue(special, NS_ConvertUTF16toUTF8(pVal->Value.lpszW).get()); success = true; } } CMapiApi::MAPIFreeBuffer(pVal); } return success; }
BOOL CMapiApi::GetStringFromProp( LPSPropValue pVal, nsString& val, BOOL delVal) { BOOL bResult = TRUE; if ( pVal && (PROP_TYPE( pVal->ulPropTag) == PT_STRING8)) { CStrToUnicode( (const char *)pVal->Value.lpszA, val); } else if ( pVal && (PROP_TYPE( pVal->ulPropTag) == PT_UNICODE)) { val = (PRUnichar *) pVal->Value.lpszW; } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_NULL)) { val.Truncate(); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_ERROR)) { val.Truncate(); bResult = FALSE; } else { if (pVal) { MAPI_TRACE1( "GetStringFromProp: invalid value, expecting string - %d\n", (int) PROP_TYPE( pVal->ulPropTag)); } else { MAPI_TRACE0( "GetStringFromProp: invalid value, expecting string, got null pointer\n"); } val.Truncate(); bResult = FALSE; } if (pVal && delVal) MAPIFreeBuffer( pVal); return( bResult); }
void CMapiApi::ReportUIDProp( const char *pTag, LPSPropValue pVal) { if ( pVal && (PROP_TYPE( pVal->ulPropTag) == PT_BINARY)) { if (pVal->Value.bin.cb != 16) { MAPI_TRACE1( "%s - INVALID, expecting 16 bytes of binary data for UID\n", pTag); } else { nsIID uid; memcpy( &uid, pVal->Value.bin.lpb, 16); char * pStr = uid.ToString(); if (pStr) { MAPI_TRACE2( "%s %s\n", pTag, (const char *)pStr); NS_Free( pStr); } } } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_NULL)) { MAPI_TRACE1( "%s {NULL}\n", pTag); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_ERROR)) { MAPI_TRACE1( "%s {Error retrieving property}\n", pTag); } else { MAPI_TRACE1( "%s invalid value, expecting binary\n", pTag); } if (pVal) MAPIFreeBuffer( pVal); }
void CMapiApi::ReportLongProp( const char *pTag, LPSPropValue pVal) { if ( pVal && (PROP_TYPE( pVal->ulPropTag) == PT_LONG)) { nsCString num; nsCString num2; num.AppendInt( (PRInt32) pVal->Value.l); num2.AppendInt( (PRInt32) pVal->Value.l, 16); MAPI_TRACE3( "%s %s, 0x%s\n", pTag, num, num2); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_NULL)) { MAPI_TRACE1( "%s {NULL}\n", pTag); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_ERROR)) { MAPI_TRACE1( "%s {Error retrieving property}\n", pTag); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_ERROR)) { MAPI_TRACE1( "%s {Error retrieving property}\n", pTag); } else { MAPI_TRACE1( "%s invalid value, expecting long\n", pTag); } if (pVal) MAPIFreeBuffer( pVal); }
ULONGLONG ComputeSingleFolderSize( _In_ LPMAPIFOLDER lpFolder) { HRESULT hRes = S_OK; LPMAPITABLE lpTable = NULL; LPSRowSet lpsRowSet = NULL; SizedSPropTagArray (1, sProps) = { 1, {PR_MESSAGE_SIZE} }; ULONGLONG ullThisFolderSize = 0; // Look at each item in this folder WC_MAPI(lpFolder->GetContentsTable(0, &lpTable)); if (lpTable) { WC_MAPI(HrQueryAllRows(lpTable, (LPSPropTagArray)&sProps, NULL, NULL, 0, &lpsRowSet)); if (lpsRowSet) { for(ULONG i = 0; i < lpsRowSet->cRows; i++) { if (PROP_TYPE(lpsRowSet->aRow[i].lpProps[0].ulPropTag) != PT_ERROR) ullThisFolderSize += lpsRowSet->aRow[i].lpProps[0].Value.l; } MAPIFreeBuffer(lpsRowSet); lpsRowSet = NULL; } lpTable->Release(); lpTable = NULL; } DebugPrint(DBGGeneric, "Content size = %I64u\n", ullThisFolderSize); // printf("Content size = %I64d\n", ullThisFolderSize); WC_MAPI(lpFolder->GetContentsTable(MAPI_ASSOCIATED, &lpTable)); if (lpTable) { WC_MAPI(HrQueryAllRows(lpTable, (LPSPropTagArray)&sProps, NULL, NULL, 0, &lpsRowSet)); if (lpsRowSet) { for(ULONG i = 0; i < lpsRowSet->cRows; i++) { if (PROP_TYPE(lpsRowSet->aRow[i].lpProps[0].ulPropTag) != PT_ERROR) ullThisFolderSize += lpsRowSet->aRow[i].lpProps[0].Value.l; } MAPIFreeBuffer(lpsRowSet); lpsRowSet = NULL; } lpTable->Release(); lpTable = NULL; } DebugPrint(DBGGeneric, "Total size = %I64u\n", ullThisFolderSize); // printf("Total size = %I64d\n", ullThisFolderSize); return ullThisFolderSize; } // ComputeSingleFolderSize
LPSPropValue CMapiApi::GetMapiProperty( LPMAPIPROP pProp, ULONG tag) { if (!pProp) return( NULL); int sz = CbNewSPropTagArray( 1); SPropTagArray *pTag = (SPropTagArray *) new char[sz]; pTag->cValues = 1; pTag->aulPropTag[0] = tag; LPSPropValue lpProp = NULL; ULONG cValues = 0; HRESULT hr = pProp->GetProps( pTag, 0, &cValues, &lpProp); delete [] pTag; if (HR_FAILED( hr) || (cValues != 1)) { if (lpProp) MAPIFreeBuffer( lpProp); return( NULL); } else { if (PROP_TYPE( lpProp->ulPropTag) == PT_ERROR) { if (lpProp->Value.l == MAPI_E_NOT_FOUND) { MAPIFreeBuffer( lpProp); lpProp = NULL; } } } return( lpProp); }
BOOL CMapiApi::IsLargeProperty( LPSPropValue pVal) { if ((PROP_TYPE( pVal->ulPropTag) == PT_ERROR) && (pVal->Value.l == E_OUTOFMEMORY)) { return( TRUE); } return( FALSE); }
void CMapiMessage::GetDownloadState() { // See http://support.microsoft.com/kb/912239 HRESULT hRes = S_OK; ULONG ulVal = 0; LPSPropValue lpPropVal = NULL; LPSPropTagArray lpNamedPropTag = NULL; MAPINAMEID NamedID = {0}; LPMAPINAMEID lpNamedID = NULL; NamedID.lpguid = (LPGUID) &PSETID_Common; NamedID.ulKind = MNID_ID; NamedID.Kind.lID = dispidHeaderItem; lpNamedID = &NamedID; hRes = m_lpMsg->GetIDsFromNames(1, &lpNamedID, NULL, &lpNamedPropTag); if (lpNamedPropTag && 1 == lpNamedPropTag->cValues) { lpNamedPropTag->aulPropTag[0] = CHANGE_PROP_TYPE(lpNamedPropTag->aulPropTag[0], PT_LONG); //Get the value of the property. hRes = m_lpMsg->GetProps(lpNamedPropTag, 0, &ulVal, &lpPropVal); if (lpPropVal && 1 == ulVal && PT_LONG == PROP_TYPE(lpPropVal->ulPropTag) && lpPropVal->Value.ul) m_dldStateHeadersOnly = true; } CMapiApi::MAPIFreeBuffer(lpPropVal); CMapiApi::MAPIFreeBuffer(lpNamedPropTag); }
LPSPropValue Workshare::Mail::Mapi::GetMessageTag(LPMESSAGE lpMessage, const std::tstring& sTag) { LPSPropValue pPropVal = 0; IMAPIPropPtr spMapiProp; HRESULT hr = lpMessage->QueryInterface(IID_IMAPIProp, (void**) &spMapiProp); if(SUCCEEDED(hr)) { LPMAPINAMEID pTagName = 0; hr = MAPIAllocateBuffer(sizeof(MAPINAMEID), (LPVOID*)&pTagName); if(SUCCEEDED(hr)) { pTagName[0].lpguid = (LPGUID)&PS_PUBLIC_STRINGS; pTagName[0].ulKind = MNID_STRING; _bstr_t bsTag(sTag.c_str()); pTagName[0].Kind.lpwstrName = bsTag; LPSPropTagArray pPropTag = 0; hr = spMapiProp->GetIDsFromNames(1, &pTagName, 0, &pPropTag); if (!FAILED(hr)) { if(1 == pPropTag->cValues && PT_ERROR != PROP_TYPE(pPropTag->aulPropTag[0])) { ULONG ulCount = 0; spMapiProp->GetProps(pPropTag, 0, &ulCount, &pPropVal); } MAPIFreeBuffer(pPropTag); } MAPIFreeBuffer(pTagName); } } return pPropVal; }
int CMapiMessage::CountAttachments( void) { m_attachNums.Clear(); LPSPropValue pVal = CMapiApi::GetMapiProperty( m_lpMsg, PR_HASATTACH); BOOL has = TRUE; if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_BOOLEAN)) { has = (pVal->Value.b != 0); } if (pVal) CMapiApi::MAPIFreeBuffer( pVal); if (has) { // Get the attachment table? HRESULT hr; LPMAPITABLE pTable = NULL; hr = m_lpMsg->GetAttachmentTable( 0, &pTable); if (FAILED( hr)) return( 0); m_pAttachTable = pTable; IterateAttachTable(); } return m_attachNums.Length(); }
HRESULT MailboxDataCollector::CollectData(LPMAPITABLE lpStoreTable) { HRESULT hr = hrSuccess; SRowSetPtr ptrRows; enum {IDX_ENTRYID, IDX_MAILBOX_OWNER_ENTRYID, IDX_STORE_ENTRYIDS, IDX_ITEM_ENTRYIDS, IDX_MAX}; while (true) { hr = lpStoreTable->QueryRows(50, 0, &ptrRows); if (hr != hrSuccess) goto exit; if (ptrRows.size() == 0) break; for (SRowSetPtr::size_type i = 0; i < ptrRows.size(); ++i) { std::pair<ArchiveStateCollector::ArchiveInfoMap::iterator, bool> res; bool bComplete = true; abentryid_t userId; for (unsigned j = 0; bComplete && j < IDX_MAX; ++j) { if (PROP_TYPE(ptrRows[i].lpProps[j].ulPropTag) == PT_ERROR) { m_lpLogger->Log(EC_LOGLEVEL_WARNING, "Got uncomplete row, row %u, column %u contains error 0x%08x", i, j, ptrRows[i].lpProps[j].Value.err); bComplete = false; } } if (!bComplete) continue; if (ptrRows[i].lpProps[IDX_STORE_ENTRYIDS].Value.MVbin.cValues != ptrRows[i].lpProps[IDX_ITEM_ENTRYIDS].Value.MVbin.cValues) { m_lpLogger->Log(EC_LOGLEVEL_DEBUG, "Mismatch in archive prop count, %u vs. %u", ptrRows[i].lpProps[IDX_STORE_ENTRYIDS].Value.MVbin.cValues, ptrRows[i].lpProps[IDX_ITEM_ENTRYIDS].Value.MVbin.cValues); continue; } userId.assign(ptrRows[i].lpProps[IDX_MAILBOX_OWNER_ENTRYID].Value.bin); res = m_mapArchiveInfo.insert(std::make_pair(userId, ArchiveStateCollector::ArchiveInfo())); if (res.second == true) m_lpLogger->Log(EC_LOGLEVEL_DEBUG, "Inserting row for user id %s", userId.tostring().c_str()); else m_lpLogger->Log(EC_LOGLEVEL_DEBUG, "Updating row for user '" TSTRING_PRINTF "'", res.first->second.userName.c_str()); // Assign entryid res.first->second.storeId.assign(ptrRows[i].lpProps[IDX_ENTRYID].Value.bin); // Assign archives m_lpLogger->Log(EC_LOGLEVEL_DEBUG, "Adding %u archive(s)", ptrRows[i].lpProps[IDX_STORE_ENTRYIDS].Value.MVbin.cValues); for (ULONG j = 0; j < ptrRows[i].lpProps[IDX_STORE_ENTRYIDS].Value.MVbin.cValues; ++j) { SObjectEntry objEntry; objEntry.sStoreEntryId.assign(entryid_t(ptrRows[i].lpProps[IDX_STORE_ENTRYIDS].Value.MVbin.lpbin[j])); objEntry.sItemEntryId.assign(entryid_t(ptrRows[i].lpProps[IDX_ITEM_ENTRYIDS].Value.MVbin.lpbin[j])); res.first->second.lstArchives.push_back(objEntry); } } } exit: return hr; }
void CMapiApi::ReportStringProp( const char *pTag, LPSPropValue pVal) { if ( pVal && (PROP_TYPE( pVal->ulPropTag) == PT_TSTRING)) { nsCString val((LPCTSTR) (pVal->Value.LPSZ)); MAPI_TRACE2( "%s %s\n", pTag, (const char *)val); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_NULL)) { MAPI_TRACE1( "%s {NULL}\n", pTag); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_ERROR)) { MAPI_TRACE1( "%s {Error retrieving property}\n", pTag); } else { MAPI_TRACE1( "%s invalid value, expecting string\n", pTag); } if (pVal) MAPIFreeBuffer( pVal); }
// If the value is a string, get it... void CWAB::GetValueString( LPSPropValue pVal, nsString& val) { val.Truncate(); if (!pVal) return; switch( PROP_TYPE( pVal->ulPropTag)) { case PT_STRING8: { CStrToUnicode( (const char *) (pVal->Value.lpszA), val); } break; case PT_UNICODE: val = (PRUnichar *) (pVal->Value.lpszW); break; case PT_MV_STRING8: { nsString tmp; ULONG j; for(j = 0; j < pVal->Value.MVszA.cValues; j++) { CStrToUnicode( (const char *) (pVal->Value.MVszA.lppszA[j]), tmp); val += tmp; val.Append(NS_ConvertASCIItoUTF16(TR_OUTPUT_EOL)); } } break; case PT_MV_UNICODE: { ULONG j; for(j = 0; j < pVal->Value.MVszW.cValues; j++) { val += (PRUnichar *) (pVal->Value.MVszW.lppszW[j]); val.Append(NS_ConvertASCIItoUTF16(TR_OUTPUT_EOL)); } } break; case PT_I2: case PT_LONG: case PT_R4: case PT_DOUBLE: case PT_BOOLEAN: { /* TCHAR sz[256]; wsprintf(sz,"%d", pVal->Value.l); val = sz; */ } break; case PT_BINARY: break; default: break; } val.Trim( kWhitespace, PR_TRUE, PR_TRUE); }
void CWAB::GetValueTime(LPSPropValue pVal, PRTime& val) { if (!pVal) return; if (PROP_TYPE(pVal->ulPropTag) != PT_SYSTIME) return; nsOE5File::FileTimeToPRTime(&pVal->Value.ft, &val); }
LONG CMapiApi::GetLongFromProp( LPSPropValue pVal, BOOL delVal) { LONG val = 0; if ( pVal && (PROP_TYPE( pVal->ulPropTag) == PT_LONG)) { val = pVal->Value.l; } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_NULL)) { val = 0; } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_ERROR)) { val = 0; MAPI_TRACE0( "GetLongFromProp: Error retrieving property\n"); } else { MAPI_TRACE0( "GetLongFromProp: invalid value, expecting long\n"); } if (pVal && delVal) MAPIFreeBuffer( pVal); return( val); }
BOOL CMapiMessage::FetchBody( void) { m_bodyIsHtml = FALSE; m_body.Truncate(); // Is it html? LPSPropValue pVal = CMapiApi::GetMapiProperty( m_lpMsg, 0x1013001e); if (pVal && CMapiApi::IsLargeProperty( pVal)) CMapiApi::GetLargeStringProperty( m_lpMsg, 0x1013001e, m_body); else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_TSTRING) && (pVal->Value.LPSZ) && (*(pVal->Value.LPSZ))) m_body = pVal->Value.LPSZ; // kind-hearted Outlook will give us html even for a plain text message. But it will include // a comment saying it did the conversion. We'll use this as a hack to really use // the plain text part. if (!m_body.IsEmpty() && m_body.Find("<!-- Converted from text/plain format -->") == kNotFound) m_bodyIsHtml = TRUE; else { pVal = CMapiApi::GetMapiProperty( m_lpMsg, PR_BODY); if (pVal) { if (pVal && CMapiApi::IsLargeProperty( pVal)) { CMapiApi::GetLargeStringProperty( m_lpMsg, PR_BODY, m_body); } else { if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_TSTRING) && (pVal->Value.LPSZ) && (*(pVal->Value.LPSZ))) { m_body = pVal->Value.LPSZ; } } } } if (pVal) CMapiApi::MAPIFreeBuffer( pVal); MAPI_DUMP_STRING(m_body.get()); MAPI_TRACE0("\r\n"); return( TRUE); }
// Headers - fetch will get PR_TRANSPORT_MESSAGE_HEADERS // or if they do not exist will build a header from // PR_DISPLAY_TO, _CC, _BCC // PR_SUBJECT // PR_MESSAGE_RECIPIENTS // and PR_CREATION_TIME if needed? bool CMapiMessage::FetchHeaders(void) { ULONG tag = PR_TRANSPORT_MESSAGE_HEADERS_A; LPSPropValue pVal = CMapiApi::GetMapiProperty(m_lpMsg, tag); if (!pVal) pVal = CMapiApi::GetMapiProperty(m_lpMsg, tag = PR_TRANSPORT_MESSAGE_HEADERS_W); if (pVal) { if (CMapiApi::IsLargeProperty(pVal)) { nsCString headers; CMapiApi::GetLargeStringProperty(m_lpMsg, tag, headers); m_headers.Assign(headers.get()); } else if ((PROP_TYPE(pVal->ulPropTag) == PT_STRING8) && (pVal->Value.lpszA) && (*(pVal->Value.lpszA))) m_headers.Assign(pVal->Value.lpszA); else if ((PROP_TYPE(pVal->ulPropTag) == PT_UNICODE) && (pVal->Value.lpszW) && (*(pVal->Value.lpszW))) { nsCString headers; LossyCopyUTF16toASCII(nsDependentString(pVal->Value.lpszW), headers); m_headers.Assign(headers.get()); } CMapiApi::MAPIFreeBuffer(pVal); } EnsureDate(); if (!EnsureHeader(CMapiMessageHeaders::hdrFrom, PR_SENDER_NAME_W)) EnsureHeader(CMapiMessageHeaders::hdrFrom, PR_SENDER_EMAIL_ADDRESS_W); EnsureHeader(CMapiMessageHeaders::hdrSubject, PR_SUBJECT_W); EnsureHeader(CMapiMessageHeaders::hdrTo, PR_DISPLAY_TO_W); EnsureHeader(CMapiMessageHeaders::hdrCc, PR_DISPLAY_CC_W); EnsureHeader(CMapiMessageHeaders::hdrBcc, PR_DISPLAY_BCC_W); ProcessContentType(); return !m_headers.IsEmpty(); }
HRESULT ArchiverSession::GetUserInfo(const abentryid_t &sEntryId, tstring *lpstrUser, tstring *lpstrFullname) { HRESULT hr = hrSuccess; ULONG ulType = 0; MAPIPropPtr ptrUser; ULONG cUserProps = 0; SPropArrayPtr ptrUserProps; SizedSPropTagArray(2, sptaUserProps) = {2, {PR_ACCOUNT, PR_DISPLAY_NAME}}; enum {IDX_ACCOUNT, IDX_DISPLAY_NAME}; hr = m_ptrSession->OpenEntry(sEntryId.size(), sEntryId, NULL, MAPI_DEFERRED_ERRORS, &ulType, &ptrUser); if (hr != hrSuccess) goto exit; hr = ptrUser->GetProps((LPSPropTagArray)&sptaUserProps, 0, &cUserProps, &ptrUserProps); if (FAILED(hr)) goto exit; hr = hrSuccess; if (lpstrUser) { if (PROP_TYPE(ptrUserProps[IDX_ACCOUNT].ulPropTag) != PT_ERROR) lpstrUser->assign(ptrUserProps[IDX_ACCOUNT].Value.LPSZ); else lpstrUser->assign(_T("<Unknown>")); } if (lpstrFullname) { if (PROP_TYPE(ptrUserProps[IDX_DISPLAY_NAME].ulPropTag) != PT_ERROR) lpstrFullname->assign(ptrUserProps[IDX_DISPLAY_NAME].Value.LPSZ); else lpstrFullname->assign(_T("<Unknown>")); } exit: return hr; }
//$--HrMAPISetPropString--------------------------------------------------------- // Set a string property. // ----------------------------------------------------------------------------- HRESULT HrMAPISetPropString( // RETURNS: return code IN LPMAPIPROP lpObj, // pointer to object IN ULONG ulPropTag, // property tag IN LPVOID lpvProp) // pointer to property { HRESULT hr = NOERROR; HRESULT hrT = NOERROR; ULONG cValues = 1; SPropValue PropValue = {0}; DEBUGPUBLIC("HrMAPISetPropString()\n"); hr = CHK_HrMAPISetPropString( lpObj, ulPropTag, lpvProp); if(FAILED(hr)) RETURN(hr); // Initialize SPropValue structure memset(&PropValue, 0, sizeof(PropValue)); PropValue.ulPropTag = ulPropTag; if(PROP_TYPE(ulPropTag) == PT_STRING8) { PropValue.Value.lpszA = (LPSTR)lpvProp; } else { PropValue.Value.lpszW = (LPWSTR)lpvProp; } hrT = MAPICALL(lpObj)->SetProps( /*lpObj,*/ cValues, &PropValue, NULL); if(FAILED(hrT)) { hr = HR_LOG(E_FAIL); } RETURN(hr); }
void CMapiApi::ListPropertyValue( LPSPropValue pVal, nsCString& s) { nsCString strVal; char nBuff[64]; nsCString t; s += "value: "; switch (PROP_TYPE( pVal->ulPropTag)) { case PT_STRING8: GetStringFromProp( pVal, strVal, FALSE); if (strVal.Length() > 60) { strVal.Left( t, 60); strVal = t; strVal += "..."; } ReplaceEolChars( strVal); s += strVal; break; case PT_LONG: s.AppendInt( (PRInt32) pVal->Value.l); s += ", 0x"; s.AppendInt( (PRInt32) pVal->Value.l, 16); s += nBuff; break; case PT_BOOLEAN: if (pVal->Value.b) s += "True"; else s += "False"; break; case PT_NULL: s += "--NULL--"; break; case PT_SYSTIME: { /* COleDateTime tm( pVal->Value.ft); s += tm.Format(); */ s += "-- Figure out how to format time in mozilla, PT_SYSTIME --"; } break; default: s += "?"; } }
BOOL CMapiMessage::FetchHeaders( void) { LPSPropValue pVal = CMapiApi::GetMapiProperty( m_lpMsg, PR_TRANSPORT_MESSAGE_HEADERS); if (pVal && CMapiApi::IsLargeProperty( pVal)) { m_headers.Truncate(); CMapiApi::GetLargeStringProperty( m_lpMsg, PR_TRANSPORT_MESSAGE_HEADERS, m_headers); } else if (pVal && (PROP_TYPE( pVal->ulPropTag) == PT_TSTRING) && (pVal->Value.LPSZ) && (*(pVal->Value.LPSZ))) { m_headers = pVal->Value.LPSZ; } else { // Need to build the headers from the other stuff m_headers.Truncate(); BuildHeaders(); } if (pVal) CMapiApi::MAPIFreeBuffer( pVal); m_fromLine.Truncate(); if (NeedsFromLine()) { BuildFromLine(); } if (!m_fromLine.IsEmpty()) { MAPI_DUMP_STRING(m_fromLine.get()); } MAPI_DUMP_STRING(m_headers.get()); MAPI_TRACE0("\r\n"); ProcessHeaders(); if (!m_headers.IsEmpty()) { if (!m_bHasSubject) AddSubject( m_headers); if (!m_bHasFrom) AddFrom( m_headers); if (!m_bHasDate) AddDate( m_headers); m_headers.Trim( kWhitespace, PR_FALSE, PR_TRUE); m_headers += "\x0D\x0A"; } return( !m_headers.IsEmpty()); }
void CMapiApi::GetPropTagName( ULONG tag, nsCString& s) { char numStr[256]; PR_snprintf( numStr, 256, "0x%lx, %ld", tag, tag); s = numStr; switch( tag) { #include "mapitagstrs.cpp" } s += ", data: "; switch( PROP_TYPE( tag)) { case PT_UNSPECIFIED: s += "PT_UNSPECIFIED"; break; case PT_NULL: s += "PT_NULL"; break; case PT_I2: s += "PT_I2"; break; case PT_LONG: s += "PT_LONG"; break; case PT_R4: s += "PT_R4"; break; case PT_DOUBLE: s += "PT_DOUBLE"; break; case PT_CURRENCY: s += "PT_CURRENCY"; break; case PT_APPTIME: s += "PT_APPTIME"; break; case PT_ERROR: s += "PT_ERROR"; break; case PT_BOOLEAN: s += "PT_BOOLEAN"; break; case PT_OBJECT: s += "PT_OBJECT"; break; case PT_I8: s += "PT_I8"; break; case PT_STRING8: s += "PT_STRING8"; break; case PT_UNICODE: s += "PT_UNICODE"; break; case PT_SYSTIME: s += "PT_SYSTIME"; break; case PT_CLSID: s += "PT_CLSID"; break; case PT_BINARY: s += "PT_BINARY"; break; case PT_MV_I2: s += "PT_MV_I2"; break; case PT_MV_LONG: s += "PT_MV_LONG"; break; case PT_MV_R4: s += "PT_MV_R4"; break; case PT_MV_DOUBLE: s += "PT_MV_DOUBLE"; break; case PT_MV_CURRENCY: s += "PT_MV_CURRENCY"; break; case PT_MV_APPTIME: s += "PT_MV_APPTIME"; break; case PT_MV_SYSTIME: s += "PT_MV_SYSTIME"; break; case PT_MV_STRING8: s += "PT_MV_STRING8"; break; case PT_MV_BINARY: s += "PT_MV_BINARY"; break; case PT_MV_UNICODE: s += "PT_MV_UNICODE"; break; case PT_MV_CLSID: s += "PT_MV_CLSID"; break; case PT_MV_I8: s += "PT_MV_I8"; break; default: s += "Unknown"; } }
void Workshare::Mail::Mapi::RemoveMessageTag(LPMESSAGE lpMessage, const std::tstring& sTag) { IMAPIPropPtr spMapiProp = lpMessage; if(spMapiProp == 0) throw Workshare::Exception(_T("Failed to extract the IID_IMAPIProp interface from lpMessage")); LPMAPINAMEID pTagName = 0; HRESULT hr = MAPIAllocateBuffer(sizeof(MAPINAMEID), (LPVOID*)&pTagName); if(FAILED(hr)) throw MapiException(hr, _T("Failed to allocate MAPI memory for the tag name")); pTagName[0].lpguid = (LPGUID)&PS_PUBLIC_STRINGS; pTagName[0].ulKind = MNID_STRING; _bstr_t bsTag(sTag.c_str()); pTagName[0].Kind.lpwstrName = bsTag; LPSPropTagArray pPropTag = 0; hr = spMapiProp->GetIDsFromNames(1, &pTagName, 0, &pPropTag); if(FAILED(hr)) { MAPIFreeBuffer(pTagName); std::tostringstream error; error << _T("Failed to determine the ID from the tag name \"") << sTag.c_str() << _T("\"") << std::ends; throw MapiException(hr, error.str().c_str()); } if(1 == pPropTag->cValues && PT_ERROR != PROP_TYPE(pPropTag->aulPropTag[0])) { spMapiProp->DeleteProps(pPropTag, 0); } else { std::tostringstream error; error << _T("Failed to delete the message tag \"") << sTag.c_str() << _T("\"") << std::ends; LOG_WS_INFO(error.str().c_str()); } MAPIFreeBuffer(pPropTag); MAPIFreeBuffer(pTagName); }
// This method must be called AFTER the retrieval of the body, // since the decision if an attachment is embedded or not is made // based on the body type and contents void CMapiMessage::ProcessAttachments() { LPSPropValue pVal = CMapiApi::GetMapiProperty(m_lpMsg, PR_HASATTACH); bool hasAttach = true; if (pVal) { if (PROP_TYPE(pVal->ulPropTag) == PT_BOOLEAN) hasAttach = (pVal->Value.b != 0); CMapiApi::MAPIFreeBuffer(pVal); } if (!hasAttach) return; // Get the attachment table? LPMAPITABLE pTable = NULL; HRESULT hr = m_lpMsg->GetAttachmentTable(0, &pTable); if (FAILED(hr) || !pTable) return; IterateAttachTable(pTable); pTable->Release(); }
// If the value is a string, get it... BOOL CMapiApi::GetEntryIdFromProp( LPSPropValue pVal, ULONG& cbEntryId, LPENTRYID& lpEntryId, BOOL delVal) { if (!pVal) return( FALSE); BOOL bResult = TRUE; switch( PROP_TYPE( pVal->ulPropTag)) { case PT_BINARY: cbEntryId = pVal->Value.bin.cb; MAPIAllocateBuffer( cbEntryId, (LPVOID *) &lpEntryId); memcpy( lpEntryId, pVal->Value.bin.lpb, cbEntryId); break; default: MAPI_TRACE0( "EntryId not in BINARY prop value\n"); bResult = FALSE; break; } if (pVal && delVal) MAPIFreeBuffer( pVal); return( bResult); }
HRESULT MAPIAppointment::SetOrganizerAndAttendees() { Zimbra::Util::ScopedInterface<IMAPITable> pRecipTable; HRESULT hr = 0; hr = m_pMessage->GetRecipientTable(fMapiUnicode, pRecipTable.getptr()); if (FAILED(hr)) { return hr; } typedef enum _AttendeePropTagIdx { AT_ADDRTYPE, AT_ENTRYID, AT_DISPLAY_NAME, AT_SMTP_ADDR, AT_RECIPIENT_FLAGS, AT_RECIPIENT_TYPE, AT_RECIPIENT_TRACKSTATUS,AT_EMAIL_ADDRESS, AT_NPROPS } AttendeePropTagIdx; SizedSPropTagArray(AT_NPROPS, reciptags) = { AT_NPROPS, { PR_ADDRTYPE, PR_ENTRYID, PR_DISPLAY_NAME_W, PR_SMTP_ADDRESS_W, PR_RECIPIENT_FLAGS, PR_RECIPIENT_TYPE, PR_RECIPIENT_TRACKSTATUS,PR_EMAIL_ADDRESS } }; ULONG ulRows = 0; Zimbra::Util::ScopedRowSet pRecipRows; hr = pRecipTable->SetColumns((LPSPropTagArray) & reciptags, 0); if (FAILED(hr)) { //LOG_ERROR(_T("could not get the recipient table, hr: %x"), hr); return hr; } hr = pRecipTable->GetRowCount(0, &ulRows); if (FAILED(hr)) { //LOG_ERROR(_T("could not get the recipient table row count, hr: %x"), hr); return hr; } hr = pRecipTable->QueryRows(ulRows, 0, pRecipRows.getptr()); if (FAILED(hr)) { //LOG_ERROR(_T("Failed to query table rows. hr: %x"), hr); return hr; } if (pRecipRows != NULL) { for (ULONG iRow = 0; iRow < pRecipRows->cRows; iRow++) { if (pRecipRows->aRow[iRow].lpProps[AT_RECIPIENT_FLAGS].ulPropTag == reciptags.aulPropTag[AT_RECIPIENT_FLAGS]) { if (pRecipRows->aRow[iRow].lpProps[AT_RECIPIENT_FLAGS].Value.l == 3) { if (PROP_TYPE(pRecipRows->aRow[iRow].lpProps[AT_DISPLAY_NAME].ulPropTag) != PT_ERROR) { m_pOrganizerName = pRecipRows->aRow[iRow].lpProps[AT_DISPLAY_NAME].Value.lpszW; } if (PROP_TYPE(pRecipRows->aRow[iRow].lpProps[AT_SMTP_ADDR].ulPropTag) != PT_ERROR) { m_pOrganizerAddr = pRecipRows->aRow[iRow].lpProps[AT_SMTP_ADDR].Value.lpszW; } if((lstrcmpiW(m_pOrganizerAddr.c_str(),L"") == 0) ||(m_pOrganizerName ==L"")) { Attendee* pAttendee = new Attendee(); dlogi("Going to Update organizer from EID..."); if(UpdateAttendeeFromEntryId(*pAttendee,pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].Value.bin) !=S_OK) { dlogi("Going to update organizer from AD"); RECIP_INFO tempRecip; tempRecip.pAddrType = NULL; tempRecip.pEmailAddr = NULL; tempRecip.cbEid = 0; tempRecip.pEid = NULL; tempRecip.pAddrType = pRecipRows->aRow[iRow].lpProps[AT_ADDRTYPE].Value.lpszW; tempRecip.pEmailAddr = pRecipRows->aRow[iRow].lpProps[AT_EMAIL_ADDRESS].Value.lpszW; if (pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].ulPropTag != PT_ERROR) { tempRecip.cbEid = pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].Value.bin.cb; tempRecip.pEid = (LPENTRYID)pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].Value .bin.lpb; } std::wstring wstrEmailAddress; try { Zimbra::MAPI::Util::GetSMTPFromAD(*m_session, tempRecip,L"" , L"",wstrEmailAddress); } catch(...) { dlogw("mapiappointment::exception from MAPi::util::GetSMTPFromAD "); } pAttendee->addr = wstrEmailAddress; dlogi("Email address(AD):",wstrEmailAddress); dlogi("AD update end."); } dlogi("EID update end."); if(m_pOrganizerAddr==L"") m_pOrganizerAddr = pAttendee->addr; if(m_pOrganizerName==L"") m_pOrganizerName = pAttendee->nam; } dlogi("OrganizerAddr: ",m_pOrganizerAddr, " OrganizerName: ",m_pOrganizerName); } else { if (!(RECIP_FLAG_EXCEP_DELETED & pRecipRows->aRow[iRow].lpProps[AT_RECIPIENT_FLAGS].Value.l)) // make sure attendee wasn't deleted { Attendee* pAttendee = new Attendee(); // delete done in CMapiAccessWrap::GetData after we allocate dict string for ZimbraAPI if (PROP_TYPE(pRecipRows->aRow[iRow].lpProps[AT_DISPLAY_NAME].ulPropTag) != PT_ERROR) pAttendee->nam = pRecipRows->aRow[iRow].lpProps[AT_DISPLAY_NAME].Value.lpszW; if (PROP_TYPE(pRecipRows->aRow[iRow].lpProps[AT_SMTP_ADDR].ulPropTag) != PT_ERROR) pAttendee->addr = pRecipRows->aRow[iRow].lpProps[AT_SMTP_ADDR].Value.lpszW; wstring attaddress = pAttendee->addr; if(lstrcmpiW(attaddress.c_str(),L"") == 0) { if (((pAttendee->nam==L"") || (pAttendee->addr==L"")) && (PROP_TYPE(pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].ulPropTag) != PT_ERROR)) { dlogi("Going to Update attendee from EID..."); if(UpdateAttendeeFromEntryId(*pAttendee,pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].Value.bin)!=S_OK) { dlogi("Going to update attendee from AD"); RECIP_INFO tempRecip; tempRecip.pAddrType = NULL; tempRecip.pEmailAddr = NULL; tempRecip.cbEid = 0; tempRecip.pEid = NULL; tempRecip.pAddrType = pRecipRows->aRow[iRow].lpProps[AT_ADDRTYPE].Value.lpszW; tempRecip.pEmailAddr = pRecipRows->aRow[iRow].lpProps[AT_EMAIL_ADDRESS].Value.lpszW; if (pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].ulPropTag != PT_ERROR) { tempRecip.cbEid = pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].Value.bin.cb; tempRecip.pEid = (LPENTRYID)pRecipRows->aRow[iRow].lpProps[AT_ENTRYID].Value .bin.lpb; } std::wstring wstrEmailAddress; try { Zimbra::MAPI::Util::GetSMTPFromAD(*m_session, tempRecip,L"" , L"",wstrEmailAddress); } catch(...) { dlogw(" Mapiappoinemtn::Exception in MAPI::Util::GetSMTPFromAD"); } pAttendee->addr = wstrEmailAddress; dlogi("Email address(AD):",wstrEmailAddress); dlogi("AD update end."); } dlogi("EID update end."); } } dlogi("AttendeeAddr: ",pAttendee->addr," AttendeeName :",pAttendee->nam); if (PROP_TYPE(pRecipRows->aRow[iRow].lpProps[AT_RECIPIENT_TYPE].ulPropTag) != PT_ERROR) pAttendee->role = ConvertValueToRole(pRecipRows->aRow[iRow].lpProps[AT_RECIPIENT_TYPE].Value.l); if (PROP_TYPE(pRecipRows->aRow[iRow].lpProps[AT_RECIPIENT_TRACKSTATUS].ulPropTag) != PT_ERROR) pAttendee->partstat = ConvertValueToPartStat(pRecipRows->aRow[iRow].lpProps[AT_RECIPIENT_TRACKSTATUS].Value.l); m_vAttendees.push_back(pAttendee); } } } } } return hr; }
PyObject *PyMAPIObject_FromSPropValue(SPropValue *pv) { PyObject *val; ULONG i; switch (PROP_TYPE(pv->ulPropTag)) { case PT_I2: // case PT_SHORT: val = PyInt_FromLong(pv->Value.i); break; case PT_I4: // case PT_LONG: val = PyInt_FromLong(pv->Value.l); break; case PT_R4: // case PT_FLOAT: val = PyFloat_FromDouble(pv->Value.flt); break; case PT_R8: // case PT_DOUBLE: val = PyFloat_FromDouble(pv->Value.dbl); break; case PT_BOOLEAN: val = pv->Value.b ? Py_True : Py_False; Py_INCREF(val); break; /* case PT_CURRENCY: pv->Value.cur?? break; */ case PT_APPTIME : val = PyWinObject_FromDATE(pv->Value.at); break; case PT_SYSTIME: val = PyWinObject_FromFILETIME(pv->Value.ft); break; case PT_STRING8: val = PyString_FromString(pv->Value.lpszA); break; case PT_UNICODE: val = PyWinObject_FromWCHAR(pv->Value.lpszW); break; case PT_BINARY: val = PyString_FromStringAndSize((char *)pv->Value.bin.lpb, pv->Value.bin.cb); break; case PT_CLSID: val = PyWinObject_FromIID(*pv->Value.lpguid); break; case PT_I8: // case PT_LONGLONG: val = PyWinObject_FromLARGE_INTEGER(pv->Value.li); break; case PT_ERROR: val = PyInt_FromLong(pv->Value.err); break; case PT_NULL: val = Py_None; Py_INCREF(Py_None); break; case PT_MV_I2: val = PyTuple_New(pv->Value.MVi.cValues); if (val) { for (i=0; i<pv->Value.MVi.cValues; i++) PyTuple_SET_ITEM(val, i, PyInt_FromLong(pv->Value.MVi.lpi[i])); } break; case PT_MV_LONG: val = PyTuple_New(pv->Value.MVi.cValues); if (val) { for (i=0; i<pv->Value.MVl.cValues; i++) PyTuple_SET_ITEM(val, i, PyInt_FromLong(pv->Value.MVl.lpl[i])); } break; case PT_MV_R4: val = PyTuple_New(pv->Value.MVflt.cValues); if (val) { for (i=0; i<pv->Value.MVflt.cValues; i++) PyTuple_SET_ITEM(val, i, PyFloat_FromDouble(pv->Value.MVflt.lpflt[i])); } break; case PT_MV_DOUBLE : val = PyTuple_New(pv->Value.MVdbl.cValues); if (val) { for (i=0; i<pv->Value.MVdbl.cValues; i++) PyTuple_SET_ITEM(val, i, PyFloat_FromDouble(pv->Value.MVdbl.lpdbl[i])); } break; /* case PT_MV_CURRENCY: MVcur SCurrencyArray */ case PT_MV_APPTIME : val = PyTuple_New(pv->Value.MVat.cValues); if (val) { for (i=0; i<pv->Value.MVat.cValues; i++) PyTuple_SET_ITEM(val, i, PyWinObject_FromDATE(pv->Value.MVat.lpat[i])); } break; case PT_MV_SYSTIME: val = PyTuple_New(pv->Value.MVft.cValues); if (val) { for (i=0; i<pv->Value.MVft.cValues; i++) PyTuple_SET_ITEM(val, i, PyWinObject_FromFILETIME(pv->Value.MVft.lpft[i])); } break; case PT_MV_BINARY: val = PyTuple_New(pv->Value.MVbin.cValues); if (val) { for (i=0; i<pv->Value.MVbin.cValues; i++) PyTuple_SET_ITEM(val, i, PyString_FromStringAndSize((char *)pv->Value.MVbin.lpbin[i].lpb, pv->Value.MVbin.lpbin[i].cb)); } break; case PT_MV_STRING8: val = PyTuple_New(pv->Value.MVszA.cValues); if (val) { for (i=0; i<pv->Value.MVszA.cValues; i++) PyTuple_SET_ITEM(val, i, PyString_FromString(pv->Value.MVszA.lppszA[i])); } break; case PT_MV_UNICODE: val = PyTuple_New(pv->Value.MVszW.cValues); if (val) { for (i=0; i<pv->Value.MVszW.cValues; i++) PyTuple_SET_ITEM(val, i, PyWinObject_FromWCHAR(pv->Value.MVszW.lppszW[i])); } break; /* case PT_MV_CLSID: MVguid SGuidArray case PT_MV_I8: MVli SLargeIntegerArray */ case PT_OBJECT: val = PyInt_FromLong(pv->Value.x); break; default: printf("File %s: Unsupported MAPI property type 0x%X", __FILE__, PROP_TYPE(pv->ulPropTag)); /* Dont set exception, as this prevents otherwise valid props from being returned */ val = Py_None; Py_INCREF(Py_None); break; } PyObject *rc = PyTuple_New(2); if (rc==NULL) { Py_DECREF(val); PyErr_SetString(PyExc_MemoryError, "Tuple(2) for PROP result"); return NULL; } PyTuple_SET_ITEM(rc, 0, PyInt_FromLong(pv->ulPropTag)); PyTuple_SET_ITEM(rc, 1, val); return rc; }
HRESULT MAPIContact::Init() { HRESULT hr = S_OK; Zimbra::Util::ScopedBuffer<SPropValue> pPropValMsgClass; if (FAILED(hr = HrGetOneProp(m_pMessage, PR_MESSAGE_CLASS, pPropValMsgClass.getptr()))) throw MAPIContactException(hr, L"Init(): HrGetOneProp Failed.", ERR_MAPI_CONTACT, __LINE__, __FILE__); if ((pPropValMsgClass->ulPropTag == PR_MESSAGE_CLASS_W) && (_tcsicmp( pPropValMsgClass->Value.LPSZ, L"ipm.distlist") == 0)) m_bPersonalDL = true; // initialize the MAPINAMEID structure GetIDsFromNames requires LPMAPINAMEID ppNames[N_NUM_NAMES] = { 0 }; for (int i = 0; i < N_NUM_NAMES; i++) { MAPIAllocateBuffer(sizeof (MAPINAMEID), (LPVOID *)&(ppNames[i])); ppNames[i]->ulKind = MNID_ID; ppNames[i]->lpguid = (LPGUID)(&PS_CONTACT_PROPERTIES); ppNames[i]->Kind.lID = nameIds[i]; } // get the real prop tag ID's LPSPropTagArray pContactTags = NULL; if (FAILED(hr = m_pMessage->GetIDsFromNames(N_NUM_NAMES, ppNames, MAPI_CREATE, &pContactTags))) throw MAPIContactException(hr, L"Init(): GetIDsFromNames Failed.", ERR_MAPI_CONTACT, __LINE__, __FILE__); // give the prop tag ID's a type pr_mail1address = SetPropType(pContactTags->aulPropTag[N_MAIL1], PT_TSTRING); pr_mail1entryid = SetPropType(pContactTags->aulPropTag[N_MAIL1EID], PT_BINARY); pr_mail1type = SetPropType(pContactTags->aulPropTag[N_MAIL1TYPE], PT_TSTRING); pr_mail1dispname = SetPropType(pContactTags->aulPropTag[N_MAIL1DISPNAME], PT_TSTRING); pr_mail2address = SetPropType(pContactTags->aulPropTag[N_MAIL2], PT_TSTRING); pr_mail2entryid = SetPropType(pContactTags->aulPropTag[N_MAIL2EID], PT_BINARY); pr_mail2type = SetPropType(pContactTags->aulPropTag[N_MAIL2TYPE], PT_TSTRING); pr_mail2dispname = SetPropType(pContactTags->aulPropTag[N_MAIL2DISPNAME], PT_TSTRING); pr_mail3address = SetPropType(pContactTags->aulPropTag[N_MAIL3], PT_TSTRING); pr_mail3entryid = SetPropType(pContactTags->aulPropTag[N_MAIL3EID], PT_BINARY); pr_mail3type = SetPropType(pContactTags->aulPropTag[N_MAIL3TYPE], PT_TSTRING); pr_mail3dispname = SetPropType(pContactTags->aulPropTag[N_MAIL3DISPNAME], PT_TSTRING); pr_fileas = SetPropType(pContactTags->aulPropTag[N_FILEAS], PT_TSTRING); pr_fileasID = SetPropType(pContactTags->aulPropTag[N_FILEAS_ID], PT_LONG); pr_business_address_city = SetPropType(pContactTags->aulPropTag[N_BUS_CITY], PT_TSTRING); pr_business_address_country = SetPropType(pContactTags->aulPropTag[N_BUS_COUNTRY], PT_TSTRING); pr_business_address_postal_code = SetPropType(pContactTags->aulPropTag[N_BUS_ZIP], PT_TSTRING); pr_business_address_state = SetPropType(pContactTags->aulPropTag[N_BUS_STATE], PT_TSTRING); pr_business_address_street = SetPropType(pContactTags->aulPropTag[N_BUS_STREET], PT_TSTRING); pr_contact_user1_idx = SetPropType(pContactTags->aulPropTag[N_CONTACT_USER1_IDX], PT_TSTRING); pr_contact_user2_idx = SetPropType(pContactTags->aulPropTag[N_CONTACT_USER2_IDX], PT_TSTRING); pr_contact_user3_idx = SetPropType(pContactTags->aulPropTag[N_CONTACT_USER3_IDX], PT_TSTRING); pr_contact_user4_idx = SetPropType(pContactTags->aulPropTag[N_CONTACT_USER4_IDX], PT_TSTRING); pr_contact_oneoffmemebrs = SetPropType( pContactTags->aulPropTag[N_CONTACT_ONEOFFMEMEBRS_IDX], PT_MV_BINARY); pr_imaddress = SetPropType(pContactTags->aulPropTag[N_IMADDRESS], PT_TSTRING); pr_anniversary = SetPropType(pContactTags->aulPropTag[N_ANNIVERSARY], PT_TSTRING); // free the memory we allocated on the head for (int i = 0; i < N_NUM_NAMES; i++) MAPIFreeBuffer(ppNames[i]); MAPIFreeBuffer(pContactTags); // these are the contact properties we need to get SizedSPropTagArray(C_NUM_PROPS, contactProps) = { C_NUM_PROPS, { PR_CALLBACK_TELEPHONE_NUMBER, PR_CAR_TELEPHONE_NUMBER, PR_COMPANY_NAME, pr_mail1address, pr_mail1entryid, pr_mail1type, pr_mail1dispname, pr_mail2address, pr_mail2entryid, pr_mail2type, pr_mail2dispname, pr_mail3address, pr_mail3entryid, pr_mail3type, pr_mail3dispname, pr_fileas, pr_fileasID, PR_GIVEN_NAME, PR_HOME_ADDRESS_CITY, PR_HOME_ADDRESS_COUNTRY, PR_HOME_FAX_NUMBER, PR_HOME_TELEPHONE_NUMBER, PR_HOME2_TELEPHONE_NUMBER, PR_HOME_ADDRESS_POSTAL_CODE, PR_HOME_ADDRESS_STATE_OR_PROVINCE, PR_HOME_ADDRESS_STREET, PR_TITLE, PR_SURNAME, PR_MIDDLE_NAME, PR_CELLULAR_TELEPHONE_NUMBER, PR_DISPLAY_NAME_PREFIX, PR_GENERATION, // notes is PR_BODY and PR_BODY_HTML PR_OTHER_ADDRESS_CITY, PR_OTHER_ADDRESS_COUNTRY, PR_PRIMARY_FAX_NUMBER, // other fax PR_OTHER_TELEPHONE_NUMBER, PR_OTHER_ADDRESS_POSTAL_CODE, PR_OTHER_ADDRESS_STATE_OR_PROVINCE, PR_OTHER_ADDRESS_STREET, PR_PAGER_TELEPHONE_NUMBER, pr_business_address_city, pr_business_address_country, PR_BUSINESS_FAX_NUMBER, PR_OFFICE_TELEPHONE_NUMBER, pr_business_address_postal_code, pr_business_address_state, pr_business_address_street, PR_BUSINESS_HOME_PAGE, PR_BIRTHDAY, pr_contact_user1_idx, pr_contact_user2_idx, pr_contact_user3_idx, pr_contact_user4_idx, pr_contact_oneoffmemebrs, pr_imaddress, PR_WEDDING_ANNIVERSARY } }; ULONG cVals = 0; if (FAILED(hr = m_pMessage->GetProps((LPSPropTagArray) & contactProps, fMapiUnicode, &cVals, &m_pPropVals))) throw MAPIContactException(hr, L"Init(): GetProps Failed.", ERR_MAPI_CONTACT, __LINE__, __FILE__); // see if there is a file-as id LONG zimbraFileAsId = 0; if (m_bPersonalDL) // PDL's always have a custom file-as { zimbraFileAsId = 8; Type(L"group"); } else if (m_pPropVals[C_FILEASID].ulPropTag == contactProps.aulPropTag[C_FILEASID]) { switch (m_pPropVals[C_FILEASID].Value.l) { case OFA_LAST_C_FIRST: zimbraFileAsId = 1; break; case OFA_FIRST_LAST: zimbraFileAsId = 2; break; case OFA_COMPANY: zimbraFileAsId = 3; break; case OFA_LAST_C_FIRST_COMPANY: zimbraFileAsId = 4; break; case OFA_COMPANY_LAST_C_FIRST: zimbraFileAsId = 6; break; case OFA_CUSTOM: zimbraFileAsId = 8; break; } } // process all "String" properties if (m_pPropVals[C_CALLBACK_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_CALLBACK_TELEPHONE_NUMBER]) CallbackPhone(m_pPropVals[C_CALLBACK_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_CAR_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_CAR_TELEPHONE_NUMBER]) CarPhone(m_pPropVals[C_CAR_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_COMPANY_NAME].ulPropTag == contactProps.aulPropTag[C_COMPANY_NAME]) Company(m_pPropVals[C_COMPANY_NAME].Value.lpszW); if (m_pPropVals[C_FILEAS].ulPropTag == contactProps.aulPropTag[C_FILEAS]) { if (zimbraFileAsId == 8) { LPWSTR pwszFileAsValue = m_pPropVals[C_FILEAS].Value.lpszW; if ((pwszFileAsValue != NULL) && (wcsicmp(pwszFileAsValue, L"") != 0)) { LPWSTR pwszTemp = new WCHAR[wcslen(m_pPropVals[C_FILEAS].Value.lpszW) + 3]; // there is a legit string for the custom fileas value wsprintf(pwszTemp, L"8:%s", pwszFileAsValue); FileAs(pwszTemp); // PDL's require a nickname if (m_bPersonalDL) NickName(m_pPropVals[C_FILEAS].Value.lpszW); delete[] pwszTemp; } else { LPWSTR pwszNONAME = new WCHAR[wcslen(L"NO_NAME") + 1]; wsprintf(pwszNONAME, L"%s", L"NO_NAME"); LPWSTR pwszTemp = new WCHAR[wcslen(pwszNONAME) + 3]; // there is a legit string for the custom fileas value wsprintf(pwszTemp, L"8:%s", pwszNONAME); FileAs(pwszTemp); // PDL's require a nickname if (m_bPersonalDL) NickName(pwszNONAME); delete[] pwszTemp; delete[] pwszNONAME; } } else if (zimbraFileAsId) { WCHAR pwszTemp[3]; _ltow(zimbraFileAsId, pwszTemp, 10); FileAs(pwszTemp); } } if (m_pPropVals[C_GIVEN_NAME].ulPropTag == contactProps.aulPropTag[C_GIVEN_NAME]) FirstName(m_pPropVals[C_GIVEN_NAME].Value.lpszW); if (m_pPropVals[C_HOME_ADDRESS_CITY].ulPropTag == contactProps.aulPropTag[C_HOME_ADDRESS_CITY]) HomeCity(m_pPropVals[C_HOME_ADDRESS_CITY].Value.lpszW); if (m_pPropVals[C_HOME_ADDRESS_COUNTRY].ulPropTag == contactProps.aulPropTag[C_HOME_ADDRESS_COUNTRY]) HomeCountry(m_pPropVals[C_HOME_ADDRESS_COUNTRY].Value.lpszW); if (m_pPropVals[C_HOME_FAX_NUMBER].ulPropTag == contactProps.aulPropTag[C_HOME_FAX_NUMBER]) HomeFax(m_pPropVals[C_HOME_FAX_NUMBER].Value.lpszW); if (m_pPropVals[C_HOME_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_HOME_TELEPHONE_NUMBER]) HomePhone(m_pPropVals[C_HOME_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_HOME2_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_HOME2_TELEPHONE_NUMBER]) HomePhone2(m_pPropVals[C_HOME2_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_HOME_ADDRESS_POSTAL_CODE].ulPropTag == contactProps.aulPropTag[C_HOME_ADDRESS_POSTAL_CODE]) HomePostalCode(m_pPropVals[C_HOME_ADDRESS_POSTAL_CODE].Value.lpszW); if (m_pPropVals[C_HOME_ADDRESS_STATE_OR_PROVINCE].ulPropTag == contactProps.aulPropTag[C_HOME_ADDRESS_STATE_OR_PROVINCE]) HomeState(m_pPropVals[C_HOME_ADDRESS_STATE_OR_PROVINCE].Value.lpszW); if (m_pPropVals[C_HOME_ADDRESS_STREET].ulPropTag == contactProps.aulPropTag[C_HOME_ADDRESS_STREET]) HomeStreet(m_pPropVals[C_HOME_ADDRESS_STREET].Value.lpszW); if (m_pPropVals[C_TITLE].ulPropTag == contactProps.aulPropTag[C_TITLE]) JobTitle(m_pPropVals[C_TITLE].Value.lpszW); if (m_pPropVals[C_SURNAME].ulPropTag == contactProps.aulPropTag[C_SURNAME]) LastName(m_pPropVals[C_SURNAME].Value.lpszW); if (m_pPropVals[C_MIDDLE_NAME].ulPropTag == contactProps.aulPropTag[C_MIDDLE_NAME]) MiddleName(m_pPropVals[C_MIDDLE_NAME].Value.lpszW); if (m_pPropVals[C_CELLULAR_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_CELLULAR_TELEPHONE_NUMBER]) MobilePhone(m_pPropVals[C_CELLULAR_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_DISPLAY_NAME_PREFIX].ulPropTag == contactProps.aulPropTag[C_DISPLAY_NAME_PREFIX]) NamePrefix(m_pPropVals[C_DISPLAY_NAME_PREFIX].Value.lpszW); if (m_pPropVals[C_GENERATION].ulPropTag == contactProps.aulPropTag[C_GENERATION]) NameSuffix(m_pPropVals[C_GENERATION].Value.lpszW); if (m_pPropVals[C_OTHER_ADDRESS_CITY].ulPropTag == contactProps.aulPropTag[C_OTHER_ADDRESS_CITY]) OtherCity(m_pPropVals[C_OTHER_ADDRESS_CITY].Value.lpszW); if (m_pPropVals[C_OTHER_ADDRESS_COUNTRY].ulPropTag == contactProps.aulPropTag[C_OTHER_ADDRESS_COUNTRY]) OtherCountry(m_pPropVals[C_OTHER_ADDRESS_COUNTRY].Value.lpszW); if (m_pPropVals[C_PRIMARY_FAX_NUMBER].ulPropTag == contactProps.aulPropTag[C_PRIMARY_FAX_NUMBER]) OtherFax(m_pPropVals[C_PRIMARY_FAX_NUMBER].Value.lpszW); if (m_pPropVals[C_OTHER_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_OTHER_TELEPHONE_NUMBER]) OtherPhone(m_pPropVals[C_OTHER_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_OTHER_ADDRESS_POSTAL_CODE].ulPropTag == contactProps.aulPropTag[C_OTHER_ADDRESS_POSTAL_CODE]) OtherPostalCode(m_pPropVals[C_OTHER_ADDRESS_POSTAL_CODE].Value.lpszW); if (m_pPropVals[C_OTHER_ADDRESS_STATE_OR_PROVINCE].ulPropTag == contactProps.aulPropTag[C_OTHER_ADDRESS_STATE_OR_PROVINCE]) OtherState(m_pPropVals[C_OTHER_ADDRESS_STATE_OR_PROVINCE].Value.lpszW); if (m_pPropVals[C_OTHER_ADDRESS_STREET].ulPropTag == contactProps.aulPropTag[C_OTHER_ADDRESS_STREET]) OtherStreet(m_pPropVals[C_OTHER_ADDRESS_STREET].Value.lpszW); if (m_pPropVals[C_PAGER_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_PAGER_TELEPHONE_NUMBER]) Pager(m_pPropVals[C_PAGER_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_BUSINESS_ADDRESS_CITY].ulPropTag == contactProps.aulPropTag[C_BUSINESS_ADDRESS_CITY]) WorkCity(m_pPropVals[C_BUSINESS_ADDRESS_CITY].Value.lpszW); if (m_pPropVals[C_BUSINESS_ADDRESS_COUNTRY].ulPropTag == contactProps.aulPropTag[C_BUSINESS_ADDRESS_COUNTRY]) WorkCountry(m_pPropVals[C_BUSINESS_ADDRESS_COUNTRY].Value.lpszW); if (m_pPropVals[C_BUSINESS_FAX_NUMBER].ulPropTag == contactProps.aulPropTag[C_BUSINESS_FAX_NUMBER]) WorkFax(m_pPropVals[C_BUSINESS_FAX_NUMBER].Value.lpszW); if (m_pPropVals[C_OFFICE_TELEPHONE_NUMBER].ulPropTag == contactProps.aulPropTag[C_OFFICE_TELEPHONE_NUMBER]) WorkPhone(m_pPropVals[C_OFFICE_TELEPHONE_NUMBER].Value.lpszW); if (m_pPropVals[C_BUSINESS_ADDRESS_POSTAL_CODE].ulPropTag == contactProps.aulPropTag[C_BUSINESS_ADDRESS_POSTAL_CODE]) WorkPostalCode(m_pPropVals[C_BUSINESS_ADDRESS_POSTAL_CODE].Value.lpszW); if (m_pPropVals[C_BUSINESS_ADDRESS_STATE].ulPropTag == contactProps.aulPropTag[C_BUSINESS_ADDRESS_STATE]) WorkState(m_pPropVals[C_BUSINESS_ADDRESS_STATE].Value.lpszW); if (m_pPropVals[C_BUSINESS_ADDRESS_STREET].ulPropTag == contactProps.aulPropTag[C_BUSINESS_ADDRESS_STREET]) WorkStreet(m_pPropVals[C_BUSINESS_ADDRESS_STREET].Value.lpszW); if (m_pPropVals[C_BUSINESS_HOME_PAGE].ulPropTag == contactProps.aulPropTag[C_BUSINESS_HOME_PAGE]) WorkURL(m_pPropVals[C_BUSINESS_HOME_PAGE].Value.lpszW); if (m_pPropVals[C_CONTACT_USER1_IDX].ulPropTag == contactProps.aulPropTag[C_CONTACT_USER1_IDX]) UserField1(m_pPropVals[C_CONTACT_USER1_IDX].Value.lpszW); if (m_pPropVals[C_CONTACT_USER2_IDX].ulPropTag == contactProps.aulPropTag[C_CONTACT_USER2_IDX]) UserField2(m_pPropVals[C_CONTACT_USER2_IDX].Value.lpszW); if (m_pPropVals[C_CONTACT_USER3_IDX].ulPropTag == contactProps.aulPropTag[C_CONTACT_USER3_IDX]) UserField3(m_pPropVals[C_CONTACT_USER3_IDX].Value.lpszW); if (m_pPropVals[C_CONTACT_USER4_IDX].ulPropTag == contactProps.aulPropTag[C_CONTACT_USER4_IDX]) UserField4(m_pPropVals[C_CONTACT_USER4_IDX].Value.lpszW); if (m_pPropVals[C_BIRTHDAY].ulPropTag == contactProps.aulPropTag[C_BIRTHDAY]) { SYSTEMTIME st = { 0 }; FileTimeToSystemTime(&(m_pPropVals[C_BIRTHDAY].Value.ft), &st); // We get PR_BIRTHDAY in UTC so let's convert it into local time TIME_ZONE_INFORMATION tzInfo = { 0 }; GetTimeZoneInformation(&tzInfo); SystemTimeToTzSpecificLocalTime(&tzInfo, &st, &st); TCHAR pszBDay[11]; swprintf(pszBDay, 11, _T("%4d-%02d-%02d"), st.wYear, st.wMonth, st.wDay); Birthday(pszBDay); } if (m_pPropVals[C_ANNIVERSARY].ulPropTag == contactProps.aulPropTag[C_ANNIVERSARY]) { SYSTEMTIME st = { 0 }; FileTimeToSystemTime(&(m_pPropVals[C_ANNIVERSARY].Value.ft), &st); // We get PR_ANNIVERSARY in UTC so let's convert it into local time TIME_ZONE_INFORMATION tzInfo = { 0 }; GetTimeZoneInformation(&tzInfo); SystemTimeToTzSpecificLocalTime(&tzInfo, &st, &st); TCHAR pszAnniv[11]; swprintf(pszAnniv, 11, _T("%4d-%02d-%02d"), st.wYear, st.wMonth, st.wDay); Anniversary(pszAnniv); } // email 1 RECIP_INFO tempRecip; if ((m_pPropVals[C_MAIL1TYPE].ulPropTag == contactProps.aulPropTag[C_MAIL1TYPE]) && (m_pPropVals[C_MAIL1ADDRESS].ulPropTag == contactProps.aulPropTag[C_MAIL1ADDRESS])) { if (wcscmp(m_pPropVals[C_MAIL1TYPE].Value.lpszW, L"SMTP") == 0) { Email(m_pPropVals[C_MAIL1ADDRESS].Value.lpszW); } else if (wcscmp(m_pPropVals[C_MAIL1TYPE].Value.lpszW, L"EX") == 0) { tempRecip.pAddrType = m_pPropVals[C_MAIL1TYPE].Value.lpszW; tempRecip.pEmailAddr = m_pPropVals[C_MAIL1ADDRESS].Value.lpszW; tempRecip.cbEid = m_pPropVals[C_MAIL1EID].Value.bin.cb; tempRecip.pEid = (LPENTRYID)(m_pPropVals[C_MAIL1EID].Value.bin.lpb); wstring strSenderEmail(_TEXT("")); HRESULT hr = Zimbra::MAPI::Util::HrMAPIGetSMTPAddress(*m_session, tempRecip, strSenderEmail); if (hr != S_OK) Email(m_pPropVals[C_MAIL1DISPNAME].Value.lpszW); else Email((LPTSTR)strSenderEmail.c_str()); } } // email 2 if ((m_pPropVals[C_MAIL2TYPE].ulPropTag == contactProps.aulPropTag[C_MAIL2TYPE]) && (m_pPropVals[C_MAIL2ADDRESS].ulPropTag == contactProps.aulPropTag[C_MAIL2ADDRESS])) { if (wcscmp(m_pPropVals[C_MAIL2TYPE].Value.lpszW, L"SMTP") == 0) { Email2(m_pPropVals[C_MAIL2ADDRESS].Value.lpszW); } else if (wcscmp(m_pPropVals[C_MAIL2TYPE].Value.lpszW, L"EX") == 0) { tempRecip.pAddrType = m_pPropVals[C_MAIL2TYPE].Value.lpszW; tempRecip.pEmailAddr = m_pPropVals[C_MAIL2ADDRESS].Value.lpszW; tempRecip.cbEid = m_pPropVals[C_MAIL2EID].Value.bin.cb; tempRecip.pEid = (LPENTRYID)(m_pPropVals[C_MAIL2EID].Value.bin.lpb); wstring strSenderEmail(_TEXT("")); HRESULT hr = Zimbra::MAPI::Util::HrMAPIGetSMTPAddress(*m_session, tempRecip, strSenderEmail); if (hr != S_OK) Email(m_pPropVals[C_MAIL2DISPNAME].Value.lpszW); else Email2((LPTSTR)strSenderEmail.c_str()); } } // email 3 if ((m_pPropVals[C_MAIL3TYPE].ulPropTag == contactProps.aulPropTag[C_MAIL3TYPE]) && (m_pPropVals[C_MAIL3ADDRESS].ulPropTag == contactProps.aulPropTag[C_MAIL3ADDRESS])) { if (wcscmp(m_pPropVals[C_MAIL3TYPE].Value.lpszW, L"SMTP") == 0) { Email3(m_pPropVals[C_MAIL3ADDRESS].Value.lpszW); } else if (wcscmp(m_pPropVals[C_MAIL3TYPE].Value.lpszW, L"EX") == 0) { tempRecip.pAddrType = m_pPropVals[C_MAIL3TYPE].Value.lpszW; tempRecip.pEmailAddr = m_pPropVals[C_MAIL3ADDRESS].Value.lpszW; tempRecip.cbEid = m_pPropVals[C_MAIL3EID].Value.bin.cb; tempRecip.pEid = (LPENTRYID)(m_pPropVals[C_MAIL3EID].Value.bin.lpb); wstring strSenderEmail(_TEXT("")); HRESULT hr = Zimbra::MAPI::Util::HrMAPIGetSMTPAddress(*m_session, tempRecip, strSenderEmail); if (hr != S_OK) Email(m_pPropVals[C_MAIL3DISPNAME].Value.lpszW); else Email3((LPTSTR)strSenderEmail.c_str()); } } if (m_pPropVals[C_IMADDRESS].ulPropTag == contactProps.aulPropTag[C_IMADDRESS]) IMAddress1(m_pPropVals[C_IMADDRESS].Value.lpszW); // add the 'notes' section if (m_mapiMessage->HasTextPart()) { LPTSTR pBody = NULL; UINT nText = 0; m_mapiMessage->TextBody(&pBody, nText); LPTSTR psz = pBody; if (psz) { const char SPACE = ' ', TAB = '\t', CR = 0x0d, LF = 0x0a; while (*psz) { // Replace control characters with space // Exclude carriage return and new line characters while doing the same if ((*psz < SPACE) && (*psz != CR) && (*psz != LF)) *psz = _T(' '); psz++; } // We'll add the body only if it has data other than white spaces and new lines bool bHasValidChars = false; psz = pBody; while (*psz) { if ((*psz == SPACE) || (*psz == TAB) || (*psz == CR) || (*psz == LF)) { psz++; continue; } else { bHasValidChars = true; break; } } if (bHasValidChars) Notes(pBody); MAPIFreeBuffer(pBody); } } // if its a distribution list, add the dist list members to the property wstring strInvalidGroupContacts; if (m_bPersonalDL) { std::wstring dlist = L""; if (m_pPropVals[C_ONEOFFMEMEBRS_IDX].ulPropTag == contactProps.aulPropTag[C_ONEOFFMEMEBRS_IDX]) { bool bFirst = true; for (ULONG i = 0; i < m_pPropVals[C_ONEOFFMEMEBRS_IDX].Value.MVbin.cValues; i++) { DWORD dwObjType; SBinary &bin = m_pPropVals[C_ONEOFFMEMEBRS_IDX].Value.MVbin.lpbin[i]; IMailUser *pUser = NULL; hr = m_session->OpenEntry(bin.cb, (LPENTRYID)bin.lpb, NULL, 0, &dwObjType, (LPUNKNOWN *)&pUser); if (FAILED(hr) || !pUser) continue; LPSPropValue pDNProp = NULL; LPSPropValue pAddrProp = NULL; std::wstring user = L""; BOOL bIsInvalidContact = TRUE; HrGetOneProp(pUser, PR_DISPLAY_NAME_W, &pDNProp); HrGetOneProp(pUser, PR_EMAIL_ADDRESS_W, &pAddrProp); if (pDNProp && (pDNProp->ulPropTag == PR_DISPLAY_NAME_W) && wcslen( pDNProp->Value.lpszW)) user += pDNProp->Value.lpszW; if (pAddrProp && (pAddrProp->ulPropTag == PR_EMAIL_ADDRESS_W) && wcslen( pAddrProp->Value.lpszW)) { std::wstring temp = pAddrProp->Value.lpszW; if (temp.find(L'@') != std::wstring::npos) bIsInvalidContact = FALSE; if (!user.empty()) user += L" "; user += L"<"; user += temp; user += L">"; } if (bIsInvalidContact) { if (!user.empty()) { if (!strInvalidGroupContacts.empty()) strInvalidGroupContacts += _T(", "); strInvalidGroupContacts += user.c_str(); } } else { if (bFirst) bFirst = false; else dlist += L","; dlist += user; } pUser->Release(); MAPIFreeBuffer(pDNProp); MAPIFreeBuffer(pAddrProp); } } //set DL values DList((LPTSTR)dlist.c_str()); } //user define props if (!m_bPersonalDL) { LPMAPINAMEID FAR *lppPropNames = NULL; LPSPropTagArray tagArray; ULONG lCount = 0; hr = m_pMessage->GetPropList(MAPI_UNICODE, &tagArray); if (hr == S_OK) { hr = m_pMessage->GetNamesFromIDs(&tagArray, (LPGUID)&PS_PUBLIC_STRINGS, 0, &lCount, &lppPropNames); if (SUCCEEDED(hr)) { WCHAR wszProps2GUID[40] = { 0 }; Zimbra::Util::Guid nameProps2Guid(OUTLOOK_NAME_PROPS_GUID_2); nameProps2Guid.toString(wszProps2GUID); WCHAR wszContactPropGUID[40] = { 0 }; WCHAR wszVal[1024]={0}; for (ULONG i = 0; i < lCount; i++) { Zimbra::Util::ScopedBuffer<SPropValue> pPropVal; hr = HrGetOneProp(m_pMessage, tagArray->aulPropTag[i], pPropVal.getptr()); if (lppPropNames[i] != NULL) // FBS bug 71786 -- 3/20/12 { if (lppPropNames[i]->ulKind == MNID_STRING) { Zimbra::Util::Guid propGuid(*lppPropNames[i]->lpguid); propGuid.toString(wszContactPropGUID); if (lstrcmpiW(wszContactPropGUID, wszProps2GUID) == 0) { LPWSTR szPropName = lppPropNames[i]->Kind.lpwstrName; // now format a string depending on the type ULONG ulPropType = PROP_TYPE(pPropVal->ulPropTag); BOOL bSetAttribute = TRUE; switch (ulPropType) { case PT_UNICODE: wcscpy(wszVal, pPropVal->Value.lpszW); break; case PT_SYSTIME: { SYSTEMTIME sysTime = { 0 }; if (FileTimeToSystemTime(&(pPropVal->Value.ft), &sysTime)) { TIME_ZONE_INFORMATION tzInfo = { 0 }; GetTimeZoneInformation(&tzInfo); SystemTimeToTzSpecificLocalTime(&tzInfo, &sysTime, &sysTime); wsprintf(wszVal, L"%4d-%02d-%02d", sysTime.wYear, sysTime.wMonth, sysTime.wDay); } break; } case PT_LONG: wsprintf(wszVal, L"%d", pPropVal->Value.l); break; case PT_DOUBLE: { CHAR tmp[36]; _gcvt(pPropVal->Value.dbl, 6, tmp); LPWSTR wszTmp = Zimbra::Util::AnsiiToUnicode(tmp); wcscpy(wszVal, wszTmp); break; } case PT_BOOLEAN: if (pPropVal->Value.b) wcscpy(wszVal, L"TRUE"); else wcscpy(wszVal, L"FALSE"); break; case PT_CURRENCY: { LONGLONG lCurrency; CURRENCY currency; currency = pPropVal->Value.cur; lCurrency = currency.int64; lCurrency = lCurrency / 10000; wsprintf(wszVal, L"$%I64d", lCurrency); break; } default: // can't deal with these other types bSetAttribute = FALSE; //LOG("%hs: MAPI type %0x not supported: user defined field %s will not be synced"), // __FUNCTION__, ulPropType, szPropName); } ContactUDFields cudf; cudf.Name = szPropName; cudf.value = wszVal; AddUserDefinedField(cudf); } } } } MAPIFreeBuffer(lppPropNames); } MAPIFreeBuffer(tagArray); } } // Save image path wstring wstrImagePath; if (m_mapiMessage->HasAttach()) { if (!FAILED(hr = GetContactImage(wstrImagePath))) ContactImagePath((LPTSTR)wstrImagePath.c_str()); } return S_OK; }
//$--HrMAPIGetPropToFile--------------------------------------------------------- // Get a property and put in a given file. // ----------------------------------------------------------------------------- HRESULT HrMAPIGetPropToFile( // RETURNS: return code IN LPMAPIPROP lpObj, // pointer to object IN ULONG ulPropTag, // property tag IN LPSTR lpszFilename, // pointer to destination file name OUT ULONG *lpcbProp) // pointer to count of bytes address // variable { HRESULT hr = NOERROR; HRESULT hrT = NOERROR; SCODE sc = 0; LPSTREAM lpStream = NULL; HANDLE hFile = NULL; ULONG ulBytesRead = 0; LPBYTE lpbBlock = NULL; DWORD dwBytesWritten = 0; DEBUGPUBLIC("HrMAPIGetPropToFile()\n"); hr = CHK_HrMAPIGetPropToFile( lpObj, ulPropTag, lpszFilename, lpcbProp); if(FAILED(hr)) RETURN(hr); // Open a stream on the property hrT = MAPICALL(lpObj)->OpenProperty( /*lpObj,*/ ulPropTag, (LPIID)&IID_IStream, STGM_READ, MAPI_DEFERRED_ERRORS, (LPUNKNOWN *)&lpStream); if(FAILED(hrT)) { // Streams are not supported by provider if((hrT == MAPI_E_NO_SUPPORT) || (hrT == MAPI_E_INTERFACE_NOT_SUPPORTED)) { ULONG PropType = 0; lpStream = NULL; MODULE_WARNING1("Streams are not supported by provider [%08lx]",hrT); PropType = PROP_TYPE(ulPropTag); // Read property into memory switch(PropType) { case PT_BINARY: hr = HrMAPIGetPropBinary( lpObj, ulPropTag, &ulBytesRead, (void **)&lpbBlock); break; default: hr = HrMAPIGetPropString( lpObj, ulPropTag, &ulBytesRead, (void **)&lpbBlock); } } else { hr = HR_LOG(E_FAIL); goto cleanup; } if(FAILED(hr)) { goto cleanup; } } hFile = CreateFile( lpszFilename, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN, NULL); if(hFile == INVALID_HANDLE_VALUE) { hr = HR_LOG(E_FAIL); goto cleanup; } // Copy propery value to the file if(lpStream != NULL) { sc = MAPIAllocateBuffer(EDK_CBTRANSFER, (void **)&lpbBlock); // An error occured allocating the block buffer if(FAILED(sc)) { hr = HR_LOG(E_OUTOFMEMORY); goto cleanup; } for (;;) { // Read a block from the stream hrT = /*OLECALL*/(lpStream)->Read( /*lpStream,*/ lpbBlock, EDK_CBTRANSFER, &ulBytesRead); if(FAILED(hrT)) { hr = HR_LOG(E_FAIL); goto cleanup; } if(ulBytesRead == 0L) break; // Write the block to the file hr = _HrWriteFile(hFile, ulBytesRead, lpbBlock); if(FAILED(hr)) { goto cleanup; } } } else { // Write the block to the file hr = _HrWriteFile(hFile, ulBytesRead, lpbBlock); if(FAILED(hr)) { goto cleanup; } } cleanup: // Close the file if(hFile != NULL) { if(CloseHandle(hFile) == FALSE) { hr = HR_LOG(E_FAIL); } } // Release the stream //ULOLERELEASE(lpStream); if (lpStream != NULL) { lpStream->Release(); } lpStream = NULL; MAPIFREEBUFFER(lpbBlock); RETURN(hr); }
// @object PySPropValue|A MAPI property value. Property values can either be passed from // python into MAPI functions, or returned from MAPI functions to Python. BOOL PyMAPIObject_AsSPropValue(PyObject *Valob, SPropValue *pv, void *pAllocMoreLinkBlock) { PyObject *ob; // @pyparm int|propType||The type of the MAPI property // @pyparm object|value||The property value if (!PyArg_ParseTuple(Valob, "lO:SPropValue item", &pv->ulPropTag, &ob )) { PyErr_Clear(); PyErr_SetString(PyExc_TypeError, "An SPropValue item must be a tuple of (integer, object)"); return NULL; } BOOL ok = TRUE; unsigned int i; PyErr_Clear(); // @comm The parameters can be one of the following pairs of values. // @flagh propType|value switch (PROP_TYPE(pv->ulPropTag)) { // @flag PT_I2|An integer case PT_I2: // case PT_SHORT: pv->Value.i = (int)PyInt_AsLong(ob); break; // @flag PT_MV_I2|A sequence of integers case PT_MV_I2: MAKE_MV(short int, pAllocMoreLinkBlock, pv->Value.MVi.lpi, pv->Value.MVi.cValues, PyInt_AsLong) // @flag PT_I4|An integer case PT_I4: // case PT_LONG: pv->Value.l = PyInt_AsLong(ob); break; // @flag PT_MV_I4|A sequence of integers case PT_MV_I4: MAKE_MV(long, pAllocMoreLinkBlock, pv->Value.MVl.lpl, pv->Value.MVl.cValues, PyInt_AsLong) // @flag PT_R4|A float case PT_R4: // case PT_FLOAT: pv->Value.flt = (float)PyFloat_AsDouble(ob); break; // @flag PT_MV_R4|A sequence of floats case PT_MV_R4: MAKE_MV(float, pAllocMoreLinkBlock, pv->Value.MVflt.lpflt, pv->Value.MVflt.cValues, PyFloat_AsDouble) // @flag PT_R8|A float case PT_R8: // case PT_DOUBLE: pv->Value.dbl = PyFloat_AsDouble(ob); break; // @flag PT_MV_R8|A sequence of floats case PT_MV_R8: MAKE_MV(double, pAllocMoreLinkBlock, pv->Value.MVdbl.lpdbl, pv->Value.MVdbl.cValues, PyFloat_AsDouble) // @flag PT_BOOLEAN|A boolean value (or an int) case PT_BOOLEAN: pv->Value.b = PyInt_AsLong(ob) ? VARIANT_TRUE : VARIANT_FALSE; break; /* case PT_CURRENCY: p->Value.cur ?? break; */ // @flag PT_APPTIME|A <o PyTime> object case PT_APPTIME : ok = PyWinObject_AsDATE(ob, &pv->Value.at); break; // @flag PT_MV_APPTIME|An sequence of <o PyTime> object case PT_MV_APPTIME: MAKEB_MV(double, pAllocMoreLinkBlock, pv->Value.MVat.lpat, pv->Value.MVat.cValues, PyWinObject_AsDATE) // @flag PT_SYSTIME|A <o PyTime> object case PT_SYSTIME: ok = PyWinObject_AsFILETIME(ob, &pv->Value.ft); break; // @flag PT_MV_APPTIME|An sequence of <o PyTime> object case PT_MV_SYSTIME: MAKEB_MV(FILETIME, pAllocMoreLinkBlock, pv->Value.MVft.lpft, pv->Value.MVft.cValues, PyWinObject_AsFILETIME) // @flag PT_STRING8|A string or <o PyUnicode> case PT_STRING8: { // Copy into new MAPI memory block DWORD bufLen; char *str; ok = PyWinObject_AsString(ob, &str, FALSE, &bufLen); if (ok) { bufLen++; HRESULT hr = MAPIAllocateMore(bufLen, pAllocMoreLinkBlock, (void **)&pv->Value.lpszA); if (S_OK!=hr) { OleSetOleError(hr); ok = FALSE; } else { memcpy(pv->Value.lpszA, str, bufLen-sizeof(char)); // Null terminate memcpy(((char *)pv->Value.lpszA)+(bufLen-sizeof(char)),"\0", sizeof(char)); } } PyWinObject_FreeString(str); break; } // @flag PT_STRING8|A sequence of string or <o PyUnicode> objects. case PT_MV_STRING8: ok = AllocMVBuffer( ob, sizeof(char *), pAllocMoreLinkBlock, (void **)&pv->Value.MVszA.lppszA, &pv->Value.MVszA.cValues); if (!ok) break; for (i=0; ok && !PyErr_Occurred() && i<pv->Value.MVszA.cValues; i++) { PyObject *obmv=PySequence_GetItem(ob,i); if (obmv==NULL) break; DWORD bufLen; char *str; ok = PyWinObject_AsString(obmv, &str, FALSE, &bufLen); if (ok) { bufLen++; HRESULT hr = MAPIAllocateMore(bufLen, pAllocMoreLinkBlock, (void **)&pv->Value.MVszA.lppszA[i]); if (S_OK!=hr) { OleSetOleError(hr); ok = FALSE; } else { memcpy(pv->Value.MVszA.lppszA[i], str, bufLen-sizeof(char)); // Null terminate memcpy(((char *)pv->Value.MVszA.lppszA[i])+(bufLen-sizeof(char)),"\0", sizeof(char)); } } PyWinObject_FreeString(str); Py_DECREF(obmv); } break; // @flag PT_UNICODE|A string or <o PyUnicode> case PT_UNICODE: { // Bit of a hack - need to copy into MAPI block. BSTR wstr = NULL; ok = PyWinObject_AsBstr(ob, &wstr, FALSE); if (ok) { DWORD bufSize = sizeof(WCHAR) * (SysStringLen(wstr)+1); HRESULT hr = MAPIAllocateMore(bufSize, pAllocMoreLinkBlock, (void **)&pv->Value.lpszW); if (S_OK!=hr) { OleSetOleError(hr); ok = FALSE; } else { memcpy(pv->Value.lpszW, wstr, bufSize-2); // Null terminate memcpy(((char *)pv->Value.lpszW)+(bufSize-2),"\0\0", 2); } } SysFreeString(wstr); break; } // @flag PT_MV_UNICODE|A sequence of string or <o PyUnicode> case PT_MV_UNICODE: ok = AllocMVBuffer( ob, sizeof(char *), pAllocMoreLinkBlock, (void **)&pv->Value.MVszW.lppszW, &pv->Value.MVszW.cValues); if (!ok) break; for (i=0; ok && !PyErr_Occurred() && i<pv->Value.MVszW.cValues; i++) { PyObject *obmv=PySequence_GetItem(ob,i); if (obmv==NULL) break; BSTR wstr = NULL; ok = PyWinObject_AsBstr(obmv, &wstr, FALSE); if (ok) { DWORD bufSize = sizeof(WCHAR) * (SysStringLen(wstr)+1); HRESULT hr = MAPIAllocateMore(bufSize, pAllocMoreLinkBlock, (void **)&pv->Value.MVszW.lppszW[i]); if (S_OK!=hr) { OleSetOleError(hr); ok = FALSE; } else { memcpy(pv->Value.MVszW.lppszW[i], wstr, bufSize-2); // Null terminate memcpy(((char *)pv->Value.MVszW.lppszW[i])+(bufSize-2),"\0\0", 2); } } SysFreeString(wstr); Py_DECREF(obmv); } break; // @flag PT_BINARY|A string containing binary data case PT_BINARY: pv->Value.bin.lpb = (unsigned char *)PyString_AsString(ob); pv->Value.bin.cb = PyString_Size(ob); break; // @flag PT_MV_BINARY|A sequence of strings containing binary data case PT_MV_BINARY: ok = AllocMVBuffer( ob, sizeof(SBinary), pAllocMoreLinkBlock, (void **)&pv->Value.MVbin.lpbin, &pv->Value.MVbin.cValues); for (i=0; !PyErr_Occurred() && i<pv->Value.MVbin.cValues; i++) { PyObject *obmv=PySequence_GetItem(ob,i); if (obmv==NULL) break; pv->Value.MVbin.lpbin[i].lpb = (unsigned char *)PyString_AsString(ob); pv->Value.MVbin.lpbin[i].cb = PyString_Size(ob); Py_DECREF(obmv); } break; // @flag PT_CLSID|A <o PyIID> case PT_CLSID: { HRESULT hr = MAPIAllocateMore(sizeof(CLSID), pAllocMoreLinkBlock, (void **)&pv->Value.lpguid); if (S_OK != hr) { OleSetOleError(hr); ok = FALSE; } else ok = PyWinObject_AsIID(ob, pv->Value.lpguid); break; } // @flag PT_MV_CLSID|A sequence of <o PyIID> objects case PT_MV_CLSID: MAKEB_MV(CLSID, pAllocMoreLinkBlock, pv->Value.MVguid.lpguid, pv->Value.MVguid.cValues, PyWinObject_AsIID) // @flag PT_I8|A <o PyLARGE_INTEGER> case PT_I8: // case PT_LONGLONG: ok = PyWinObject_AsLARGE_INTEGER(ob, &pv->Value.li); break; // @flag PT_MV_I8|A sequence of <o PyLARGE_INTEGER> case PT_MV_I8: MAKEB_MV(LARGE_INTEGER, pAllocMoreLinkBlock, pv->Value.MVli.lpli, pv->Value.MVli.cValues, PyWinObject_AsLARGE_INTEGER) // @flag PT_ERROR|An integer error code. case PT_ERROR: pv->Value.err = (SCODE)PyInt_AsLong(ob); break; // @flag PT_NULL|Anything! case PT_NULL: pv->Value.x = 0; break; default: { char buf[128]; sprintf(buf, "Unsupported MAPI property type 0x%X", PROP_TYPE(pv->ulPropTag)); PyErr_SetString(PyExc_TypeError, buf); ok = FALSE; } } ok = (ok && !PyErr_Occurred()); return ok; }