Bug 1851535 - Remove dead file importers and some other dead importer code. r=mkmelin
These files aren't used by any Thunderbird code. Differential Revision: https://phabricator.services.mozilla.com/D211683 --HG-- extra : moz-landing-system : lando
This commit is contained in:
Родитель
0d2f987844
Коммит
780f801b57
|
@ -1,58 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "ImportCharSet.h"
|
||||
|
||||
char ImportCharSet::m_upperCaseMap[256];
|
||||
char ImportCharSet::m_Ascii[256] = {0}; // the initialiser makes it strong
|
||||
|
||||
class UInitMaps {
|
||||
public:
|
||||
UInitMaps();
|
||||
};
|
||||
|
||||
UInitMaps gInitMaps;
|
||||
|
||||
UInitMaps::UInitMaps() {
|
||||
int i;
|
||||
|
||||
for (i = 0; i < 256; i++) ImportCharSet::m_upperCaseMap[i] = i;
|
||||
for (i = 'a'; i <= 'z'; i++) ImportCharSet::m_upperCaseMap[i] = i - 'a' + 'A';
|
||||
|
||||
for (i = 0; i < 256; i++) ImportCharSet::m_Ascii[i] = 0;
|
||||
|
||||
for (i = ImportCharSet::cUpperAChar; i <= ImportCharSet::cUpperZChar; i++)
|
||||
ImportCharSet::m_Ascii[i] |=
|
||||
(ImportCharSet::cAlphaNumChar | ImportCharSet::cAlphaChar);
|
||||
for (i = ImportCharSet::cLowerAChar; i <= ImportCharSet::cLowerZChar; i++)
|
||||
ImportCharSet::m_Ascii[i] |=
|
||||
(ImportCharSet::cAlphaNumChar | ImportCharSet::cAlphaChar);
|
||||
for (i = ImportCharSet::cZeroChar; i <= ImportCharSet::cNineChar; i++)
|
||||
ImportCharSet::m_Ascii[i] |=
|
||||
(ImportCharSet::cAlphaNumChar | ImportCharSet::cDigitChar);
|
||||
|
||||
ImportCharSet::m_Ascii[ImportCharSet::cTabChar] |=
|
||||
ImportCharSet::cWhiteSpaceChar;
|
||||
ImportCharSet::m_Ascii[ImportCharSet::cCRChar] |=
|
||||
ImportCharSet::cWhiteSpaceChar;
|
||||
ImportCharSet::m_Ascii[ImportCharSet::cLinefeedChar] |=
|
||||
ImportCharSet::cWhiteSpaceChar;
|
||||
ImportCharSet::m_Ascii[ImportCharSet::cSpaceChar] |=
|
||||
ImportCharSet::cWhiteSpaceChar;
|
||||
|
||||
ImportCharSet::m_Ascii[uint8_t('(')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t(')')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t('<')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t('>')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t('@')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t(',')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t(';')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t(':')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t('\\')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t('"')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t('.')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t('[')] |= ImportCharSet::c822SpecialChar;
|
||||
ImportCharSet::m_Ascii[uint8_t(']')] |= ImportCharSet::c822SpecialChar;
|
||||
}
|
|
@ -1,201 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef ImportCharSet_h___
|
||||
#define ImportCharSet_h___
|
||||
|
||||
#include "nscore.h"
|
||||
|
||||
// Some useful ASCII values
|
||||
// 'A' = 65, 0x41
|
||||
// 'Z' = 90, 0x5a
|
||||
// '_' = 95, 0x5f
|
||||
// 'a' = 97, 0x61
|
||||
// 'z' = 122, 0x7a
|
||||
// '0' = 48, 0x30
|
||||
// '1' = 49, 0x31
|
||||
// '9' = 57, 0x39
|
||||
// ' ' = 32, 0x20
|
||||
// whitespace, 10, 13, 32, 9 (linefeed, cr, space, tab) - 0x0a, 0x0d, 0x20,
|
||||
// 0x09
|
||||
// ':' = 58, 0x3a
|
||||
|
||||
// a typedef enum would be nicer but some compilers still have trouble with
|
||||
// treating enum's as plain numbers when needed
|
||||
|
||||
class ImportCharSet {
|
||||
public:
|
||||
enum {
|
||||
cTabChar = 9,
|
||||
cLinefeedChar = 10,
|
||||
cCRChar = 13,
|
||||
cSpaceChar = 32,
|
||||
cUpperAChar = 65,
|
||||
cUpperZChar = 90,
|
||||
cUnderscoreChar = 95,
|
||||
cLowerAChar = 97,
|
||||
cLowerZChar = 122,
|
||||
cZeroChar = 48,
|
||||
cNineChar = 57,
|
||||
|
||||
cAlphaNumChar = 1,
|
||||
cAlphaChar = 2,
|
||||
cWhiteSpaceChar = 4,
|
||||
cDigitChar = 8,
|
||||
c822SpecialChar = 16
|
||||
};
|
||||
|
||||
static char m_upperCaseMap[256];
|
||||
static char m_Ascii[256];
|
||||
|
||||
inline static bool IsUSAscii(uint8_t ch) {
|
||||
return (((ch & (uint8_t)0x80) == 0));
|
||||
}
|
||||
inline static bool Is822CtlChar(uint8_t ch) { return (ch < 32); }
|
||||
inline static bool Is822SpecialChar(uint8_t ch) {
|
||||
return ((m_Ascii[ch] & c822SpecialChar) == c822SpecialChar);
|
||||
}
|
||||
inline static bool IsWhiteSpace(uint8_t ch) {
|
||||
return ((m_Ascii[ch] & cWhiteSpaceChar) == cWhiteSpaceChar);
|
||||
}
|
||||
inline static bool IsAlphaNum(uint8_t ch) {
|
||||
return ((m_Ascii[ch] & cAlphaNumChar) == cAlphaNumChar);
|
||||
}
|
||||
inline static bool IsDigit(uint8_t ch) {
|
||||
return ((m_Ascii[ch] & cDigitChar) == cDigitChar);
|
||||
}
|
||||
|
||||
inline static uint8_t ToLower(uint8_t ch) {
|
||||
if ((m_Ascii[ch] & cAlphaChar) == cAlphaChar) {
|
||||
return cLowerAChar + (m_upperCaseMap[ch] - cUpperAChar);
|
||||
} else
|
||||
return ch;
|
||||
}
|
||||
|
||||
inline static long AsciiToLong(const uint8_t* pChar, uint32_t len) {
|
||||
long num = 0;
|
||||
while (len) {
|
||||
if ((m_Ascii[*pChar] & cDigitChar) == 0) return num;
|
||||
num *= 10;
|
||||
num += (*pChar - cZeroChar);
|
||||
len--;
|
||||
pChar++;
|
||||
}
|
||||
return num;
|
||||
}
|
||||
|
||||
inline static void ByteToHex(uint8_t byte, uint8_t* pHex) {
|
||||
uint8_t val = byte;
|
||||
val /= 16;
|
||||
if (val < 10)
|
||||
*pHex = '0' + val;
|
||||
else
|
||||
*pHex = 'A' + (val - 10);
|
||||
pHex++;
|
||||
val = byte;
|
||||
val &= 0x0F;
|
||||
if (val < 10)
|
||||
*pHex = '0' + val;
|
||||
else
|
||||
*pHex = 'A' + (val - 10);
|
||||
}
|
||||
|
||||
inline static void LongToHexBytes(uint32_t type, uint8_t* pStr) {
|
||||
ByteToHex((uint8_t)(type >> 24), pStr);
|
||||
pStr += 2;
|
||||
ByteToHex((uint8_t)((type >> 16) & 0x0FF), pStr);
|
||||
pStr += 2;
|
||||
ByteToHex((uint8_t)((type >> 8) & 0x0FF), pStr);
|
||||
pStr += 2;
|
||||
ByteToHex((uint8_t)(type & 0x0FF), pStr);
|
||||
}
|
||||
|
||||
inline static void SkipWhiteSpace(const uint8_t*& pChar, uint32_t& pos,
|
||||
uint32_t max) {
|
||||
while ((pos < max) && (IsWhiteSpace(*pChar))) {
|
||||
pos++;
|
||||
pChar++;
|
||||
}
|
||||
}
|
||||
|
||||
inline static void SkipSpaceTab(const uint8_t*& pChar, uint32_t& pos,
|
||||
uint32_t max) {
|
||||
while ((pos < max) &&
|
||||
((*pChar == (uint8_t)cSpaceChar) || (*pChar == (uint8_t)cTabChar))) {
|
||||
pos++;
|
||||
pChar++;
|
||||
}
|
||||
}
|
||||
|
||||
inline static void SkipTilSpaceTab(const uint8_t*& pChar, uint32_t& pos,
|
||||
uint32_t max) {
|
||||
while ((pos < max) && (*pChar != (uint8_t)cSpaceChar) &&
|
||||
(*pChar != (uint8_t)cTabChar)) {
|
||||
pos++;
|
||||
pChar++;
|
||||
}
|
||||
}
|
||||
|
||||
inline static bool StrNICmp(const uint8_t* pChar, const uint8_t* pSrc,
|
||||
uint32_t len) {
|
||||
while (len && (m_upperCaseMap[*pChar] == m_upperCaseMap[*pSrc])) {
|
||||
pChar++;
|
||||
pSrc++;
|
||||
len--;
|
||||
}
|
||||
return len == 0;
|
||||
}
|
||||
|
||||
inline static bool StrNCmp(const uint8_t* pChar, const uint8_t* pSrc,
|
||||
uint32_t len) {
|
||||
while (len && (*pChar == *pSrc)) {
|
||||
pChar++;
|
||||
pSrc++;
|
||||
len--;
|
||||
}
|
||||
return len == 0;
|
||||
}
|
||||
|
||||
inline static int FindChar(const uint8_t* pChar, uint8_t ch, uint32_t max) {
|
||||
uint32_t pos = 0;
|
||||
while ((pos < max) && (*pChar != ch)) {
|
||||
pos++;
|
||||
pChar++;
|
||||
}
|
||||
if (pos < max)
|
||||
return (int)pos;
|
||||
else
|
||||
return -1;
|
||||
}
|
||||
|
||||
inline static bool NextChar(const uint8_t*& pChar, uint8_t ch, uint32_t& pos,
|
||||
uint32_t max) {
|
||||
if ((pos < max) && (*pChar == ch)) {
|
||||
pos++;
|
||||
pChar++;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
inline static int32_t strcmp(const char* pS1, const char* pS2) {
|
||||
while (*pS1 && *pS2 && (*pS1 == *pS2)) {
|
||||
pS1++;
|
||||
pS2++;
|
||||
}
|
||||
return *pS1 - *pS2;
|
||||
}
|
||||
|
||||
inline static int32_t stricmp(const char* pS1, const char* pS2) {
|
||||
while (*pS1 && *pS2 &&
|
||||
(m_upperCaseMap[uint8_t(*pS1)] == m_upperCaseMap[uint8_t(*pS2)])) {
|
||||
pS1++;
|
||||
pS2++;
|
||||
}
|
||||
return m_upperCaseMap[uint8_t(*pS1)] - m_upperCaseMap[uint8_t(*pS2)];
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* ImportCharSet_h__ */
|
|
@ -1,257 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nscore.h"
|
||||
#include "nsString.h"
|
||||
#include "prio.h"
|
||||
#include "nsNetUtil.h"
|
||||
#include "nsISeekableStream.h"
|
||||
#include "nsMsgUtils.h"
|
||||
#include "ImportOutFile.h"
|
||||
#include "ImportCharSet.h"
|
||||
|
||||
#include "ImportDebug.h"
|
||||
|
||||
/*
|
||||
#ifdef _MAC
|
||||
#define kMacNoCreator '????'
|
||||
#define kMacTextFile 'TEXT'
|
||||
#else
|
||||
#define kMacNoCreator 0
|
||||
#define kMacTextFile 0
|
||||
#endif
|
||||
*/
|
||||
|
||||
ImportOutFile::ImportOutFile() {
|
||||
m_ownsFileAndBuffer = false;
|
||||
m_pos = 0;
|
||||
m_pBuf = nullptr;
|
||||
m_bufSz = 0;
|
||||
m_pTrans = nullptr;
|
||||
m_pTransOut = nullptr;
|
||||
m_pTransBuf = nullptr;
|
||||
}
|
||||
|
||||
ImportOutFile::ImportOutFile(nsIFile* pFile, uint8_t* pBuf, uint32_t sz) {
|
||||
m_pTransBuf = nullptr;
|
||||
m_pTransOut = nullptr;
|
||||
m_pTrans = nullptr;
|
||||
m_ownsFileAndBuffer = false;
|
||||
InitOutFile(pFile, pBuf, sz);
|
||||
}
|
||||
|
||||
ImportOutFile::~ImportOutFile() {
|
||||
if (m_ownsFileAndBuffer) {
|
||||
Flush();
|
||||
delete[] m_pBuf;
|
||||
}
|
||||
|
||||
delete m_pTrans;
|
||||
delete m_pTransOut;
|
||||
delete[] m_pTransBuf;
|
||||
}
|
||||
|
||||
bool ImportOutFile::Set8bitTranslator(nsImportTranslator* pTrans) {
|
||||
if (!Flush()) return false;
|
||||
|
||||
m_engaged = false;
|
||||
m_pTrans = pTrans;
|
||||
m_supports8to7 = pTrans->Supports8bitEncoding();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ImportOutFile::End8bitTranslation(bool* pEngaged, nsCString& useCharset,
|
||||
nsCString& encoding) {
|
||||
if (!m_pTrans) return false;
|
||||
|
||||
bool bResult = Flush();
|
||||
if (m_supports8to7 && m_pTransOut) {
|
||||
if (bResult) bResult = m_pTrans->FinishConvertToFile(m_pTransOut);
|
||||
if (bResult) bResult = Flush();
|
||||
}
|
||||
|
||||
if (m_supports8to7) {
|
||||
m_pTrans->GetCharset(useCharset);
|
||||
m_pTrans->GetEncoding(encoding);
|
||||
} else
|
||||
useCharset.Truncate();
|
||||
*pEngaged = m_engaged;
|
||||
delete m_pTrans;
|
||||
m_pTrans = nullptr;
|
||||
delete m_pTransOut;
|
||||
m_pTransOut = nullptr;
|
||||
delete[] m_pTransBuf;
|
||||
m_pTransBuf = nullptr;
|
||||
|
||||
return bResult;
|
||||
}
|
||||
|
||||
bool ImportOutFile::InitOutFile(nsIFile* pFile, uint32_t bufSz) {
|
||||
if (!bufSz) bufSz = 32 * 1024;
|
||||
if (!m_pBuf) m_pBuf = new uint8_t[bufSz];
|
||||
|
||||
if (!m_outputStream) {
|
||||
nsresult rv;
|
||||
rv = MsgNewBufferedFileOutputStream(
|
||||
getter_AddRefs(m_outputStream), pFile,
|
||||
PR_CREATE_FILE | PR_WRONLY | PR_TRUNCATE, 0644);
|
||||
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("Couldn't create outfile\n");
|
||||
delete[] m_pBuf;
|
||||
m_pBuf = nullptr;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
m_pFile = pFile;
|
||||
m_ownsFileAndBuffer = true;
|
||||
m_pos = 0;
|
||||
m_bufSz = bufSz;
|
||||
return true;
|
||||
}
|
||||
|
||||
void ImportOutFile::InitOutFile(nsIFile* pFile, uint8_t* pBuf, uint32_t sz) {
|
||||
m_ownsFileAndBuffer = false;
|
||||
m_pFile = pFile;
|
||||
m_pBuf = pBuf;
|
||||
m_bufSz = sz;
|
||||
m_pos = 0;
|
||||
}
|
||||
|
||||
bool ImportOutFile::Flush(void) {
|
||||
if (!m_pos) return true;
|
||||
|
||||
uint32_t transLen;
|
||||
bool duddleyDoWrite = false;
|
||||
|
||||
// handle translations if appropriate
|
||||
if (m_pTrans) {
|
||||
if (m_engaged && m_supports8to7) {
|
||||
// Markers can get confused by this crap!!!
|
||||
// TLR: FIXME: Need to update the markers based on
|
||||
// the difference between the translated len and untranslated len
|
||||
|
||||
if (!m_pTrans->ConvertToFile(m_pBuf, m_pos, m_pTransOut, &transLen))
|
||||
return false;
|
||||
if (!m_pTransOut->Flush()) return false;
|
||||
// now update our buffer...
|
||||
if (transLen < m_pos) {
|
||||
memcpy(m_pBuf, m_pBuf + transLen, m_pos - transLen);
|
||||
}
|
||||
m_pos -= transLen;
|
||||
} else if (m_engaged) {
|
||||
// does not actually support translation!
|
||||
duddleyDoWrite = true;
|
||||
} else {
|
||||
// should we engage?
|
||||
uint8_t* pChar = m_pBuf;
|
||||
uint32_t len = m_pos;
|
||||
while (len) {
|
||||
if (!ImportCharSet::IsUSAscii(*pChar)) break;
|
||||
pChar++;
|
||||
len--;
|
||||
}
|
||||
if (len) {
|
||||
m_engaged = true;
|
||||
if (m_supports8to7) {
|
||||
// allocate our translation output buffer and file...
|
||||
m_pTransBuf = new uint8_t[m_bufSz];
|
||||
m_pTransOut = new ImportOutFile(m_pFile, m_pTransBuf, m_bufSz);
|
||||
return Flush();
|
||||
} else
|
||||
duddleyDoWrite = true;
|
||||
} else {
|
||||
duddleyDoWrite = true;
|
||||
}
|
||||
}
|
||||
} else
|
||||
duddleyDoWrite = true;
|
||||
|
||||
if (duddleyDoWrite) {
|
||||
uint32_t written = 0;
|
||||
nsresult rv =
|
||||
m_outputStream->Write((const char*)m_pBuf, (int32_t)m_pos, &written);
|
||||
if (NS_FAILED(rv) || ((uint32_t)written != m_pos)) return false;
|
||||
m_pos = 0;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ImportOutFile::WriteU8NullTerm(const uint8_t* pSrc, bool includeNull) {
|
||||
while (*pSrc) {
|
||||
if (m_pos >= m_bufSz) {
|
||||
if (!Flush()) return false;
|
||||
}
|
||||
*(m_pBuf + m_pos) = *pSrc;
|
||||
m_pos++;
|
||||
pSrc++;
|
||||
}
|
||||
if (includeNull) {
|
||||
if (m_pos >= m_bufSz) {
|
||||
if (!Flush()) return false;
|
||||
}
|
||||
*(m_pBuf + m_pos) = 0;
|
||||
m_pos++;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ImportOutFile::SetMarker(int markerID) {
|
||||
if (!Flush()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (markerID < kMaxMarkers) {
|
||||
int64_t pos = 0;
|
||||
if (m_outputStream) {
|
||||
// do we need to flush for the seek to give us the right pos?
|
||||
m_outputStream->Flush();
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsISeekableStream> seekStream =
|
||||
do_QueryInterface(m_outputStream, &rv);
|
||||
NS_ENSURE_SUCCESS(rv, false);
|
||||
rv = seekStream->Tell(&pos);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error, Tell failed on output stream\n");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
m_markers[markerID] = (uint32_t)pos + m_pos;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void ImportOutFile::ClearMarker(int markerID) {
|
||||
if (markerID < kMaxMarkers) m_markers[markerID] = 0;
|
||||
}
|
||||
|
||||
bool ImportOutFile::WriteStrAtMarker(int markerID, const char* pStr) {
|
||||
if (markerID >= kMaxMarkers) return false;
|
||||
|
||||
if (!Flush()) return false;
|
||||
int64_t pos;
|
||||
m_outputStream->Flush();
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsISeekableStream> seekStream =
|
||||
do_QueryInterface(m_outputStream, &rv);
|
||||
NS_ENSURE_SUCCESS(rv, false);
|
||||
rv = seekStream->Tell(&pos);
|
||||
if (NS_FAILED(rv)) return false;
|
||||
rv = seekStream->Seek(nsISeekableStream::NS_SEEK_SET,
|
||||
(int32_t)m_markers[markerID]);
|
||||
if (NS_FAILED(rv)) return false;
|
||||
uint32_t written;
|
||||
rv = m_outputStream->Write(pStr, strlen(pStr), &written);
|
||||
if (NS_FAILED(rv)) return false;
|
||||
|
||||
rv = seekStream->Seek(nsISeekableStream::NS_SEEK_SET, pos);
|
||||
if (NS_FAILED(rv)) return false;
|
||||
|
||||
return true;
|
||||
}
|
|
@ -1,94 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef ImportOutFile_h___
|
||||
#define ImportOutFile_h___
|
||||
|
||||
#include "nsImportTranslator.h"
|
||||
#include "nsIOutputStream.h"
|
||||
#include "nsIFile.h"
|
||||
|
||||
#define kMaxMarkers 10
|
||||
|
||||
class ImportOutFile;
|
||||
|
||||
class ImportOutFile {
|
||||
public:
|
||||
ImportOutFile();
|
||||
ImportOutFile(nsIFile* pFile, uint8_t* pBuf, uint32_t sz);
|
||||
~ImportOutFile();
|
||||
|
||||
bool InitOutFile(nsIFile* pFile, uint32_t bufSz = 4096);
|
||||
void InitOutFile(nsIFile* pFile, uint8_t* pBuf, uint32_t sz);
|
||||
inline bool WriteData(const uint8_t* pSrc, uint32_t len);
|
||||
inline bool WriteByte(uint8_t byte);
|
||||
bool WriteStr(const char* pStr) {
|
||||
return WriteU8NullTerm((const uint8_t*)pStr, false);
|
||||
}
|
||||
bool WriteU8NullTerm(const uint8_t* pSrc, bool includeNull);
|
||||
bool WriteEol(void) { return WriteStr("\x0D\x0A"); }
|
||||
bool Done(void) { return Flush(); }
|
||||
|
||||
// Marker support
|
||||
bool SetMarker(int markerID);
|
||||
void ClearMarker(int markerID);
|
||||
bool WriteStrAtMarker(int markerID, const char* pStr);
|
||||
|
||||
// 8-bit to 7-bit translation
|
||||
bool Set8bitTranslator(nsImportTranslator* pTrans);
|
||||
bool End8bitTranslation(bool* pEngaged, nsCString& useCharset,
|
||||
nsCString& encoding);
|
||||
|
||||
protected:
|
||||
bool Flush(void);
|
||||
|
||||
protected:
|
||||
nsCOMPtr<nsIFile> m_pFile;
|
||||
nsCOMPtr<nsIOutputStream> m_outputStream;
|
||||
uint8_t* m_pBuf;
|
||||
uint32_t m_bufSz;
|
||||
uint32_t m_pos;
|
||||
bool m_ownsFileAndBuffer;
|
||||
|
||||
// markers
|
||||
uint32_t m_markers[kMaxMarkers];
|
||||
|
||||
// 8 bit to 7 bit translations
|
||||
nsImportTranslator* m_pTrans;
|
||||
bool m_engaged;
|
||||
bool m_supports8to7;
|
||||
ImportOutFile* m_pTransOut;
|
||||
uint8_t* m_pTransBuf;
|
||||
};
|
||||
|
||||
inline bool ImportOutFile::WriteData(const uint8_t* pSrc, uint32_t len) {
|
||||
while ((len + m_pos) > m_bufSz) {
|
||||
if ((m_bufSz - m_pos)) {
|
||||
memcpy(m_pBuf + m_pos, pSrc, m_bufSz - m_pos);
|
||||
len -= (m_bufSz - m_pos);
|
||||
pSrc += (m_bufSz - m_pos);
|
||||
m_pos = m_bufSz;
|
||||
}
|
||||
if (!Flush()) return false;
|
||||
}
|
||||
|
||||
if (len) {
|
||||
memcpy(m_pBuf + m_pos, pSrc, len);
|
||||
m_pos += len;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
inline bool ImportOutFile::WriteByte(uint8_t byte) {
|
||||
if (m_pos == m_bufSz) {
|
||||
if (!Flush()) return false;
|
||||
}
|
||||
*(m_pBuf + m_pos) = byte;
|
||||
m_pos++;
|
||||
return true;
|
||||
}
|
||||
|
||||
#endif /* ImportOutFile_h__ */
|
|
@ -1,100 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "ImportTranslate.h"
|
||||
|
||||
int ImportTranslate::m_useTranslator = -1;
|
||||
|
||||
bool ImportTranslate::ConvertString(const nsCString& inStr, nsCString& outStr,
|
||||
bool mimeHeader) {
|
||||
if (inStr.IsEmpty()) {
|
||||
outStr = inStr;
|
||||
return true;
|
||||
}
|
||||
|
||||
nsImportTranslator* pTrans = GetTranslator();
|
||||
// int maxLen = (int) pTrans->GetMaxBufferSize(inStr.Length());
|
||||
// int hLen = 0;
|
||||
nsCString set;
|
||||
nsCString lang;
|
||||
|
||||
if (mimeHeader) {
|
||||
// add the charset and language
|
||||
pTrans->GetCharset(set);
|
||||
pTrans->GetLanguage(lang);
|
||||
}
|
||||
|
||||
// Unfortunately, we didn't implement ConvertBuffer for all translators,
|
||||
// just ConvertToFile. This means that this data will not always
|
||||
// be converted to the charset of pTrans. In that case...
|
||||
// We don't always have the data in the same charset as the current
|
||||
// translator...
|
||||
// It is safer to leave the charset and language field blank
|
||||
set.Truncate();
|
||||
lang.Truncate();
|
||||
|
||||
uint8_t* pBuf;
|
||||
/*
|
||||
pBuf = (P_U8) outStr.GetBuffer(maxLen);
|
||||
if (!pBuf) {
|
||||
delete pTrans;
|
||||
return FALSE;
|
||||
}
|
||||
pTrans->ConvertBuffer((PC_U8)(PC_S8)inStr, inStr.GetLength(), pBuf);
|
||||
outStr.ReleaseBuffer();
|
||||
*/
|
||||
outStr = inStr;
|
||||
delete pTrans;
|
||||
|
||||
// Now I need to run the string through the mime-header special char
|
||||
// encoder.
|
||||
|
||||
pTrans = new CMHTranslator;
|
||||
pBuf = new uint8_t[pTrans->GetMaxBufferSize(outStr.Length())];
|
||||
pTrans->ConvertBuffer((const uint8_t*)(outStr.get()), outStr.Length(), pBuf);
|
||||
delete pTrans;
|
||||
outStr.Truncate();
|
||||
if (mimeHeader) {
|
||||
outStr = set;
|
||||
outStr += "'";
|
||||
outStr += lang;
|
||||
outStr += "'";
|
||||
}
|
||||
outStr += (const char*)pBuf;
|
||||
delete[] pBuf;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
nsImportTranslator* ImportTranslate::GetTranslator(void) {
|
||||
if (m_useTranslator == -1) {
|
||||
// get the translator to use...
|
||||
// CString trans;
|
||||
// trans.LoadString(IDS_LANGUAGE_TRANSLATION);
|
||||
m_useTranslator = 0;
|
||||
// if (!trans.CompareNoCase("iso-2022-jp"))
|
||||
// gWizData.m_useTranslator = 1;
|
||||
}
|
||||
|
||||
switch (m_useTranslator) {
|
||||
case 0:
|
||||
return new nsImportTranslator;
|
||||
// case 1:
|
||||
// return new CSJis2JisTranslator;
|
||||
default:
|
||||
return new nsImportTranslator;
|
||||
}
|
||||
}
|
||||
|
||||
nsImportTranslator* ImportTranslate::GetMatchingTranslator(
|
||||
const char* pCharSet) {
|
||||
/*
|
||||
CString jp = "iso-2022-jp";
|
||||
if (!jp.CompareNoCase(pCharSet))
|
||||
return new CSJis2JisTranslator;
|
||||
*/
|
||||
|
||||
return nullptr;
|
||||
}
|
|
@ -1,23 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef ImportTranslate_h___
|
||||
#define ImportTranslate_h___
|
||||
|
||||
#include "nsString.h"
|
||||
#include "nsImportTranslator.h"
|
||||
|
||||
class ImportTranslate {
|
||||
public:
|
||||
static bool ConvertString(const nsCString& inStr, nsCString& outStr,
|
||||
bool mimeHeader);
|
||||
static nsImportTranslator* GetTranslator(void);
|
||||
static nsImportTranslator* GetMatchingTranslator(const char* pCharSet);
|
||||
|
||||
protected:
|
||||
static int m_useTranslator;
|
||||
};
|
||||
|
||||
#endif /* ImportTranslate_h__ */
|
|
@ -10,13 +10,6 @@
|
|||
|
||||
#include "MorkImport.h"
|
||||
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIImportService.h"
|
||||
#include "nsIImportGeneric.h"
|
||||
#include "nsIImportAddressBooks.h"
|
||||
#include "nsIImportABDescriptor.h"
|
||||
#include "nsIImportFieldMap.h"
|
||||
#include "nsImportStringBundle.h"
|
||||
#include "nsIComponentManager.h"
|
||||
#include "nsIAbDirectory.h"
|
||||
#include "nsAddrDatabase.h"
|
||||
|
@ -25,176 +18,6 @@
|
|||
|
||||
static const char kRowIDProperty[] = "DbRowID";
|
||||
|
||||
class MorkImportAddressImpl final : public nsIImportAddressBooks {
|
||||
public:
|
||||
explicit MorkImportAddressImpl(nsIStringBundle* aStringBundle);
|
||||
|
||||
static nsresult Create(nsIImportAddressBooks** aImport,
|
||||
nsIStringBundle* aStringBundle);
|
||||
|
||||
NS_DECL_THREADSAFE_ISUPPORTS
|
||||
NS_DECL_NSIIMPORTADDRESSBOOKS
|
||||
|
||||
private:
|
||||
~MorkImportAddressImpl() {}
|
||||
nsCOMPtr<nsIFile> mFileLocation;
|
||||
nsCOMPtr<nsIStringBundle> mStringBundle;
|
||||
};
|
||||
|
||||
MorkImport::MorkImport() {
|
||||
nsImportStringBundle::GetStringBundle(
|
||||
"chrome://messenger/locale/morkImportMsgs.properties",
|
||||
getter_AddRefs(mStringBundle));
|
||||
}
|
||||
|
||||
MorkImport::~MorkImport() {}
|
||||
|
||||
NS_IMPL_ISUPPORTS(MorkImport, nsIImportModule)
|
||||
|
||||
NS_IMETHODIMP MorkImport::GetImportInterface(const char* importType,
|
||||
nsISupports** interface) {
|
||||
NS_ENSURE_ARG_POINTER(importType);
|
||||
NS_ENSURE_ARG_POINTER(interface);
|
||||
|
||||
*interface = nullptr;
|
||||
nsresult rv;
|
||||
|
||||
if (strcmp(importType, "addressbook")) {
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIImportAddressBooks> pAddress;
|
||||
nsCOMPtr<nsIImportGeneric> pGeneric;
|
||||
rv = MorkImportAddressImpl::Create(getter_AddRefs(pAddress), mStringBundle);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
nsCOMPtr<nsIImportService> impSvc(
|
||||
do_GetService(NS_IMPORTSERVICE_CONTRACTID, &rv));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
rv = impSvc->CreateNewGenericAddressBooks(getter_AddRefs(pGeneric));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
pGeneric->SetData("addressInterface", pAddress);
|
||||
nsCOMPtr<nsISupports> pInterface(do_QueryInterface(pGeneric));
|
||||
pInterface.forget(interface);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
nsresult MorkImportAddressImpl::Create(nsIImportAddressBooks** aImport,
|
||||
nsIStringBundle* aStringBundle) {
|
||||
NS_ENSURE_ARG_POINTER(aImport);
|
||||
NS_ADDREF(*aImport = new MorkImportAddressImpl(aStringBundle));
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
MorkImportAddressImpl::MorkImportAddressImpl(nsIStringBundle* aStringBundle)
|
||||
: mStringBundle(aStringBundle) {}
|
||||
|
||||
NS_IMPL_ISUPPORTS(MorkImportAddressImpl, nsIImportAddressBooks)
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::GetSupportsMultiple(bool* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
*_retval = false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::GetAutoFind(char16_t** addrDescription,
|
||||
bool* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(addrDescription);
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
*_retval = false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::GetNeedsFieldMap(nsIFile* aLocation,
|
||||
bool* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
*_retval = false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::GetDefaultLocation(nsIFile** ppLoc,
|
||||
bool* found,
|
||||
bool* userVerify) {
|
||||
NS_ENSURE_ARG_POINTER(ppLoc);
|
||||
NS_ENSURE_ARG_POINTER(found);
|
||||
NS_ENSURE_ARG_POINTER(userVerify);
|
||||
|
||||
*ppLoc = nullptr;
|
||||
*found = false;
|
||||
*userVerify = true;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::FindAddressBooks(
|
||||
nsIFile* pLoc, nsTArray<RefPtr<nsIImportABDescriptor>>& books) {
|
||||
NS_ENSURE_ARG_POINTER(pLoc);
|
||||
|
||||
books.Clear();
|
||||
bool exists = false;
|
||||
nsresult rv = pLoc->Exists(&exists);
|
||||
if (NS_FAILED(rv) || !exists) return NS_ERROR_FAILURE;
|
||||
|
||||
bool isFile = false;
|
||||
rv = pLoc->IsFile(&isFile);
|
||||
if (NS_FAILED(rv) || !isFile) return NS_ERROR_FAILURE;
|
||||
|
||||
mFileLocation = pLoc;
|
||||
|
||||
/* Build an address book descriptor based on the file passed in! */
|
||||
nsString name;
|
||||
rv = mFileLocation->GetLeafName(name);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
int32_t idx = name.RFindChar('.');
|
||||
if ((idx != -1) && (idx > 0) && ((name.Length() - idx - 1) < 5)) {
|
||||
name.SetLength(idx);
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIImportABDescriptor> desc;
|
||||
|
||||
nsCOMPtr<nsIImportService> impSvc(
|
||||
do_GetService(NS_IMPORTSERVICE_CONTRACTID, &rv));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
rv = impSvc->CreateNewABDescriptor(getter_AddRefs(desc));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
int64_t sz = 0;
|
||||
pLoc->GetFileSize(&sz);
|
||||
desc->SetPreferredName(name);
|
||||
desc->SetSize((uint32_t)sz);
|
||||
desc->SetAbFile(mFileLocation);
|
||||
books.AppendElement(desc);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::InitFieldMap(nsIImportFieldMap* fieldMap) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
MorkImportAddressImpl::ImportAddressBook(
|
||||
nsIImportABDescriptor* pSource, nsIAbDirectory* pDestination,
|
||||
nsIImportFieldMap* fieldMap, nsISupports* aSupportService,
|
||||
char16_t** pErrorLog, char16_t** pSuccessLog, bool* fatalError) {
|
||||
NS_ENSURE_ARG_POINTER(pSource);
|
||||
NS_ENSURE_ARG_POINTER(pDestination);
|
||||
NS_ENSURE_ARG_POINTER(fatalError);
|
||||
|
||||
nsCOMPtr<nsIFile> oldFile;
|
||||
pSource->GetAbFile(getter_AddRefs(oldFile));
|
||||
|
||||
nsresult rv = ReadMABToDirectory(oldFile, pDestination);
|
||||
|
||||
*pSuccessLog =
|
||||
nsImportStringBundle::GetStringByName("morkImportSuccess", mStringBundle);
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsresult ReadMABToDirectory(nsIFile* oldFile, nsIAbDirectory* newDirectory) {
|
||||
nsresult rv;
|
||||
|
||||
|
@ -290,22 +113,6 @@ nsresult ReadMABToDirectory(nsIFile* oldFile, nsIAbDirectory* newDirectory) {
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::GetImportProgress(uint32_t* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
*_retval = 0;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::SetSampleLocation(nsIFile* pLocation) {
|
||||
NS_ENSURE_ARG_POINTER(pLocation);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP MorkImportAddressImpl::GetSampleData(int32_t index, bool* pFound,
|
||||
char16_t** pStr) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMPL_ISUPPORTS(nsImportABFromMab, nsIImportABFile)
|
||||
|
||||
nsImportABFromMab::nsImportABFromMab() {}
|
||||
|
|
|
@ -8,20 +8,9 @@
|
|||
#define MorkImport_h___
|
||||
|
||||
#include "nsIImportABFile.h"
|
||||
#include "nsIImportModule.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIStringBundle.h"
|
||||
|
||||
#include "nsIFile.h"
|
||||
#include "nsIAbDirectory.h"
|
||||
|
||||
#define MORKIMPORT_CID \
|
||||
{ /* 54d48d9f-1bac-47be-9190-c4dc74e837e2 */ \
|
||||
0x54d48d9f, 0x1bac, 0x47be, { \
|
||||
0x91, 0x90, 0xc4, 0xdc, 0x74, 0xe8, 0x37, 0xe2 \
|
||||
} \
|
||||
}
|
||||
|
||||
nsresult ReadMABToDirectory(nsIFile* oldFile, nsIAbDirectory* newDirectory);
|
||||
|
||||
class nsImportABFromMab : public nsIImportABFile {
|
||||
|
@ -32,19 +21,7 @@ class nsImportABFromMab : public nsIImportABFile {
|
|||
NS_DECL_NSIIMPORTABFILE
|
||||
|
||||
protected:
|
||||
virtual ~nsImportABFromMab(){};
|
||||
};
|
||||
|
||||
class MorkImport : public nsIImportModule {
|
||||
public:
|
||||
MorkImport();
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIIMPORTMODULE
|
||||
|
||||
protected:
|
||||
virtual ~MorkImport();
|
||||
nsCOMPtr<nsIStringBundle> mStringBundle;
|
||||
virtual ~nsImportABFromMab() {};
|
||||
};
|
||||
|
||||
#endif /* MorkImport_h___ */
|
||||
|
|
|
@ -31,24 +31,6 @@ Classes = [
|
|||
"name": "Import",
|
||||
"interfaces": ["nsIImportService"],
|
||||
},
|
||||
{
|
||||
"cid": "{a5991d01-ada7-11d3-a9c2-00a0cc26da63}",
|
||||
"contract_ids": ["@mozilla.org/import/import-text;1"],
|
||||
"type": "nsTextImport",
|
||||
"headers": ["/comm/mailnews/import/src/nsTextImport.h"],
|
||||
},
|
||||
{
|
||||
"cid": "{0eb034a3-964a-4e2f-92ebcc55d9ae9dd2}",
|
||||
"contract_ids": ["@mozilla.org/import/import-vcard;1"],
|
||||
"type": "nsVCardImport",
|
||||
"headers": ["/comm/mailnews/import/src/nsVCardImport.h"],
|
||||
},
|
||||
{
|
||||
"cid": "{54d48d9f-1bac-47be-9190-c4dc74e837e2}",
|
||||
"contract_ids": ["@mozilla.org/import/import-mork;1"],
|
||||
"type": "MorkImport",
|
||||
"headers": ["/comm/mailnews/import/src/MorkImport.h"],
|
||||
},
|
||||
]
|
||||
|
||||
if buildconfig.substs["OS_ARCH"] == "Darwin":
|
||||
|
|
|
@ -4,26 +4,17 @@
|
|||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
SOURCES += [
|
||||
"ImportCharSet.cpp",
|
||||
"ImportOutFile.cpp",
|
||||
"ImportTranslate.cpp",
|
||||
"MorkImport.cpp",
|
||||
"nsAddrDatabase.cpp",
|
||||
"nsImportABDescriptor.cpp",
|
||||
"nsImportAddressBooks.cpp",
|
||||
"nsImportEmbeddedImageData.cpp",
|
||||
"nsImportEncodeScan.cpp",
|
||||
"nsImportFieldMap.cpp",
|
||||
"nsImportMail.cpp",
|
||||
"nsImportMailboxDescriptor.cpp",
|
||||
"nsImportScanFile.cpp",
|
||||
"nsImportService.cpp",
|
||||
"nsImportStringBundle.cpp",
|
||||
"nsImportTranslator.cpp",
|
||||
"nsTextAddress.cpp",
|
||||
"nsTextImport.cpp",
|
||||
"nsVCardAddress.cpp",
|
||||
"nsVCardImport.cpp",
|
||||
]
|
||||
|
||||
if not CONFIG["MOZ_SUITE"]:
|
||||
|
|
|
@ -1,334 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nscore.h"
|
||||
#include "nsImportEncodeScan.h"
|
||||
#include "nsNetUtil.h"
|
||||
|
||||
#define kBeginAppleSingle 0
|
||||
#define kBeginDataFork 1
|
||||
#define kBeginResourceFork 2
|
||||
#define kAddEntries 3
|
||||
#define kScanningDataFork 4
|
||||
#define kScanningRsrcFork 5
|
||||
#define kDoneWithFile 6
|
||||
|
||||
uint32_t gAppleSingleHeader[6] = {0x00051600, 0x00020000, 0, 0, 0, 0};
|
||||
#define kAppleSingleHeaderSize (6 * sizeof(uint32_t))
|
||||
|
||||
#ifdef _MAC_IMPORT_CODE
|
||||
# include "MoreDesktopMgr.h"
|
||||
|
||||
CInfoPBRec gCatInfoPB;
|
||||
U32 g2000Secs = 0;
|
||||
long gGMTDelta = 0;
|
||||
|
||||
long GetGmtDelta(void);
|
||||
U32 Get2000Secs(void);
|
||||
|
||||
long GetGmtDelta(void) {
|
||||
MachineLocation myLocation;
|
||||
ReadLocation(&myLocation);
|
||||
long myDelta = BitAnd(myLocation.u.gmtDelta, 0x00FFFFFF);
|
||||
if (BitTst(&myDelta, 23)) myDelta = BitOr(myDelta, 0xFF000000);
|
||||
return myDelta;
|
||||
}
|
||||
|
||||
U32 Get2000Secs(void) {
|
||||
DateTimeRec dr;
|
||||
dr.year = 2000;
|
||||
dr.month = 1;
|
||||
dr.day = 1;
|
||||
dr.hour = 0;
|
||||
dr.minute = 0;
|
||||
dr.second = 0;
|
||||
dr.dayOfWeek = 0;
|
||||
U32 result;
|
||||
DateToSeconds(&dr, &result);
|
||||
return result;
|
||||
}
|
||||
#endif
|
||||
|
||||
nsImportEncodeScan::nsImportEncodeScan() {
|
||||
m_isAppleSingle = false;
|
||||
m_encodeScanState = 0;
|
||||
m_resourceForkSize = 0;
|
||||
m_dataForkSize = 0;
|
||||
}
|
||||
|
||||
nsImportEncodeScan::~nsImportEncodeScan() {}
|
||||
|
||||
bool nsImportEncodeScan::InitEncodeScan(bool appleSingleEncode,
|
||||
nsIFile* fileLoc, const char* pName,
|
||||
uint8_t* pBuf, uint32_t sz) {
|
||||
CleanUpEncodeScan();
|
||||
m_isAppleSingle = appleSingleEncode;
|
||||
m_encodeScanState = kBeginAppleSingle;
|
||||
m_pInputFile = fileLoc;
|
||||
m_useFileName = pName;
|
||||
m_pBuf = pBuf;
|
||||
m_bufSz = sz;
|
||||
if (!m_isAppleSingle) {
|
||||
if (!m_inputStream) {
|
||||
nsresult rv = NS_NewLocalFileInputStream(getter_AddRefs(m_inputStream),
|
||||
m_pInputFile);
|
||||
NS_ENSURE_SUCCESS(rv, false);
|
||||
}
|
||||
|
||||
InitScan(m_inputStream, pBuf, sz);
|
||||
} else {
|
||||
#ifdef _MAC_IMPORT_CODE
|
||||
// Fill in the file sizes
|
||||
m_resourceForkSize = fileLoc.GetMacFileSize(UFileLocation::eResourceFork);
|
||||
m_dataForkSize = fileLoc.GetMacFileSize(UFileLocation::eDataFork);
|
||||
#endif
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void nsImportEncodeScan::CleanUpEncodeScan(void) {
|
||||
m_pInputStream->Close();
|
||||
m_pInputStream = nullptr;
|
||||
m_pInputFile = nullptr;
|
||||
}
|
||||
|
||||
// 26 + 12 per entry
|
||||
|
||||
void nsImportEncodeScan::FillInEntries(int numEntries) {
|
||||
#ifdef _MAC_IMPORT_CODE
|
||||
int len = m_useFileName.GetLength();
|
||||
if (len < 32) len = 32;
|
||||
long entry[3];
|
||||
long fileOffset = 26 + (12 * numEntries);
|
||||
entry[0] = 3;
|
||||
entry[1] = fileOffset;
|
||||
entry[2] = m_useFileName.GetLength();
|
||||
fileOffset += len;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, entry, 12);
|
||||
m_bytesInBuf += 12;
|
||||
|
||||
Str255 comment;
|
||||
comment[0] = 0;
|
||||
OSErr err = FSpDTGetComment(m_inputFileLoc, comment);
|
||||
if (comment[0] > 200) comment[0] = 200;
|
||||
entry[0] = 4;
|
||||
entry[1] = fileOffset;
|
||||
entry[2] = comment[0];
|
||||
fileOffset += 200;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, entry, 12);
|
||||
m_bytesInBuf += 12;
|
||||
|
||||
entry[0] = 8;
|
||||
entry[1] = fileOffset;
|
||||
entry[2] = 16;
|
||||
fileOffset += 16;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, entry, 12);
|
||||
m_bytesInBuf += 12;
|
||||
|
||||
entry[0] = 9;
|
||||
entry[1] = fileOffset;
|
||||
entry[2] = 32;
|
||||
fileOffset += 32;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, entry, 12);
|
||||
m_bytesInBuf += 12;
|
||||
|
||||
entry[0] = 10;
|
||||
entry[1] = fileOffset;
|
||||
entry[2] = 4;
|
||||
fileOffset += 4;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, entry, 12);
|
||||
m_bytesInBuf += 12;
|
||||
|
||||
if (m_resourceForkSize) {
|
||||
entry[0] = 2;
|
||||
entry[1] = fileOffset;
|
||||
entry[2] = m_resourceForkSize;
|
||||
fileOffset += m_resourceForkSize;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, entry, 12);
|
||||
m_bytesInBuf += 12;
|
||||
}
|
||||
|
||||
if (m_dataForkSize) {
|
||||
entry[0] = 1;
|
||||
entry[1] = fileOffset;
|
||||
entry[2] = m_dataForkSize;
|
||||
fileOffset += m_dataForkSize;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, entry, 12);
|
||||
m_bytesInBuf += 12;
|
||||
}
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
bool nsImportEncodeScan::AddEntries(void) {
|
||||
#ifdef _MAC_IMPORT_CODE
|
||||
if (!g2000Secs) {
|
||||
g2000Secs = Get2000Secs();
|
||||
gGMTDelta = GetGmtDelta();
|
||||
}
|
||||
MemCpy(m_pBuf + m_bytesInBuf, (PC_S8)m_useFileName,
|
||||
m_useFileName.GetLength());
|
||||
m_bytesInBuf += m_useFileName.GetLength();
|
||||
if (m_useFileName.GetLength() < 32) {
|
||||
int len = m_useFileName.GetLength();
|
||||
while (len < 32) {
|
||||
*((P_S8)m_pBuf + m_bytesInBuf) = 0;
|
||||
m_bytesInBuf++;
|
||||
len++;
|
||||
}
|
||||
}
|
||||
|
||||
Str255 comment;
|
||||
comment[0] = 0;
|
||||
OSErr err = FSpDTGetComment(m_inputFileLoc, comment);
|
||||
comment[0] = 200;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, &(comment[1]), comment[0]);
|
||||
m_bytesInBuf += comment[0];
|
||||
|
||||
long dates[4];
|
||||
dates[0] = gCatInfoPB.hFileInfo.ioFlCrDat;
|
||||
dates[1] = gCatInfoPB.hFileInfo.ioFlMdDat;
|
||||
dates[2] = gCatInfoPB.hFileInfo.ioFlBkDat;
|
||||
dates[3] = 0x80000000;
|
||||
for (short i = 0; i < 3; i++) {
|
||||
dates[i] -= g2000Secs;
|
||||
dates[i] += gGMTDelta;
|
||||
}
|
||||
MemCpy(m_pBuf + m_bytesInBuf, dates, 16);
|
||||
m_bytesInBuf += 16;
|
||||
|
||||
FInfo fInfo = gCatInfoPB.hFileInfo.ioFlFndrInfo;
|
||||
FXInfo fxInfo = gCatInfoPB.hFileInfo.ioFlXFndrInfo;
|
||||
fInfo.fdFlags = 0;
|
||||
fInfo.fdLocation.h = 0;
|
||||
fInfo.fdLocation.v = 0;
|
||||
fInfo.fdFldr = 0;
|
||||
MemSet(&fxInfo, 0, sizeof(fxInfo));
|
||||
MemCpy(m_pBuf + m_bytesInBuf, &fInfo, 16);
|
||||
m_bytesInBuf += 16;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, &fxInfo, 16);
|
||||
m_bytesInBuf += 16;
|
||||
|
||||
dates[0] = 0;
|
||||
if ((gCatInfoPB.hFileInfo.ioFlAttrib & 1) != 0) dates[0] |= 1;
|
||||
MemCpy(m_pBuf + m_bytesInBuf, dates, 4);
|
||||
m_bytesInBuf += 4;
|
||||
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
||||
bool nsImportEncodeScan::Scan(bool* pDone) {
|
||||
nsresult rv;
|
||||
|
||||
*pDone = false;
|
||||
if (m_isAppleSingle) {
|
||||
// Stuff the buffer with things needed to encode the file...
|
||||
// then just allow UScanFile to handle each fork, but be careful
|
||||
// when handling eof.
|
||||
switch (m_encodeScanState) {
|
||||
case kBeginAppleSingle: {
|
||||
#ifdef _MAC_IMPORT_CODE
|
||||
OSErr err = GetCatInfoNoName(
|
||||
m_inputFileLoc.GetVRefNum(), m_inputFileLoc.GetParID(),
|
||||
m_inputFileLoc.GetFileNamePtr(), &gCatInfoPB);
|
||||
if (err != noErr) return FALSE;
|
||||
#endif
|
||||
m_eof = false;
|
||||
m_pos = 0;
|
||||
memcpy(m_pBuf, gAppleSingleHeader, kAppleSingleHeaderSize);
|
||||
m_bytesInBuf = kAppleSingleHeaderSize;
|
||||
int numEntries = 5;
|
||||
if (m_dataForkSize) numEntries++;
|
||||
if (m_resourceForkSize) numEntries++;
|
||||
memcpy(m_pBuf + m_bytesInBuf, &numEntries, sizeof(numEntries));
|
||||
m_bytesInBuf += sizeof(numEntries);
|
||||
FillInEntries(numEntries);
|
||||
m_encodeScanState = kAddEntries;
|
||||
return ScanBuffer(pDone);
|
||||
} break;
|
||||
|
||||
case kBeginDataFork: {
|
||||
if (!m_dataForkSize) {
|
||||
m_encodeScanState = kDoneWithFile;
|
||||
return true;
|
||||
}
|
||||
// Initialize the scan of the data fork...
|
||||
if (!m_inputStream) {
|
||||
rv = NS_NewLocalFileInputStream(getter_AddRefs(m_inputStream),
|
||||
m_pInputFile);
|
||||
NS_ENSURE_SUCCESS(rv, false);
|
||||
}
|
||||
m_encodeScanState = kScanningDataFork;
|
||||
return true;
|
||||
} break;
|
||||
|
||||
case kScanningDataFork: {
|
||||
bool result = FillBufferFromFile();
|
||||
if (!result) return false;
|
||||
if (m_eof) {
|
||||
m_eof = false;
|
||||
result = ScanBuffer(pDone);
|
||||
if (!result) return false;
|
||||
m_inputStream->Close();
|
||||
m_inputStream = nullptr;
|
||||
m_encodeScanState = kDoneWithFile;
|
||||
return true;
|
||||
} else
|
||||
return ScanBuffer(pDone);
|
||||
} break;
|
||||
|
||||
case kScanningRsrcFork: {
|
||||
bool result = FillBufferFromFile();
|
||||
if (!result) return false;
|
||||
if (m_eof) {
|
||||
m_eof = false;
|
||||
result = ScanBuffer(pDone);
|
||||
if (!result) return false;
|
||||
m_inputStream->Close();
|
||||
m_inputStream = nullptr;
|
||||
m_encodeScanState = kBeginDataFork;
|
||||
return true;
|
||||
} else
|
||||
return ScanBuffer(pDone);
|
||||
} break;
|
||||
|
||||
case kBeginResourceFork: {
|
||||
if (!m_resourceForkSize) {
|
||||
m_encodeScanState = kBeginDataFork;
|
||||
return true;
|
||||
}
|
||||
/*
|
||||
// FIXME: Open the resource fork on the Mac!!!
|
||||
m_fH = UFile::OpenRsrcFileRead(m_inputFileLoc);
|
||||
if (m_fH == TR_FILE_ERROR)
|
||||
return FALSE;
|
||||
*/
|
||||
m_encodeScanState = kScanningRsrcFork;
|
||||
return true;
|
||||
} break;
|
||||
|
||||
case kAddEntries: {
|
||||
ShiftBuffer();
|
||||
if (!AddEntries()) return false;
|
||||
m_encodeScanState = kBeginResourceFork;
|
||||
return ScanBuffer(pDone);
|
||||
} break;
|
||||
|
||||
case kDoneWithFile: {
|
||||
ShiftBuffer();
|
||||
m_eof = true;
|
||||
if (!ScanBuffer(pDone)) return false;
|
||||
*pDone = true;
|
||||
return true;
|
||||
} break;
|
||||
}
|
||||
|
||||
} else
|
||||
return nsImportScanFile::Scan(pDone);
|
||||
|
||||
return false;
|
||||
}
|
|
@ -1,39 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsImportEncodeScan_h___
|
||||
#define nsImportEncodeScan_h___
|
||||
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "nsIFile.h"
|
||||
#include "nsImportScanFile.h"
|
||||
#include "nsString.h"
|
||||
|
||||
class nsImportEncodeScan : public nsImportScanFile {
|
||||
public:
|
||||
nsImportEncodeScan();
|
||||
~nsImportEncodeScan();
|
||||
|
||||
bool InitEncodeScan(bool appleSingleEncode, nsIFile* pFile, const char* pName,
|
||||
uint8_t* pBuf, uint32_t sz);
|
||||
void CleanUpEncodeScan(void);
|
||||
|
||||
virtual bool Scan(bool* pDone) override;
|
||||
|
||||
protected:
|
||||
void FillInEntries(int numEntries);
|
||||
bool AddEntries(void);
|
||||
|
||||
protected:
|
||||
bool m_isAppleSingle;
|
||||
nsCOMPtr<nsIFile> m_pInputFile;
|
||||
nsCOMPtr<nsIInputStream> m_inputStream;
|
||||
int m_encodeScanState;
|
||||
long m_resourceForkSize;
|
||||
long m_dataForkSize;
|
||||
nsCString m_useFileName;
|
||||
};
|
||||
|
||||
#endif /* nsImportEncodeScan_h__ */
|
|
@ -1,154 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nscore.h"
|
||||
#include "nsImportScanFile.h"
|
||||
#include "ImportCharSet.h"
|
||||
|
||||
nsImportScanFile::nsImportScanFile() {
|
||||
m_allocated = false;
|
||||
m_eof = false;
|
||||
m_pBuf = nullptr;
|
||||
}
|
||||
|
||||
nsImportScanFile::~nsImportScanFile() {
|
||||
if (m_allocated) CleanUpScan();
|
||||
}
|
||||
|
||||
void nsImportScanFile::InitScan(nsIInputStream* pInputStream, uint8_t* pBuf,
|
||||
uint32_t sz) {
|
||||
m_pInputStream = pInputStream;
|
||||
m_pBuf = pBuf;
|
||||
m_bufSz = sz;
|
||||
m_bytesInBuf = 0;
|
||||
m_pos = 0;
|
||||
}
|
||||
|
||||
void nsImportScanFile::CleanUpScan(void) {
|
||||
m_pInputStream = nullptr;
|
||||
if (m_allocated) {
|
||||
delete[] m_pBuf;
|
||||
m_pBuf = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
void nsImportScanFile::ShiftBuffer(void) {
|
||||
uint8_t* pTop;
|
||||
uint8_t* pCurrent;
|
||||
|
||||
if (m_pos < m_bytesInBuf) {
|
||||
pTop = m_pBuf;
|
||||
pCurrent = pTop + m_pos;
|
||||
uint32_t cnt = m_bytesInBuf - m_pos;
|
||||
while (cnt) {
|
||||
*pTop = *pCurrent;
|
||||
pTop++;
|
||||
pCurrent++;
|
||||
cnt--;
|
||||
}
|
||||
}
|
||||
|
||||
m_bytesInBuf -= m_pos;
|
||||
m_pos = 0;
|
||||
}
|
||||
|
||||
bool nsImportScanFile::FillBufferFromFile(void) {
|
||||
uint64_t available;
|
||||
nsresult rv = m_pInputStream->Available(&available);
|
||||
if (NS_FAILED(rv)) return false;
|
||||
|
||||
// Fill up a buffer and scan it
|
||||
ShiftBuffer();
|
||||
|
||||
// Read in some more bytes
|
||||
uint32_t cnt = m_bufSz - m_bytesInBuf;
|
||||
// To distinguish from disk errors
|
||||
// Check first for end of file?
|
||||
// Set a done flag if true...
|
||||
uint32_t read;
|
||||
char* pBuf = (char*)m_pBuf;
|
||||
pBuf += m_bytesInBuf;
|
||||
rv = m_pInputStream->Read(pBuf, (int32_t)cnt, &read);
|
||||
|
||||
if (NS_FAILED(rv)) return false;
|
||||
rv = m_pInputStream->Available(&available);
|
||||
if (NS_FAILED(rv)) m_eof = true;
|
||||
|
||||
m_bytesInBuf += cnt;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool nsImportScanFile::Scan(bool* pDone) {
|
||||
uint64_t available;
|
||||
nsresult rv = m_pInputStream->Available(&available);
|
||||
if (NS_FAILED(rv)) {
|
||||
if (m_pos < m_bytesInBuf) ScanBuffer(pDone);
|
||||
*pDone = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Fill up a buffer and scan it
|
||||
if (!FillBufferFromFile()) return false;
|
||||
|
||||
return ScanBuffer(pDone);
|
||||
}
|
||||
|
||||
bool nsImportScanFile::ScanBuffer(bool*) { return true; }
|
||||
|
||||
bool nsImportScanFileLines::ScanBuffer(bool* pDone) {
|
||||
// m_pos, m_bytesInBuf, m_eof, m_pBuf are relevant
|
||||
|
||||
uint32_t pos = m_pos;
|
||||
uint32_t max = m_bytesInBuf;
|
||||
uint8_t* pChar = m_pBuf + pos;
|
||||
uint32_t startPos;
|
||||
|
||||
while (pos < max) {
|
||||
if (m_needEol) {
|
||||
// Find the next eol...
|
||||
while ((pos < max) && (*pChar != ImportCharSet::cCRChar) &&
|
||||
(*pChar != ImportCharSet::cLinefeedChar)) {
|
||||
pos++;
|
||||
pChar++;
|
||||
}
|
||||
m_pos = pos;
|
||||
if (pos < max) m_needEol = false;
|
||||
if (pos == max) // need more buffer for an end of line
|
||||
break;
|
||||
}
|
||||
// Skip past any eol characters
|
||||
while ((pos < max) && ((*pChar == ImportCharSet::cCRChar) ||
|
||||
(*pChar == ImportCharSet::cLinefeedChar))) {
|
||||
pos++;
|
||||
pChar++;
|
||||
}
|
||||
m_pos = pos;
|
||||
if (pos == max) break;
|
||||
// Make sure we can find either the eof or the
|
||||
// next end of line
|
||||
startPos = pos;
|
||||
while ((pos < max) && (*pChar != ImportCharSet::cCRChar) &&
|
||||
(*pChar != ImportCharSet::cLinefeedChar)) {
|
||||
pos++;
|
||||
pChar++;
|
||||
}
|
||||
|
||||
// Is line too big for our buffer?
|
||||
if ((pos == max) && !m_eof) {
|
||||
if (!m_pos) { // line too big for our buffer
|
||||
m_pos = pos;
|
||||
m_needEol = true;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (!ProcessLine(m_pBuf + startPos, pos - startPos, pDone)) {
|
||||
return false;
|
||||
}
|
||||
m_pos = pos;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
|
@ -1,56 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsImportScanFile_h__
|
||||
#define nsImportScanFile_h__
|
||||
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIInputStream.h"
|
||||
|
||||
class nsImportScanFile {
|
||||
public:
|
||||
nsImportScanFile();
|
||||
virtual ~nsImportScanFile();
|
||||
|
||||
void InitScan(nsIInputStream* pInputStream, uint8_t* pBuf, uint32_t sz);
|
||||
|
||||
void CleanUpScan(void);
|
||||
|
||||
virtual bool Scan(bool* pDone);
|
||||
|
||||
protected:
|
||||
void ShiftBuffer(void);
|
||||
bool FillBufferFromFile(void);
|
||||
virtual bool ScanBuffer(bool* pDone);
|
||||
|
||||
protected:
|
||||
nsCOMPtr<nsIInputStream> m_pInputStream;
|
||||
uint8_t* m_pBuf;
|
||||
uint32_t m_bufSz;
|
||||
uint32_t m_bytesInBuf;
|
||||
uint32_t m_pos;
|
||||
bool m_eof;
|
||||
bool m_allocated;
|
||||
};
|
||||
|
||||
class nsImportScanFileLines : public nsImportScanFile {
|
||||
public:
|
||||
nsImportScanFileLines() { m_needEol = false; }
|
||||
|
||||
void ResetLineScan(void) { m_needEol = false; }
|
||||
|
||||
virtual bool ProcessLine(uint8_t* /* pLine */, uint32_t /* len */,
|
||||
bool* /* pDone */) {
|
||||
return true;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual bool ScanBuffer(bool* pDone) override;
|
||||
|
||||
bool m_needEol;
|
||||
};
|
||||
|
||||
#endif /* nsImportScanFile_h__ */
|
|
@ -1,308 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "ImportOutFile.h"
|
||||
#include "nsImportTranslator.h"
|
||||
|
||||
#include "ImportCharSet.h"
|
||||
|
||||
bool nsImportTranslator::ConvertToFile(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile,
|
||||
uint32_t* pProcessed) {
|
||||
if (pProcessed) *pProcessed = inLen;
|
||||
return (pOutFile->WriteData(pIn, inLen));
|
||||
}
|
||||
|
||||
void CMHTranslator::ConvertBuffer(const uint8_t* pIn, uint32_t inLen,
|
||||
uint8_t* pOut) {
|
||||
while (inLen) {
|
||||
if (!ImportCharSet::IsUSAscii(*pIn) ||
|
||||
ImportCharSet::Is822SpecialChar(*pIn) ||
|
||||
ImportCharSet::Is822CtlChar(*pIn) ||
|
||||
(*pIn == ImportCharSet::cSpaceChar) || (*pIn == '*') ||
|
||||
(*pIn == '\'') || (*pIn == '%')) {
|
||||
// needs to be encode as %hex val
|
||||
*pOut = '%';
|
||||
pOut++;
|
||||
ImportCharSet::ByteToHex(*pIn, pOut);
|
||||
pOut += 2;
|
||||
} else {
|
||||
*pOut = *pIn;
|
||||
pOut++;
|
||||
}
|
||||
pIn++;
|
||||
inLen--;
|
||||
}
|
||||
*pOut = 0;
|
||||
}
|
||||
|
||||
bool CMHTranslator::ConvertToFile(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile,
|
||||
uint32_t* pProcessed) {
|
||||
uint8_t hex[2];
|
||||
while (inLen) {
|
||||
if (!ImportCharSet::IsUSAscii(*pIn) ||
|
||||
ImportCharSet::Is822SpecialChar(*pIn) ||
|
||||
ImportCharSet::Is822CtlChar(*pIn) ||
|
||||
(*pIn == ImportCharSet::cSpaceChar) || (*pIn == '*') ||
|
||||
(*pIn == '\'') || (*pIn == '%')) {
|
||||
// needs to be encode as %hex val
|
||||
if (!pOutFile->WriteByte('%')) return false;
|
||||
ImportCharSet::ByteToHex(*pIn, hex);
|
||||
if (!pOutFile->WriteData(hex, 2)) return false;
|
||||
} else {
|
||||
if (!pOutFile->WriteByte(*pIn)) return false;
|
||||
}
|
||||
pIn++;
|
||||
inLen--;
|
||||
}
|
||||
|
||||
if (pProcessed) *pProcessed = inLen;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool C2047Translator::ConvertToFileQ(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile,
|
||||
uint32_t* pProcessed) {
|
||||
if (!inLen) return true;
|
||||
|
||||
int maxLineLen = 64;
|
||||
int curLineLen = m_startLen;
|
||||
bool startLine = true;
|
||||
|
||||
uint8_t hex[2];
|
||||
while (inLen) {
|
||||
if (startLine) {
|
||||
if (!pOutFile->WriteStr(" =?")) return false;
|
||||
if (!pOutFile->WriteStr(m_charset.get())) return false;
|
||||
if (!pOutFile->WriteStr("?q?")) return false;
|
||||
curLineLen += (6 + m_charset.Length());
|
||||
startLine = false;
|
||||
}
|
||||
|
||||
if (!ImportCharSet::IsUSAscii(*pIn) ||
|
||||
ImportCharSet::Is822SpecialChar(*pIn) ||
|
||||
ImportCharSet::Is822CtlChar(*pIn) ||
|
||||
(*pIn == ImportCharSet::cSpaceChar) || (*pIn == '?') || (*pIn == '=')) {
|
||||
// needs to be encode as =hex val
|
||||
if (!pOutFile->WriteByte('=')) return false;
|
||||
ImportCharSet::ByteToHex(*pIn, hex);
|
||||
if (!pOutFile->WriteData(hex, 2)) return false;
|
||||
curLineLen += 3;
|
||||
} else {
|
||||
if (!pOutFile->WriteByte(*pIn)) return false;
|
||||
curLineLen++;
|
||||
}
|
||||
pIn++;
|
||||
inLen--;
|
||||
if (curLineLen > maxLineLen) {
|
||||
if (!pOutFile->WriteStr("?=")) return false;
|
||||
if (inLen) {
|
||||
if (!pOutFile->WriteStr("\x0D\x0A ")) return false;
|
||||
}
|
||||
|
||||
startLine = true;
|
||||
curLineLen = 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (!startLine) {
|
||||
// end the encoding!
|
||||
if (!pOutFile->WriteStr("?=")) return false;
|
||||
}
|
||||
|
||||
if (pProcessed) *pProcessed = inLen;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool C2047Translator::ConvertToFile(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile,
|
||||
uint32_t* pProcessed) {
|
||||
if (m_useQuotedPrintable)
|
||||
return ConvertToFileQ(pIn, inLen, pOutFile, pProcessed);
|
||||
|
||||
if (!inLen) return true;
|
||||
|
||||
int maxLineLen = 64;
|
||||
int curLineLen = m_startLen;
|
||||
bool startLine = true;
|
||||
int encodeMax;
|
||||
uint8_t* pEncoded = new uint8_t[maxLineLen * 2];
|
||||
|
||||
while (inLen) {
|
||||
if (startLine) {
|
||||
if (!pOutFile->WriteStr(" =?")) {
|
||||
delete[] pEncoded;
|
||||
return false;
|
||||
}
|
||||
if (!pOutFile->WriteStr(m_charset.get())) {
|
||||
delete[] pEncoded;
|
||||
return false;
|
||||
}
|
||||
if (!pOutFile->WriteStr("?b?")) {
|
||||
delete[] pEncoded;
|
||||
return false;
|
||||
}
|
||||
curLineLen += (6 + m_charset.Length());
|
||||
startLine = false;
|
||||
}
|
||||
encodeMax = maxLineLen - curLineLen;
|
||||
encodeMax *= 3;
|
||||
encodeMax /= 4;
|
||||
if ((uint32_t)encodeMax > inLen) encodeMax = (int)inLen;
|
||||
|
||||
// encode the line, end the line
|
||||
// then continue. Update curLineLen, pIn, startLine, and inLen
|
||||
UMimeEncode::ConvertBuffer(pIn, encodeMax, pEncoded, maxLineLen, maxLineLen,
|
||||
"\x0D\x0A");
|
||||
|
||||
if (!pOutFile->WriteStr((const char*)pEncoded)) {
|
||||
delete[] pEncoded;
|
||||
return false;
|
||||
}
|
||||
|
||||
pIn += encodeMax;
|
||||
inLen -= encodeMax;
|
||||
startLine = true;
|
||||
curLineLen = 0;
|
||||
if (!pOutFile->WriteStr("?=")) {
|
||||
delete[] pEncoded;
|
||||
return false;
|
||||
}
|
||||
if (inLen) {
|
||||
if (!pOutFile->WriteStr("\x0D\x0A ")) {
|
||||
delete[] pEncoded;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
delete[] pEncoded;
|
||||
|
||||
if (pProcessed) *pProcessed = inLen;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
uint32_t UMimeEncode::GetBufferSize(uint32_t inBytes) {
|
||||
// it takes 4 base64 bytes to represent 3 regular bytes
|
||||
inBytes += 3;
|
||||
inBytes /= 3;
|
||||
inBytes *= 4;
|
||||
// This should be plenty, but just to be safe
|
||||
inBytes += 4;
|
||||
|
||||
// now allow for end of line characters
|
||||
inBytes += ((inBytes + 39) / 40) * 4;
|
||||
|
||||
return inBytes;
|
||||
}
|
||||
|
||||
static uint8_t gBase64[] =
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
|
||||
|
||||
uint32_t UMimeEncode::ConvertBuffer(const uint8_t* pIn, uint32_t inLen,
|
||||
uint8_t* pOut, uint32_t maxLen,
|
||||
uint32_t firstLineLen,
|
||||
const char* pEolStr) {
|
||||
uint32_t pos = 0;
|
||||
uint32_t len = 0;
|
||||
uint32_t lineLen = 0;
|
||||
uint32_t maxLine = firstLineLen;
|
||||
int eolLen = 0;
|
||||
if (pEolStr) eolLen = strlen(pEolStr);
|
||||
|
||||
while ((pos + 2) < inLen) {
|
||||
// Encode 3 bytes
|
||||
*pOut = gBase64[*pIn >> 2];
|
||||
pOut++;
|
||||
len++;
|
||||
lineLen++;
|
||||
*pOut = gBase64[(((*pIn) & 0x3) << 4) | (((*(pIn + 1)) & 0xF0) >> 4)];
|
||||
pIn++;
|
||||
pOut++;
|
||||
len++;
|
||||
lineLen++;
|
||||
*pOut = gBase64[(((*pIn) & 0xF) << 2) | (((*(pIn + 1)) & 0xC0) >> 6)];
|
||||
pIn++;
|
||||
pOut++;
|
||||
len++;
|
||||
lineLen++;
|
||||
*pOut = gBase64[(*pIn) & 0x3F];
|
||||
pIn++;
|
||||
pOut++;
|
||||
len++;
|
||||
lineLen++;
|
||||
pos += 3;
|
||||
if (lineLen >= maxLine) {
|
||||
lineLen = 0;
|
||||
maxLine = maxLen;
|
||||
if (pEolStr) {
|
||||
memcpy(pOut, pEolStr, eolLen);
|
||||
pOut += eolLen;
|
||||
len += eolLen;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ((pos < inLen) && ((lineLen + 3) > maxLine)) {
|
||||
lineLen = 0;
|
||||
maxLine = maxLen;
|
||||
if (pEolStr) {
|
||||
memcpy(pOut, pEolStr, eolLen);
|
||||
pOut += eolLen;
|
||||
len += eolLen;
|
||||
}
|
||||
}
|
||||
|
||||
if (pos < inLen) {
|
||||
// Get the last few bytes!
|
||||
*pOut = gBase64[*pIn >> 2];
|
||||
pOut++;
|
||||
len++;
|
||||
pos++;
|
||||
if (pos < inLen) {
|
||||
*pOut = gBase64[(((*pIn) & 0x3) << 4) | (((*(pIn + 1)) & 0xF0) >> 4)];
|
||||
pIn++;
|
||||
pOut++;
|
||||
pos++;
|
||||
len++;
|
||||
if (pos < inLen) {
|
||||
// Should be dead code!! (Then why is it here doofus?)
|
||||
*pOut = gBase64[(((*pIn) & 0xF) << 2) | (((*(pIn + 1)) & 0xC0) >> 6)];
|
||||
pIn++;
|
||||
pOut++;
|
||||
len++;
|
||||
*pOut = gBase64[(*pIn) & 0x3F];
|
||||
pos++;
|
||||
pOut++;
|
||||
len++;
|
||||
} else {
|
||||
*pOut = gBase64[(((*pIn) & 0xF) << 2)];
|
||||
pOut++;
|
||||
len++;
|
||||
*pOut = '=';
|
||||
pOut++;
|
||||
len++;
|
||||
}
|
||||
} else {
|
||||
*pOut = gBase64[(((*pIn) & 0x3) << 4)];
|
||||
pOut++;
|
||||
len++;
|
||||
*pOut = '=';
|
||||
pOut++;
|
||||
len++;
|
||||
*pOut = '=';
|
||||
pOut++;
|
||||
len++;
|
||||
}
|
||||
}
|
||||
|
||||
*pOut = 0;
|
||||
|
||||
return len;
|
||||
}
|
|
@ -1,87 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsImportTranslator_h___
|
||||
#define nsImportTranslator_h___
|
||||
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "nscore.h"
|
||||
#include "nsString.h"
|
||||
#include "nsCOMPtr.h"
|
||||
|
||||
class ImportOutFile;
|
||||
|
||||
class UMimeEncode {
|
||||
public:
|
||||
static uint32_t GetBufferSize(uint32_t inByes);
|
||||
static uint32_t ConvertBuffer(const uint8_t* pIn, uint32_t inLen,
|
||||
uint8_t* pOut, uint32_t maxLen = 72,
|
||||
uint32_t firstLineLen = 72,
|
||||
const char* pEolStr = nullptr);
|
||||
};
|
||||
|
||||
class nsImportTranslator {
|
||||
public:
|
||||
virtual ~nsImportTranslator() {}
|
||||
virtual bool Supports8bitEncoding(void) { return false; }
|
||||
virtual uint32_t GetMaxBufferSize(uint32_t inLen) { return inLen + 1; }
|
||||
virtual void ConvertBuffer(const uint8_t* pIn, uint32_t inLen,
|
||||
uint8_t* pOut) {
|
||||
memcpy(pOut, pIn, inLen);
|
||||
pOut[inLen] = 0;
|
||||
}
|
||||
virtual bool ConvertToFile(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile,
|
||||
uint32_t* pProcessed = nullptr);
|
||||
virtual bool FinishConvertToFile(ImportOutFile* /* pOutFile */) {
|
||||
return true;
|
||||
}
|
||||
|
||||
virtual void GetCharset(nsCString& charSet) { charSet = "us-ascii"; }
|
||||
virtual void GetLanguage(nsCString& lang) { lang = "en"; }
|
||||
virtual void GetEncoding(nsCString& encoding) { encoding.Truncate(); }
|
||||
};
|
||||
|
||||
// Specialized encoder, not a valid language translator, used for Mime headers.
|
||||
// rfc2231
|
||||
class CMHTranslator : public nsImportTranslator {
|
||||
public:
|
||||
virtual uint32_t GetMaxBufferSize(uint32_t inLen) override {
|
||||
return (inLen * 3) + 1;
|
||||
}
|
||||
virtual void ConvertBuffer(const uint8_t* pIn, uint32_t inLen,
|
||||
uint8_t* pOut) override;
|
||||
virtual bool ConvertToFile(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile,
|
||||
uint32_t* pProcessed = nullptr) override;
|
||||
};
|
||||
|
||||
// Specialized encoder, not a valid language translator, used for mail headers
|
||||
// rfc2047
|
||||
class C2047Translator : public nsImportTranslator {
|
||||
public:
|
||||
virtual ~C2047Translator() {}
|
||||
|
||||
C2047Translator(const char* pCharset, uint32_t headerLen) {
|
||||
m_charset = pCharset;
|
||||
m_startLen = headerLen;
|
||||
m_useQuotedPrintable = false;
|
||||
}
|
||||
|
||||
void SetUseQuotedPrintable(void) { m_useQuotedPrintable = true; }
|
||||
|
||||
virtual bool ConvertToFile(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile,
|
||||
uint32_t* pProcessed = nullptr) override;
|
||||
bool ConvertToFileQ(const uint8_t* pIn, uint32_t inLen,
|
||||
ImportOutFile* pOutFile, uint32_t* pProcessed);
|
||||
|
||||
protected:
|
||||
bool m_useQuotedPrintable;
|
||||
nsCString m_charset;
|
||||
uint32_t m_startLen;
|
||||
};
|
||||
|
||||
#endif /* nsImportTranslator_h__ */
|
|
@ -1,426 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nsTextAddress.h"
|
||||
#include "nsIAbCard.h"
|
||||
#include "nsIAbDirectory.h"
|
||||
#include "nsNativeCharsetUtils.h"
|
||||
#include "nsIFile.h"
|
||||
#include "nsIInputStream.h"
|
||||
#include "nsNetUtil.h"
|
||||
#include "nsMsgI18N.h"
|
||||
#include "nsMsgUtils.h"
|
||||
#include "nsIConverterInputStream.h"
|
||||
#include "nsIUnicharLineInputStream.h"
|
||||
#include "nsMsgUtils.h"
|
||||
|
||||
#include "ImportDebug.h"
|
||||
#include "plstr.h"
|
||||
#include "msgCore.h"
|
||||
|
||||
#define kWhitespace " \t\b\r\n"
|
||||
|
||||
nsTextAddress::nsTextAddress() {
|
||||
m_LFCount = 0;
|
||||
m_CRCount = 0;
|
||||
}
|
||||
|
||||
nsTextAddress::~nsTextAddress() {}
|
||||
|
||||
nsresult nsTextAddress::GetUnicharLineStreamForFile(
|
||||
nsIFile* aFile, nsIInputStream* aInputStream,
|
||||
nsIUnicharLineInputStream** aStream) {
|
||||
nsAutoCString charset;
|
||||
nsresult rv = MsgDetectCharsetFromFile(aFile, charset);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
nsCOMPtr<nsIConverterInputStream> converterStream =
|
||||
do_CreateInstance("@mozilla.org/intl/converter-input-stream;1", &rv);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = converterStream->Init(
|
||||
aInputStream, charset.get(), 8192,
|
||||
nsIConverterInputStream::DEFAULT_REPLACEMENT_CHARACTER);
|
||||
}
|
||||
|
||||
return CallQueryInterface(converterStream, aStream);
|
||||
}
|
||||
|
||||
nsresult nsTextAddress::ImportAddresses(bool* pAbort, const char16_t* pName,
|
||||
nsIFile* pSrc,
|
||||
nsIAbDirectory* pDirectory,
|
||||
nsIImportFieldMap* fieldMap,
|
||||
nsString& errors, uint32_t* pProgress) {
|
||||
// Open the source file for reading, read each line and process it!
|
||||
m_directory = pDirectory;
|
||||
m_fieldMap = fieldMap;
|
||||
|
||||
nsCOMPtr<nsIInputStream> inputStream;
|
||||
nsresult rv = NS_NewLocalFileInputStream(getter_AddRefs(inputStream), pSrc);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error opening address file for reading\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
// Here we use this to work out the size of the file, so we can update
|
||||
// an integer as we go through the file which will update a progress
|
||||
// bar if required by the caller.
|
||||
uint64_t bytesLeft = 0;
|
||||
rv = inputStream->Available(&bytesLeft);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error checking address file for size\n");
|
||||
inputStream->Close();
|
||||
return rv;
|
||||
}
|
||||
|
||||
uint64_t totalBytes = bytesLeft;
|
||||
bool skipRecord = false;
|
||||
|
||||
rv = m_fieldMap->GetSkipFirstRecord(&skipRecord);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0(
|
||||
"*** Error checking to see if we should skip the first record\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIUnicharLineInputStream> lineStream;
|
||||
rv = GetUnicharLineStreamForFile(pSrc, inputStream,
|
||||
getter_AddRefs(lineStream));
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error opening converter stream for importer\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
bool more = true;
|
||||
nsAutoString line;
|
||||
|
||||
// Skip the first record if the user has requested it.
|
||||
if (skipRecord) rv = ReadRecord(lineStream, line, &more);
|
||||
|
||||
while (!(*pAbort) && more && NS_SUCCEEDED(rv)) {
|
||||
// Read the line in
|
||||
rv = ReadRecord(lineStream, line, &more);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
// Now process it to add it to the database
|
||||
rv = ProcessLine(line, errors);
|
||||
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error processing text record.\n");
|
||||
}
|
||||
}
|
||||
if (NS_SUCCEEDED(rv) && pProgress) {
|
||||
// This won't be totally accurate, but its the best we can do
|
||||
// considering that lineStream won't give us how many bytes
|
||||
// are actually left.
|
||||
bytesLeft -= line.Length();
|
||||
*pProgress = std::min(totalBytes - bytesLeft, uint64_t(PR_UINT32_MAX));
|
||||
}
|
||||
}
|
||||
|
||||
inputStream->Close();
|
||||
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0(
|
||||
"*** Error reading the address book - probably incorrect ending\n");
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult nsTextAddress::ReadRecord(nsIUnicharLineInputStream* aLineStream,
|
||||
nsAString& aLine, bool* aMore) {
|
||||
bool more = true;
|
||||
uint32_t numQuotes = 0;
|
||||
nsresult rv;
|
||||
nsAutoString line;
|
||||
|
||||
// ensure aLine is empty
|
||||
aLine.Truncate();
|
||||
|
||||
do {
|
||||
if (!more) {
|
||||
// No more, so we must have an incorrect file.
|
||||
rv = NS_ERROR_FAILURE;
|
||||
} else {
|
||||
// Read the line and append it
|
||||
rv = aLineStream->ReadLine(line, &more);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
if (!aLine.IsEmpty()) aLine.AppendLiteral(MSG_LINEBREAK);
|
||||
aLine.Append(line);
|
||||
|
||||
numQuotes += line.CountChar(char16_t('"'));
|
||||
}
|
||||
}
|
||||
// Continue whilst everything is ok, and we have an odd number of quotes.
|
||||
} while (NS_SUCCEEDED(rv) && (numQuotes % 2 != 0));
|
||||
|
||||
*aMore = more;
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsresult nsTextAddress::ReadRecordNumber(nsIFile* aSrc, nsAString& aLine,
|
||||
int32_t rNum) {
|
||||
nsCOMPtr<nsIInputStream> inputStream;
|
||||
nsresult rv = NS_NewLocalFileInputStream(getter_AddRefs(inputStream), aSrc);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error opening address file for reading\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
int32_t rIndex = 0;
|
||||
uint64_t bytesLeft = 0;
|
||||
|
||||
rv = inputStream->Available(&bytesLeft);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error checking address file for eof\n");
|
||||
inputStream->Close();
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIUnicharLineInputStream> lineStream;
|
||||
rv = GetUnicharLineStreamForFile(aSrc, inputStream,
|
||||
getter_AddRefs(lineStream));
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error opening converter stream for importer\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
bool more = true;
|
||||
|
||||
while (more && (rIndex <= rNum)) {
|
||||
rv = ReadRecord(lineStream, aLine, &more);
|
||||
if (NS_FAILED(rv)) {
|
||||
inputStream->Close();
|
||||
return rv;
|
||||
}
|
||||
if (rIndex == rNum) {
|
||||
inputStream->Close();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
rIndex++;
|
||||
}
|
||||
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
int32_t nsTextAddress::CountFields(const nsAString& aLine, char16_t delim) {
|
||||
int32_t pos = 0;
|
||||
int32_t maxLen = aLine.Length();
|
||||
int32_t count = 0;
|
||||
char16_t tab = char16_t('\t');
|
||||
char16_t doubleQuote = char16_t('"');
|
||||
|
||||
if (delim == tab) tab = char16_t('\0');
|
||||
|
||||
while (pos < maxLen) {
|
||||
while (((aLine[pos] == char16_t(' ')) || (aLine[pos] == tab)) &&
|
||||
(pos < maxLen)) {
|
||||
pos++;
|
||||
}
|
||||
if ((pos < maxLen) && (aLine[pos] == doubleQuote)) {
|
||||
pos++;
|
||||
while ((pos < maxLen) && (aLine[pos] != doubleQuote)) {
|
||||
pos++;
|
||||
if (((pos + 1) < maxLen) && (aLine[pos] == doubleQuote) &&
|
||||
(aLine[pos + 1] == doubleQuote)) {
|
||||
pos += 2;
|
||||
}
|
||||
}
|
||||
if (pos < maxLen) pos++;
|
||||
}
|
||||
while ((pos < maxLen) && (aLine[pos] != delim)) pos++;
|
||||
|
||||
count++;
|
||||
pos++;
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
bool nsTextAddress::GetField(const nsAString& aLine, int32_t index,
|
||||
nsString& field, char16_t delim) {
|
||||
bool result = false;
|
||||
int32_t pos = 0;
|
||||
int32_t maxLen = aLine.Length();
|
||||
char16_t tab = char16_t('\t');
|
||||
char16_t doubleQuote = char16_t('"');
|
||||
|
||||
field.Truncate();
|
||||
|
||||
if (delim == tab) tab = 0;
|
||||
|
||||
while (index && (pos < maxLen)) {
|
||||
while (((aLine[pos] == char16_t(' ')) || (aLine[pos] == tab)) &&
|
||||
(pos < maxLen)) {
|
||||
pos++;
|
||||
}
|
||||
if (pos >= maxLen) break;
|
||||
if (aLine[pos] == doubleQuote) {
|
||||
do {
|
||||
pos++;
|
||||
if (((pos + 1) < maxLen) && (aLine[pos] == doubleQuote) &&
|
||||
(aLine[pos + 1] == doubleQuote)) {
|
||||
pos += 2;
|
||||
}
|
||||
} while ((pos < maxLen) && (aLine[pos] != doubleQuote));
|
||||
if (pos < maxLen) pos++;
|
||||
}
|
||||
if (pos >= maxLen) break;
|
||||
|
||||
while ((pos < maxLen) && (aLine[pos] != delim)) pos++;
|
||||
|
||||
if (pos >= maxLen) break;
|
||||
|
||||
index--;
|
||||
pos++;
|
||||
}
|
||||
|
||||
if (pos >= maxLen) return result;
|
||||
|
||||
result = true;
|
||||
|
||||
while ((pos < maxLen) && ((aLine[pos] == ' ') || (aLine[pos] == tab))) pos++;
|
||||
|
||||
int32_t fLen = 0;
|
||||
int32_t startPos = pos;
|
||||
bool quoted = false;
|
||||
if (aLine[pos] == '"') {
|
||||
startPos++;
|
||||
fLen = -1;
|
||||
do {
|
||||
pos++;
|
||||
fLen++;
|
||||
if (((pos + 1) < maxLen) && (aLine[pos] == doubleQuote) &&
|
||||
(aLine[pos + 1] == doubleQuote)) {
|
||||
quoted = true;
|
||||
pos += 2;
|
||||
fLen += 2;
|
||||
}
|
||||
} while ((pos < maxLen) && (aLine[pos] != doubleQuote));
|
||||
} else {
|
||||
while ((pos < maxLen) && (aLine[pos] != delim)) {
|
||||
pos++;
|
||||
fLen++;
|
||||
}
|
||||
}
|
||||
|
||||
if (!fLen) {
|
||||
return result;
|
||||
}
|
||||
|
||||
field.Append(nsDependentSubstring(aLine, startPos, fLen));
|
||||
field.Trim(kWhitespace);
|
||||
|
||||
if (quoted) {
|
||||
int32_t offset = field.Find(u"\"\"");
|
||||
while (offset != -1) {
|
||||
field.Cut(offset, 1);
|
||||
offset = field.Find(u"\"\"", offset + 1);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
nsresult nsTextAddress::DetermineDelim(nsIFile* aSrc) {
|
||||
nsCOMPtr<nsIInputStream> inputStream;
|
||||
nsresult rv = NS_NewLocalFileInputStream(getter_AddRefs(inputStream), aSrc);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error opening address file for reading\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
int32_t lineCount = 0;
|
||||
int32_t tabCount = 0;
|
||||
int32_t commaCount = 0;
|
||||
int32_t tabLines = 0;
|
||||
int32_t commaLines = 0;
|
||||
nsAutoString line;
|
||||
bool more = true;
|
||||
|
||||
nsCOMPtr<nsIUnicharLineInputStream> lineStream;
|
||||
rv = GetUnicharLineStreamForFile(aSrc, inputStream,
|
||||
getter_AddRefs(lineStream));
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error opening converter stream for importer\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
while (more && NS_SUCCEEDED(rv) && (lineCount < 100)) {
|
||||
rv = lineStream->ReadLine(line, &more);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
tabCount = CountFields(line, char16_t('\t'));
|
||||
commaCount = CountFields(line, char16_t(','));
|
||||
if (tabCount > commaCount)
|
||||
tabLines++;
|
||||
else if (commaCount)
|
||||
commaLines++;
|
||||
}
|
||||
lineCount++;
|
||||
}
|
||||
|
||||
rv = inputStream->Close();
|
||||
|
||||
if (tabLines > commaLines)
|
||||
m_delim = char16_t('\t');
|
||||
else
|
||||
m_delim = char16_t(',');
|
||||
|
||||
IMPORT_LOG2("Tab count = %d, Comma count = %d\n", tabLines, commaLines);
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
/*
|
||||
This is where the real work happens!
|
||||
Go through the field map and set the data in a new database row
|
||||
*/
|
||||
nsresult nsTextAddress::ProcessLine(const nsAString& aLine, nsString& errors) {
|
||||
if (!m_fieldMap) {
|
||||
IMPORT_LOG0("*** Error, text import needs a field map\n");
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsresult rv;
|
||||
|
||||
// Wait until we get our first non-empty field, then create a new row,
|
||||
// fill in the data, then add the row to the database.
|
||||
nsCOMPtr<nsIAbCard> newCard;
|
||||
nsAutoString fieldVal;
|
||||
int32_t fieldNum;
|
||||
int32_t numFields = 0;
|
||||
bool active;
|
||||
rv = m_fieldMap->GetMapSize(&numFields);
|
||||
for (int32_t i = 0; (i < numFields) && NS_SUCCEEDED(rv); i++) {
|
||||
active = false;
|
||||
rv = m_fieldMap->GetFieldMap(i, &fieldNum);
|
||||
if (NS_SUCCEEDED(rv)) rv = m_fieldMap->GetFieldActive(i, &active);
|
||||
if (NS_SUCCEEDED(rv) && active) {
|
||||
if (GetField(aLine, i, fieldVal, m_delim)) {
|
||||
if (!fieldVal.IsEmpty()) {
|
||||
if (!newCard) {
|
||||
newCard = do_CreateInstance(
|
||||
"@mozilla.org/addressbook/cardproperty;1", &rv);
|
||||
}
|
||||
if (newCard) {
|
||||
rv = m_fieldMap->SetFieldValue(m_directory, newCard, fieldNum,
|
||||
fieldVal);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
} else if (active) {
|
||||
IMPORT_LOG1("*** Error getting field map for index %ld\n", (long)i);
|
||||
}
|
||||
}
|
||||
|
||||
nsIAbCard* outCard;
|
||||
rv = m_directory->AddCard(newCard, &outCard);
|
||||
|
||||
return rv;
|
||||
}
|
|
@ -1,60 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsTextAddress_h__
|
||||
#define nsTextAddress_h__
|
||||
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsString.h"
|
||||
#include "nsIImportFieldMap.h"
|
||||
#include "nsIImportService.h"
|
||||
|
||||
class nsIAbDirectory;
|
||||
class nsIFile;
|
||||
class nsIInputStream;
|
||||
class nsIUnicharLineInputStream;
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
class nsTextAddress {
|
||||
public:
|
||||
nsTextAddress();
|
||||
virtual ~nsTextAddress();
|
||||
|
||||
nsresult ImportAddresses(bool* pAbort, const char16_t* pName, nsIFile* pSrc,
|
||||
nsIAbDirectory* pDirectory,
|
||||
nsIImportFieldMap* fieldMap, nsString& errors,
|
||||
uint32_t* pProgress);
|
||||
|
||||
nsresult DetermineDelim(nsIFile* pSrc);
|
||||
char16_t GetDelim(void) { return m_delim; }
|
||||
|
||||
static nsresult ReadRecordNumber(nsIFile* pSrc, nsAString& aLine,
|
||||
int32_t rNum);
|
||||
static bool GetField(const nsAString& aLine, int32_t index, nsString& field,
|
||||
char16_t delim);
|
||||
|
||||
private:
|
||||
nsresult ProcessLine(const nsAString& aLine, nsString& errors);
|
||||
|
||||
static int32_t CountFields(const nsAString& aLine, char16_t delim);
|
||||
static nsresult ReadRecord(nsIUnicharLineInputStream* pSrc, nsAString& aLine,
|
||||
bool* aMore);
|
||||
static nsresult GetUnicharLineStreamForFile(
|
||||
nsIFile* aFile, nsIInputStream* aInputStream,
|
||||
nsIUnicharLineInputStream** aStream);
|
||||
|
||||
char16_t m_delim;
|
||||
int32_t m_LFCount;
|
||||
int32_t m_CRCount;
|
||||
nsCOMPtr<nsIAbDirectory> m_directory;
|
||||
nsCOMPtr<nsIImportFieldMap> m_fieldMap;
|
||||
nsCOMPtr<nsIImportService> m_pService;
|
||||
};
|
||||
|
||||
#endif /* nsTextAddress_h__ */
|
|
@ -1,618 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
/*
|
||||
* Text import addressbook interfaces
|
||||
*/
|
||||
|
||||
#include "nscore.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIImportService.h"
|
||||
#include "nsMsgI18N.h"
|
||||
#include "nsTextImport.h"
|
||||
#include "nsIImportGeneric.h"
|
||||
#include "nsIImportAddressBooks.h"
|
||||
#include "nsIImportABDescriptor.h"
|
||||
#include "nsIImportFieldMap.h"
|
||||
#include "nsIAbLDIFService.h"
|
||||
#include "nsTextFormatter.h"
|
||||
#include "nsImportStringBundle.h"
|
||||
#include "nsTextAddress.h"
|
||||
#include "nsIPrefService.h"
|
||||
#include "nsIPrefBranch.h"
|
||||
#include "ImportDebug.h"
|
||||
#include "nsNetUtil.h"
|
||||
#include "nsMsgUtils.h"
|
||||
|
||||
#define TEXT_MSGS_URL "chrome://messenger/locale/textImportMsgs.properties"
|
||||
#define TEXTIMPORT_NAME 2000
|
||||
#define TEXTIMPORT_DESCRIPTION 2001
|
||||
#define TEXTIMPORT_ADDRESS_NAME 2002
|
||||
#define TEXTIMPORT_ADDRESS_SUCCESS 2003
|
||||
#define TEXTIMPORT_ADDRESS_BADPARAM 2004
|
||||
#define TEXTIMPORT_ADDRESS_BADSOURCEFILE 2005
|
||||
#define TEXTIMPORT_ADDRESS_CONVERTERROR 2006
|
||||
|
||||
class ImportAddressImpl final : public nsIImportAddressBooks {
|
||||
public:
|
||||
explicit ImportAddressImpl(nsIStringBundle* aStringBundle);
|
||||
|
||||
static nsresult Create(nsIImportAddressBooks** aImport,
|
||||
nsIStringBundle* aStringBundle);
|
||||
|
||||
// nsISupports interface
|
||||
NS_DECL_THREADSAFE_ISUPPORTS
|
||||
|
||||
// nsIImportAddressBooks interface
|
||||
|
||||
NS_IMETHOD GetSupportsMultiple(bool* _retval) override {
|
||||
*_retval = false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHOD GetAutoFind(char16_t** description, bool* _retval) override;
|
||||
|
||||
NS_IMETHOD GetNeedsFieldMap(nsIFile* location, bool* _retval) override;
|
||||
|
||||
NS_IMETHOD GetDefaultLocation(nsIFile** location, bool* found,
|
||||
bool* userVerify) override;
|
||||
|
||||
NS_IMETHOD FindAddressBooks(
|
||||
nsIFile* location,
|
||||
nsTArray<RefPtr<nsIImportABDescriptor>>& books) override;
|
||||
|
||||
NS_IMETHOD InitFieldMap(nsIImportFieldMap* fieldMap) override;
|
||||
|
||||
NS_IMETHOD ImportAddressBook(nsIImportABDescriptor* source,
|
||||
nsIAbDirectory* destination,
|
||||
nsIImportFieldMap* fieldMap,
|
||||
nsISupports* aSupportService,
|
||||
char16_t** errorLog, char16_t** successLog,
|
||||
bool* fatalError) override;
|
||||
|
||||
NS_IMETHOD GetImportProgress(uint32_t* _retval) override;
|
||||
|
||||
NS_IMETHOD GetSampleData(int32_t index, bool* pFound,
|
||||
char16_t** pStr) override;
|
||||
|
||||
NS_IMETHOD SetSampleLocation(nsIFile*) override;
|
||||
|
||||
private:
|
||||
void ClearSampleFile(void);
|
||||
void SaveFieldMap(nsIImportFieldMap* pMap);
|
||||
|
||||
static void ReportSuccess(nsString& name, nsString* pStream,
|
||||
nsIStringBundle* pBundle);
|
||||
static void SetLogs(nsString& success, nsString& error, char16_t** pError,
|
||||
char16_t** pSuccess);
|
||||
static void ReportError(int32_t errorNum, nsString& name, nsString* pStream,
|
||||
nsIStringBundle* pBundle);
|
||||
static void SanitizeSampleData(nsString& val);
|
||||
|
||||
private:
|
||||
~ImportAddressImpl() {}
|
||||
nsTextAddress m_text;
|
||||
bool m_haveDelim;
|
||||
nsCOMPtr<nsIFile> m_fileLoc;
|
||||
nsCOMPtr<nsIStringBundle> m_notProxyBundle;
|
||||
char16_t m_delim;
|
||||
uint32_t m_bytesImported;
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
nsTextImport::nsTextImport() {
|
||||
IMPORT_LOG0("nsTextImport Module Created\n");
|
||||
|
||||
nsImportStringBundle::GetStringBundle(TEXT_MSGS_URL,
|
||||
getter_AddRefs(m_stringBundle));
|
||||
}
|
||||
|
||||
nsTextImport::~nsTextImport() { IMPORT_LOG0("nsTextImport Module Deleted\n"); }
|
||||
|
||||
NS_IMPL_ISUPPORTS(nsTextImport, nsIImportModule)
|
||||
|
||||
NS_IMETHODIMP nsTextImport::GetImportInterface(const char* pImportType,
|
||||
nsISupports** ppInterface) {
|
||||
NS_ENSURE_ARG_POINTER(pImportType);
|
||||
NS_ENSURE_ARG_POINTER(ppInterface);
|
||||
|
||||
*ppInterface = nullptr;
|
||||
nsresult rv;
|
||||
|
||||
if (!strcmp(pImportType, "addressbook")) {
|
||||
// create the nsIImportMail interface and return it!
|
||||
nsCOMPtr<nsIImportAddressBooks> pAddress;
|
||||
nsCOMPtr<nsIImportGeneric> pGeneric;
|
||||
rv = ImportAddressImpl::Create(getter_AddRefs(pAddress), m_stringBundle);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
nsCOMPtr<nsIImportService> impSvc(
|
||||
do_GetService(NS_IMPORTSERVICE_CONTRACTID, &rv));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = impSvc->CreateNewGenericAddressBooks(getter_AddRefs(pGeneric));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
pGeneric->SetData("addressInterface", pAddress);
|
||||
nsCOMPtr<nsISupports> pInterface(do_QueryInterface(pGeneric));
|
||||
pInterface.forget(ppInterface);
|
||||
}
|
||||
}
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
nsresult ImportAddressImpl::Create(nsIImportAddressBooks** aImport,
|
||||
nsIStringBundle* aStringBundle) {
|
||||
NS_ENSURE_ARG_POINTER(aImport);
|
||||
NS_ADDREF(*aImport = new ImportAddressImpl(aStringBundle));
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
ImportAddressImpl::ImportAddressImpl(nsIStringBundle* aStringBundle)
|
||||
: m_notProxyBundle(aStringBundle) {
|
||||
m_haveDelim = false;
|
||||
}
|
||||
|
||||
NS_IMPL_ISUPPORTS(ImportAddressImpl, nsIImportAddressBooks)
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::GetAutoFind(char16_t** addrDescription,
|
||||
bool* _retval) {
|
||||
NS_ASSERTION(addrDescription != nullptr, "null ptr");
|
||||
NS_ASSERTION(_retval != nullptr, "null ptr");
|
||||
if (!addrDescription || !_retval) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
nsString str;
|
||||
*_retval = false;
|
||||
|
||||
if (!m_notProxyBundle) return NS_ERROR_FAILURE;
|
||||
|
||||
nsImportStringBundle::GetStringByID(TEXTIMPORT_ADDRESS_NAME, m_notProxyBundle,
|
||||
str);
|
||||
*addrDescription = ToNewUnicode(str);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::GetDefaultLocation(nsIFile** ppLoc,
|
||||
bool* found,
|
||||
bool* userVerify) {
|
||||
NS_ASSERTION(found != nullptr, "null ptr");
|
||||
NS_ASSERTION(ppLoc != nullptr, "null ptr");
|
||||
NS_ASSERTION(userVerify != nullptr, "null ptr");
|
||||
if (!found || !userVerify || !ppLoc) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
*ppLoc = nullptr;
|
||||
*found = false;
|
||||
*userVerify = true;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::FindAddressBooks(
|
||||
nsIFile* pLoc, nsTArray<RefPtr<nsIImportABDescriptor>>& books) {
|
||||
NS_ASSERTION(pLoc != nullptr, "null ptr");
|
||||
if (!pLoc) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
books.Clear();
|
||||
ClearSampleFile();
|
||||
|
||||
bool exists = false;
|
||||
nsresult rv = pLoc->Exists(&exists);
|
||||
if (NS_FAILED(rv) || !exists) return NS_ERROR_FAILURE;
|
||||
|
||||
bool isFile = false;
|
||||
rv = pLoc->IsFile(&isFile);
|
||||
if (NS_FAILED(rv) || !isFile) return NS_ERROR_FAILURE;
|
||||
|
||||
rv = m_text.DetermineDelim(pLoc);
|
||||
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error determining delimitter\n");
|
||||
return rv;
|
||||
}
|
||||
m_haveDelim = true;
|
||||
m_delim = m_text.GetDelim();
|
||||
|
||||
m_fileLoc = pLoc;
|
||||
|
||||
/* Build an address book descriptor based on the file passed in! */
|
||||
nsString name;
|
||||
m_fileLoc->GetLeafName(name);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Failed getting leaf name of file\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
int32_t idx = name.RFindChar('.');
|
||||
if ((idx != -1) && (idx > 0) && ((name.Length() - idx - 1) < 5)) {
|
||||
name.SetLength(idx);
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIImportABDescriptor> desc;
|
||||
|
||||
nsCOMPtr<nsIImportService> impSvc(
|
||||
do_GetService(NS_IMPORTSERVICE_CONTRACTID, &rv));
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Failed to obtain the import service\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = impSvc->CreateNewABDescriptor(getter_AddRefs(desc));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
int64_t sz = 0;
|
||||
pLoc->GetFileSize(&sz);
|
||||
desc->SetPreferredName(name);
|
||||
desc->SetSize((uint32_t)sz);
|
||||
desc->SetAbFile(m_fileLoc);
|
||||
books.AppendElement(desc);
|
||||
}
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error creating address book descriptor for text import\n");
|
||||
return rv;
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
void ImportAddressImpl::ReportSuccess(nsString& name, nsString* pStream,
|
||||
nsIStringBundle* pBundle) {
|
||||
if (!pStream) return;
|
||||
|
||||
// load the success string
|
||||
char16_t* pFmt =
|
||||
nsImportStringBundle::GetStringByID(TEXTIMPORT_ADDRESS_SUCCESS, pBundle);
|
||||
|
||||
nsString pText;
|
||||
nsTextFormatter::ssprintf(pText, pFmt, name.get());
|
||||
pStream->Append(pText);
|
||||
free(pFmt);
|
||||
pStream->Append(char16_t('\n'));
|
||||
}
|
||||
|
||||
void ImportAddressImpl::ReportError(int32_t errorNum, nsString& name,
|
||||
nsString* pStream,
|
||||
nsIStringBundle* pBundle) {
|
||||
if (!pStream) return;
|
||||
|
||||
// load the error string
|
||||
char16_t* pFmt = nsImportStringBundle::GetStringByID(errorNum, pBundle);
|
||||
nsString pText;
|
||||
nsTextFormatter::ssprintf(pText, pFmt, name.get());
|
||||
pStream->Append(pText);
|
||||
free(pFmt);
|
||||
pStream->Append(char16_t('\n'));
|
||||
}
|
||||
|
||||
void ImportAddressImpl::SetLogs(nsString& success, nsString& error,
|
||||
char16_t** pError, char16_t** pSuccess) {
|
||||
if (pError) *pError = ToNewUnicode(error);
|
||||
if (pSuccess) *pSuccess = ToNewUnicode(success);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
ImportAddressImpl::ImportAddressBook(nsIImportABDescriptor* pSource,
|
||||
nsIAbDirectory* pDestination,
|
||||
nsIImportFieldMap* fieldMap,
|
||||
nsISupports* aSupportService,
|
||||
char16_t** pErrorLog,
|
||||
char16_t** pSuccessLog, bool* fatalError) {
|
||||
NS_ASSERTION(pSource != nullptr, "null ptr");
|
||||
NS_ASSERTION(pDestination != nullptr, "null ptr");
|
||||
NS_ASSERTION(fatalError != nullptr, "null ptr");
|
||||
|
||||
m_bytesImported = 0;
|
||||
|
||||
nsString success, error;
|
||||
if (!pSource || !pDestination || !fatalError) {
|
||||
IMPORT_LOG0("*** Bad param passed to text address import\n");
|
||||
nsImportStringBundle::GetStringByID(TEXTIMPORT_ADDRESS_BADPARAM,
|
||||
m_notProxyBundle, error);
|
||||
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
|
||||
if (fatalError) *fatalError = true;
|
||||
|
||||
return NS_ERROR_NULL_POINTER;
|
||||
}
|
||||
|
||||
ClearSampleFile();
|
||||
|
||||
bool addrAbort = false;
|
||||
nsString name;
|
||||
pSource->GetPreferredName(name);
|
||||
|
||||
uint32_t addressSize = 0;
|
||||
pSource->GetSize(&addressSize);
|
||||
if (addressSize == 0) {
|
||||
IMPORT_LOG0("Address book size is 0, skipping import.\n");
|
||||
ReportSuccess(name, &success, m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIFile> inFile;
|
||||
if (NS_FAILED(pSource->GetAbFile(getter_AddRefs(inFile)))) {
|
||||
ReportError(TEXTIMPORT_ADDRESS_BADSOURCEFILE, name, &error,
|
||||
m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
if (!aSupportService) {
|
||||
IMPORT_LOG0("Missing support service to import call");
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
bool isLDIF = false;
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIAbLDIFService> ldifService(
|
||||
do_QueryInterface(aSupportService, &rv));
|
||||
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = ldifService->IsLDIFFile(inFile, &isLDIF);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error reading address file\n");
|
||||
}
|
||||
}
|
||||
|
||||
if (NS_FAILED(rv)) {
|
||||
ReportError(TEXTIMPORT_ADDRESS_CONVERTERROR, name, &error,
|
||||
m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (isLDIF) {
|
||||
if (ldifService)
|
||||
rv = ldifService->ImportLDIFFile(pDestination, inFile, false,
|
||||
&m_bytesImported);
|
||||
else
|
||||
return NS_ERROR_FAILURE;
|
||||
} else {
|
||||
rv = m_text.ImportAddresses(&addrAbort, name.get(), inFile, pDestination,
|
||||
fieldMap, error, &m_bytesImported);
|
||||
SaveFieldMap(fieldMap);
|
||||
}
|
||||
|
||||
if (NS_SUCCEEDED(rv) && error.IsEmpty()) {
|
||||
ReportSuccess(name, &success, m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
} else {
|
||||
ReportError(TEXTIMPORT_ADDRESS_CONVERTERROR, name, &error,
|
||||
m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
}
|
||||
|
||||
IMPORT_LOG0("*** Text address import done\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::GetImportProgress(uint32_t* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
*_retval = m_bytesImported;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::GetNeedsFieldMap(nsIFile* aLocation,
|
||||
bool* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
NS_ENSURE_ARG_POINTER(aLocation);
|
||||
|
||||
*_retval = true;
|
||||
bool exists = false;
|
||||
bool isFile = false;
|
||||
|
||||
nsresult rv = aLocation->Exists(&exists);
|
||||
rv = aLocation->IsFile(&isFile);
|
||||
|
||||
if (!exists || !isFile) return NS_ERROR_FAILURE;
|
||||
|
||||
bool isLDIF = false;
|
||||
nsCOMPtr<nsIAbLDIFService> ldifService =
|
||||
do_GetService("@mozilla.org/addressbook/abldifservice;1", &rv);
|
||||
|
||||
if (NS_SUCCEEDED(rv)) rv = ldifService->IsLDIFFile(aLocation, &isLDIF);
|
||||
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Error determining if file is of type LDIF\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (isLDIF) *_retval = false;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
void ImportAddressImpl::SanitizeSampleData(nsString& val) {
|
||||
// remove any line-feeds...
|
||||
int32_t offset = val.Find(u"\x0D\x0A"_ns);
|
||||
while (offset != -1) {
|
||||
val.Replace(offset, 2, u", "_ns);
|
||||
offset = val.Find(u"\x0D\x0A"_ns, offset + 2);
|
||||
}
|
||||
offset = val.FindChar(13);
|
||||
while (offset != -1) {
|
||||
val.Replace(offset, 1, ',');
|
||||
offset = val.FindChar(13, offset + 2);
|
||||
}
|
||||
offset = val.FindChar(10);
|
||||
while (offset != -1) {
|
||||
val.Replace(offset, 1, ',');
|
||||
offset = val.FindChar(10, offset + 2);
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::GetSampleData(int32_t index, bool* pFound,
|
||||
char16_t** pStr) {
|
||||
NS_ASSERTION(pFound != nullptr, "null ptr");
|
||||
NS_ASSERTION(pStr != nullptr, "null ptr");
|
||||
if (!pFound || !pStr) return NS_ERROR_NULL_POINTER;
|
||||
|
||||
if (!m_fileLoc) {
|
||||
IMPORT_LOG0("*** Error, called GetSampleData before SetSampleLocation\n");
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsresult rv;
|
||||
*pStr = nullptr;
|
||||
char16_t term = 0;
|
||||
|
||||
if (!m_haveDelim) {
|
||||
rv = m_text.DetermineDelim(m_fileLoc);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
m_haveDelim = true;
|
||||
m_delim = m_text.GetDelim();
|
||||
}
|
||||
|
||||
bool fileExists;
|
||||
rv = m_fileLoc->Exists(&fileExists);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
if (!fileExists) {
|
||||
*pFound = false;
|
||||
*pStr = NS_xstrdup(&term);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsAutoString line;
|
||||
rv = nsTextAddress::ReadRecordNumber(m_fileLoc, line, index);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
nsString str;
|
||||
nsString field;
|
||||
int32_t fNum = 0;
|
||||
while (nsTextAddress::GetField(line, fNum, field, m_delim)) {
|
||||
if (fNum) str.Append(char16_t('\n'));
|
||||
SanitizeSampleData(field);
|
||||
str.Append(field);
|
||||
fNum++;
|
||||
field.Truncate();
|
||||
}
|
||||
|
||||
*pStr = ToNewUnicode(str);
|
||||
*pFound = true;
|
||||
|
||||
/* IMPORT_LOG1("Sample data: %S\n", str.get()); */
|
||||
} else {
|
||||
*pFound = false;
|
||||
*pStr = NS_xstrdup(&term);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::SetSampleLocation(nsIFile* pLocation) {
|
||||
NS_ENSURE_ARG_POINTER(pLocation);
|
||||
|
||||
m_fileLoc = pLocation;
|
||||
m_haveDelim = false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
void ImportAddressImpl::ClearSampleFile(void) {
|
||||
m_fileLoc = nullptr;
|
||||
m_haveDelim = false;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportAddressImpl::InitFieldMap(nsIImportFieldMap* fieldMap) {
|
||||
// Let's remember the last one the user used!
|
||||
// This should be normal for someone importing multiple times, it's usually
|
||||
// from the same file format.
|
||||
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIPrefBranch> prefs(do_GetService(NS_PREFSERVICE_CONTRACTID, &rv));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
nsCString prefStr;
|
||||
rv = prefs->GetCharPref("mailnews.import.text.fieldmap", prefStr);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
const char* pStr = prefStr.get();
|
||||
if (pStr) {
|
||||
fieldMap->SetFieldMapSize(0);
|
||||
long fNum;
|
||||
bool active;
|
||||
long fIndex = 0;
|
||||
while (*pStr) {
|
||||
while (*pStr && (*pStr != '+') && (*pStr != '-')) pStr++;
|
||||
if (*pStr == '+')
|
||||
active = true;
|
||||
else if (*pStr == '-')
|
||||
active = false;
|
||||
else
|
||||
break;
|
||||
fNum = 0;
|
||||
while (*pStr && ((*pStr < '0') || (*pStr > '9'))) pStr++;
|
||||
if (!(*pStr)) break;
|
||||
while (*pStr && (*pStr >= '0') && (*pStr <= '9')) {
|
||||
fNum *= 10;
|
||||
fNum += (*pStr - '0');
|
||||
pStr++;
|
||||
}
|
||||
while (*pStr && (*pStr != ',')) pStr++;
|
||||
if (*pStr == ',') pStr++;
|
||||
if (!active) {
|
||||
fNum *= -1; // Re-add the stripped minus sign.
|
||||
}
|
||||
fieldMap->SetFieldMap(-1, fNum);
|
||||
fieldMap->SetFieldActive(fIndex, active);
|
||||
fIndex++;
|
||||
}
|
||||
if (!fIndex) {
|
||||
int num;
|
||||
fieldMap->GetNumMozFields(&num);
|
||||
fieldMap->DefaultFieldMap(num);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Now also get the last used skip first record value.
|
||||
bool skipFirstRecord = false;
|
||||
rv = prefs->GetBoolPref("mailnews.import.text.skipfirstrecord",
|
||||
&skipFirstRecord);
|
||||
if (NS_SUCCEEDED(rv)) fieldMap->SetSkipFirstRecord(skipFirstRecord);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
void ImportAddressImpl::SaveFieldMap(nsIImportFieldMap* pMap) {
|
||||
if (!pMap) return;
|
||||
|
||||
int size;
|
||||
int index;
|
||||
bool active;
|
||||
nsCString str;
|
||||
|
||||
pMap->GetMapSize(&size);
|
||||
for (long i = 0; i < size; i++) {
|
||||
index = i;
|
||||
active = false;
|
||||
pMap->GetFieldMap(i, &index);
|
||||
pMap->GetFieldActive(i, &active);
|
||||
if (active)
|
||||
str.Append('+');
|
||||
else
|
||||
str.Append('-');
|
||||
|
||||
str.AppendInt(index);
|
||||
str.Append(',');
|
||||
}
|
||||
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIPrefBranch> prefs(do_GetService(NS_PREFSERVICE_CONTRACTID, &rv));
|
||||
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
nsCString prefStr;
|
||||
rv = prefs->GetCharPref("mailnews.import.text.fieldmap", prefStr);
|
||||
if (NS_FAILED(rv) || !str.Equals(prefStr))
|
||||
rv = prefs->SetCharPref("mailnews.import.text.fieldmap", str);
|
||||
}
|
||||
|
||||
// Now also save last used skip first record value.
|
||||
bool skipFirstRecord = false;
|
||||
rv = pMap->GetSkipFirstRecord(&skipFirstRecord);
|
||||
if (NS_SUCCEEDED(rv))
|
||||
prefs->SetBoolPref("mailnews.import.text.skipfirstrecord", skipFirstRecord);
|
||||
}
|
|
@ -1,40 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsTextImport_h___
|
||||
#define nsTextImport_h___
|
||||
|
||||
#include "nsIImportModule.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIStringBundle.h"
|
||||
|
||||
#define NS_TEXTIMPORT_CID \
|
||||
{ /* A5991D01-ADA7-11d3-A9C2-00A0CC26DA63 */ \
|
||||
0xa5991d01, 0xada7, 0x11d3, { \
|
||||
0xa9, 0xc2, 0x0, 0xa0, 0xcc, 0x26, 0xda, 0x63 \
|
||||
} \
|
||||
}
|
||||
|
||||
#define kTextSupportsString "addressbook"
|
||||
|
||||
class nsTextImport : public nsIImportModule {
|
||||
public:
|
||||
nsTextImport();
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
// we support the nsIImportModule interface
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
NS_DECL_NSIIMPORTMODULE
|
||||
|
||||
protected:
|
||||
virtual ~nsTextImport();
|
||||
nsCOMPtr<nsIStringBundle> m_stringBundle;
|
||||
};
|
||||
|
||||
#endif /* nsTextImport_h___ */
|
|
@ -1,326 +0,0 @@
|
|||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
/*
|
||||
VCard import addressbook interfaces
|
||||
*/
|
||||
#include "nscore.h"
|
||||
#include "nsIFile.h"
|
||||
#include "nsIImportABDescriptor.h"
|
||||
#include "nsIImportAddressBooks.h"
|
||||
#include "nsIImportFieldMap.h"
|
||||
#include "nsIImportGeneric.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIImportService.h"
|
||||
#include "nsIFile.h"
|
||||
#include "nsImportStringBundle.h"
|
||||
#include "nsMsgUtils.h"
|
||||
#include "nsComponentManagerUtils.h"
|
||||
#include "nsServiceManagerUtils.h"
|
||||
#include "nsTextFormatter.h"
|
||||
#include "nsVCardAddress.h"
|
||||
#include "nsVCardImport.h"
|
||||
|
||||
class ImportVCardAddressImpl : public nsIImportAddressBooks {
|
||||
public:
|
||||
explicit ImportVCardAddressImpl(nsIStringBundle* aStringBundle);
|
||||
|
||||
static nsresult Create(nsIImportAddressBooks** aImport,
|
||||
nsIStringBundle* aStringBundle);
|
||||
|
||||
// nsISupports interface
|
||||
NS_DECL_THREADSAFE_ISUPPORTS
|
||||
|
||||
// nsIImportAddressBooks interface
|
||||
|
||||
// TODO: support multiple vCard files in future - shouldn't be too hard,
|
||||
// since you just import each file in turn.
|
||||
NS_IMETHOD GetSupportsMultiple(bool* _retval) override {
|
||||
*_retval = false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHOD GetAutoFind(char16_t** description, bool* _retval) override;
|
||||
|
||||
NS_IMETHOD GetNeedsFieldMap(nsIFile* location, bool* _retval) override {
|
||||
*_retval = false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHOD GetDefaultLocation(nsIFile** location, bool* found,
|
||||
bool* userVerify) override;
|
||||
|
||||
NS_IMETHOD FindAddressBooks(
|
||||
nsIFile* location,
|
||||
nsTArray<RefPtr<nsIImportABDescriptor>>& books) override;
|
||||
|
||||
NS_IMETHOD InitFieldMap(nsIImportFieldMap* fieldMap) override {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
NS_IMETHOD ImportAddressBook(nsIImportABDescriptor* source,
|
||||
nsIAbDirectory* destination,
|
||||
nsIImportFieldMap* fieldMap,
|
||||
nsISupports* aSupportService,
|
||||
char16_t** errorLog, char16_t** successLog,
|
||||
bool* fatalError) override;
|
||||
|
||||
NS_IMETHOD GetImportProgress(uint32_t* _retval) override;
|
||||
|
||||
NS_IMETHOD GetSampleData(int32_t index, bool* pFound,
|
||||
char16_t** pStr) override {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
NS_IMETHOD SetSampleLocation(nsIFile*) override { return NS_ERROR_FAILURE; }
|
||||
|
||||
private:
|
||||
virtual ~ImportVCardAddressImpl();
|
||||
static void ReportSuccess(nsString& name, nsString* pStream,
|
||||
nsIStringBundle* pBundle);
|
||||
static void SetLogs(nsString& success, nsString& error, char16_t** pError,
|
||||
char16_t** pSuccess);
|
||||
static void ReportError(const char* errorName, nsString& name,
|
||||
nsString* pStream, nsIStringBundle* pBundle);
|
||||
|
||||
private:
|
||||
nsVCardAddress m_vCard;
|
||||
nsCOMPtr<nsIFile> m_fileLoc;
|
||||
uint32_t m_bytesImported;
|
||||
nsCOMPtr<nsIStringBundle> m_notProxyBundle;
|
||||
};
|
||||
|
||||
nsVCardImport::nsVCardImport() {
|
||||
nsImportStringBundle::GetStringBundle(VCARDIMPORT_MSGS_URL,
|
||||
getter_AddRefs(m_stringBundle));
|
||||
|
||||
IMPORT_LOG0("nsVCardImport Module Created\n");
|
||||
}
|
||||
|
||||
nsVCardImport::~nsVCardImport() {
|
||||
IMPORT_LOG0("nsVCardImport Module Deleted\n");
|
||||
}
|
||||
|
||||
NS_IMPL_ISUPPORTS(nsVCardImport, nsIImportModule)
|
||||
|
||||
NS_IMETHODIMP nsVCardImport::GetImportInterface(const char* pImportType,
|
||||
nsISupports** ppInterface) {
|
||||
NS_ENSURE_ARG_POINTER(pImportType);
|
||||
NS_ENSURE_ARG_POINTER(ppInterface);
|
||||
*ppInterface = nullptr;
|
||||
if (!strcmp(pImportType, "addressbook")) {
|
||||
nsresult rv;
|
||||
// create the nsIImportMail interface and return it!
|
||||
nsCOMPtr<nsIImportAddressBooks> pAddress;
|
||||
nsCOMPtr<nsIImportGeneric> pGeneric;
|
||||
rv = ImportVCardAddressImpl::Create(getter_AddRefs(pAddress),
|
||||
m_stringBundle);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
nsCOMPtr<nsIImportService> impSvc(
|
||||
do_GetService(NS_IMPORTSERVICE_CONTRACTID, &rv));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = impSvc->CreateNewGenericAddressBooks(getter_AddRefs(pGeneric));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
pGeneric->SetData("addressInterface", pAddress);
|
||||
nsCOMPtr<nsISupports> pInterface(do_QueryInterface(pGeneric));
|
||||
pInterface.forget(ppInterface);
|
||||
}
|
||||
}
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
|
||||
nsresult ImportVCardAddressImpl::Create(nsIImportAddressBooks** aImport,
|
||||
nsIStringBundle* aStringBundle) {
|
||||
NS_ENSURE_ARG_POINTER(aImport);
|
||||
NS_ADDREF(*aImport = new ImportVCardAddressImpl(aStringBundle));
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
ImportVCardAddressImpl::ImportVCardAddressImpl(nsIStringBundle* aStringBundle)
|
||||
: m_notProxyBundle(aStringBundle) {}
|
||||
|
||||
ImportVCardAddressImpl::~ImportVCardAddressImpl() {}
|
||||
|
||||
NS_IMPL_ISUPPORTS(ImportVCardAddressImpl, nsIImportAddressBooks)
|
||||
|
||||
NS_IMETHODIMP ImportVCardAddressImpl::GetAutoFind(char16_t** addrDescription,
|
||||
bool* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(addrDescription);
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
|
||||
nsString str;
|
||||
*_retval = false;
|
||||
|
||||
if (!m_notProxyBundle) return NS_ERROR_FAILURE;
|
||||
|
||||
nsImportStringBundle::GetStringByName("vCardImportAddressName",
|
||||
m_notProxyBundle, str);
|
||||
*addrDescription = ToNewUnicode(str);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportVCardAddressImpl::GetDefaultLocation(nsIFile** ppLoc,
|
||||
bool* found,
|
||||
bool* userVerify) {
|
||||
NS_ENSURE_ARG_POINTER(found);
|
||||
NS_ENSURE_ARG_POINTER(ppLoc);
|
||||
NS_ENSURE_ARG_POINTER(userVerify);
|
||||
|
||||
*ppLoc = nullptr;
|
||||
*found = false;
|
||||
*userVerify = true;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportVCardAddressImpl::FindAddressBooks(
|
||||
nsIFile* pLoc, nsTArray<RefPtr<nsIImportABDescriptor>>& books) {
|
||||
NS_ENSURE_ARG_POINTER(pLoc);
|
||||
|
||||
books.Clear();
|
||||
bool exists = false;
|
||||
nsresult rv = pLoc->Exists(&exists);
|
||||
if (NS_FAILED(rv) || !exists) return NS_ERROR_FAILURE;
|
||||
|
||||
bool isFile = false;
|
||||
rv = pLoc->IsFile(&isFile);
|
||||
if (NS_FAILED(rv) || !isFile) return NS_ERROR_FAILURE;
|
||||
|
||||
m_fileLoc = pLoc;
|
||||
|
||||
/* Build an address book descriptor based on the file passed in! */
|
||||
nsString name;
|
||||
m_fileLoc->GetLeafName(name);
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Failed getting leaf name of file\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
int32_t idx = name.RFindChar('.');
|
||||
if ((idx != -1) && (idx > 0) && ((name.Length() - idx - 1) < 5)) {
|
||||
name.SetLength(idx);
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIImportABDescriptor> desc;
|
||||
nsCOMPtr<nsIImportService> impSvc(
|
||||
do_GetService(NS_IMPORTSERVICE_CONTRACTID, &rv));
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0("*** Failed to obtain the import service\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = impSvc->CreateNewABDescriptor(getter_AddRefs(desc));
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
int64_t sz = 0;
|
||||
pLoc->GetFileSize(&sz);
|
||||
desc->SetPreferredName(name);
|
||||
desc->SetSize((uint32_t)sz);
|
||||
desc->SetAbFile(m_fileLoc);
|
||||
books.AppendElement(desc);
|
||||
}
|
||||
if (NS_FAILED(rv)) {
|
||||
IMPORT_LOG0(
|
||||
"*** Error creating address book descriptor for vCard import\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
void ImportVCardAddressImpl::ReportSuccess(nsString& name, nsString* pStream,
|
||||
nsIStringBundle* pBundle) {
|
||||
if (!pStream) return;
|
||||
|
||||
// load the success string
|
||||
char16_t* pFmt = nsImportStringBundle::GetStringByName(
|
||||
"vCardImportAddressSuccess", pBundle);
|
||||
|
||||
nsString pText;
|
||||
nsTextFormatter::ssprintf(pText, pFmt, name.get());
|
||||
pStream->Append(pText);
|
||||
free(pFmt);
|
||||
pStream->Append(char16_t('\n'));
|
||||
}
|
||||
|
||||
void ImportVCardAddressImpl::ReportError(const char* errorName, nsString& name,
|
||||
nsString* pStream,
|
||||
nsIStringBundle* pBundle) {
|
||||
if (!pStream) return;
|
||||
|
||||
// load the error string
|
||||
char16_t* pFmt = nsImportStringBundle::GetStringByName(errorName, pBundle);
|
||||
nsString pText;
|
||||
nsTextFormatter::ssprintf(pText, pFmt, name.get());
|
||||
pStream->Append(pText);
|
||||
free(pFmt);
|
||||
pStream->Append(char16_t('\n'));
|
||||
}
|
||||
|
||||
void ImportVCardAddressImpl::SetLogs(nsString& success, nsString& error,
|
||||
char16_t** pError, char16_t** pSuccess) {
|
||||
if (pError) *pError = ToNewUnicode(error);
|
||||
if (pSuccess) *pSuccess = ToNewUnicode(success);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportVCardAddressImpl::ImportAddressBook(
|
||||
nsIImportABDescriptor* pSource, nsIAbDirectory* pDestination,
|
||||
nsIImportFieldMap* fieldMap, nsISupports* aSupportService,
|
||||
char16_t** pErrorLog, char16_t** pSuccessLog, bool* fatalError) {
|
||||
NS_ENSURE_ARG_POINTER(pSource);
|
||||
NS_ENSURE_ARG_POINTER(pDestination);
|
||||
NS_ENSURE_ARG_POINTER(fatalError);
|
||||
|
||||
if (!m_notProxyBundle) return NS_ERROR_FAILURE;
|
||||
|
||||
m_bytesImported = 0;
|
||||
nsString success, error;
|
||||
bool addrAbort = false;
|
||||
nsString name;
|
||||
pSource->GetPreferredName(name);
|
||||
|
||||
uint32_t addressSize = 0;
|
||||
pSource->GetSize(&addressSize);
|
||||
if (addressSize == 0) {
|
||||
IMPORT_LOG0("Address book size is 0, skipping import.\n");
|
||||
ReportSuccess(name, &success, m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIFile> inFile;
|
||||
if (NS_FAILED(pSource->GetAbFile(getter_AddRefs(inFile)))) {
|
||||
ReportError("vCardImportAddressBadSourceFile", name, &error,
|
||||
m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
if (!aSupportService) {
|
||||
IMPORT_LOG0("Missing support service to import call\n");
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsresult rv = m_vCard.ImportAddresses(&addrAbort, name.get(), inFile,
|
||||
pDestination, error, &m_bytesImported);
|
||||
|
||||
if (NS_SUCCEEDED(rv) && error.IsEmpty()) {
|
||||
ReportSuccess(name, &success, m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
} else {
|
||||
ReportError("vCardImportAddressConvertError", name, &error,
|
||||
m_notProxyBundle);
|
||||
SetLogs(success, error, pErrorLog, pSuccessLog);
|
||||
}
|
||||
|
||||
IMPORT_LOG0("*** VCard address import done\n");
|
||||
return rv;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP ImportVCardAddressImpl::GetImportProgress(uint32_t* _retval) {
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
*_retval = m_bytesImported;
|
||||
return NS_OK;
|
||||
}
|
|
@ -1,39 +0,0 @@
|
|||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef nsVCardImport_h___
|
||||
#define nsVCardImport_h___
|
||||
|
||||
#include "nsIImportModule.h"
|
||||
#include "nsIStringBundle.h"
|
||||
#include "nsCOMPtr.h"
|
||||
|
||||
#define NS_VCARDIMPORT_CID \
|
||||
{ /* 0EB034A3-964A-4E2F-92EBCC55D9AE9DD2 */ \
|
||||
0x0eb034a3, 0x964a, 0x4e2f, { \
|
||||
0x92, 0xeb, 0xcc, 0x55, 0xd9, 0xae, 0x9d, 0xd2 \
|
||||
} \
|
||||
}
|
||||
|
||||
#define VCARDIMPORT_MSGS_URL \
|
||||
"chrome://messenger/locale/vCardImportMsgs.properties"
|
||||
|
||||
class nsVCardImport : public nsIImportModule {
|
||||
public:
|
||||
nsVCardImport();
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
// we support the nsIImportModule interface
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
NS_DECL_NSIIMPORTMODULE
|
||||
|
||||
protected:
|
||||
virtual ~nsVCardImport();
|
||||
nsCOMPtr<nsIStringBundle> m_stringBundle;
|
||||
};
|
||||
|
||||
#endif /* nsVCardImport_h___ */
|
Загрузка…
Ссылка в новой задаче