From e2b4d331b166dc74b39cbbbb78b5c09b9a2a9ba3 Mon Sep 17 00:00:00 2001 From: "ftang%netscape.com" Date: Fri, 10 Sep 1999 19:04:14 +0000 Subject: [PATCH] add new implementation to UCS2 encoder git-svn-id: svn://10.0.0.236/trunk@46821 18797224-902f-48f8-a5cc-f745e15eee43 --- .../intl/uconv/ucvlatin/nsUCS2BEToUnicode.cpp | 9 - mozilla/intl/uconv/ucvlatin/nsUCvLatinDll.cpp | 28 ++- .../intl/uconv/ucvlatin/nsUCvLatinSupport.cpp | 86 +++++---- .../intl/uconv/ucvlatin/nsUCvLatinSupport.h | 22 ++- .../intl/uconv/ucvlatin/nsUnicodeToUCS2BE.cpp | 181 +++++++++++++++++- .../intl/uconv/ucvlatin/nsUnicodeToUCS2BE.h | 4 + 6 files changed, 269 insertions(+), 61 deletions(-) diff --git a/mozilla/intl/uconv/ucvlatin/nsUCS2BEToUnicode.cpp b/mozilla/intl/uconv/ucvlatin/nsUCS2BEToUnicode.cpp index ce9cdcb373c..6855e54feb4 100644 --- a/mozilla/intl/uconv/ucvlatin/nsUCS2BEToUnicode.cpp +++ b/mozilla/intl/uconv/ucvlatin/nsUCS2BEToUnicode.cpp @@ -76,10 +76,6 @@ public: NS_IMETHOD Convert(const char * aSrc, PRInt32 * aSrcLength, PRUnichar * aDest, PRInt32 * aDestLength); NS_IMETHOD Reset(); - /** - * Static class constructor. - */ - static nsresult CreateInstance(nsISupports **aResult); protected: //-------------------------------------------------------------------- @@ -92,11 +88,6 @@ protected: PRUint8 mData; }; -nsresult nsUTF16SameEndianToUnicode::CreateInstance(nsISupports ** aResult) -{ - *aResult = new nsUTF16SameEndianToUnicode(); - return (*aResult == NULL)? NS_ERROR_OUT_OF_MEMORY : NS_OK; -} //---------------------------------------------------------------------- // Subclassing of nsTableDecoderSupport class [implementation] diff --git a/mozilla/intl/uconv/ucvlatin/nsUCvLatinDll.cpp b/mozilla/intl/uconv/ucvlatin/nsUCvLatinDll.cpp index 5afd6759e09..82a30046185 100644 --- a/mozilla/intl/uconv/ucvlatin/nsUCvLatinDll.cpp +++ b/mozilla/intl/uconv/ucvlatin/nsUCvLatinDll.cpp @@ -443,7 +443,7 @@ FactoryData g_FactoryData[] = "Unicode" }, { - &kUTF32LEToUnicodeCID, + &kUTF16LEToUnicodeCID, //nsUCS2LEToUnicode::CreateInstance, NEW_UTF16LEToUnicode, "UTF-16LE", @@ -745,16 +745,24 @@ FactoryData g_FactoryData[] = }, { &kUnicodeToUTF16BECID, - nsUnicodeToUCS2BE::CreateInstance, + // nsUnicodeToUCS2BE::CreateInstance, + NEW_UnicodeToUTF16BE, "Unicode", "UTF-16BE" }, { - &kUnicodeToUTF16CID, - nsUnicodeToUCS2LE::CreateInstance, + &kUnicodeToUTF16LECID, + // nsUnicodeToUCS2LE::CreateInstance, + NEW_UnicodeToUTF16LE, "Unicode", "UTF-16LE" }, + { + &kUnicodeToUTF16CID, + NEW_UnicodeToUTF16, + "Unicode", + "UTF-16" + }, { &kUnicodeToUTF32BECID, nsUnicodeToUCS4BE::CreateInstance, @@ -793,8 +801,8 @@ FactoryData g_FactoryData[] = } }; -#define ARRAY_SIZE(_array) \ - (sizeof(_array) / sizeof(_array[0])) +#define ARRAY_SIZE \ + (sizeof(g_FactoryData) / sizeof(FactoryData)) //---------------------------------------------------------------------- // Class nsConverterFactory [declaration] @@ -861,7 +869,7 @@ extern "C" NS_EXPORT nsresult NSGetFactory(nsISupports* aServMgr, nsConverterFactory * fac; FactoryData * data; - for (PRUint32 i=0; imCID))) { fac = new nsConverterFactory(data); @@ -910,7 +918,7 @@ extern "C" NS_EXPORT nsresult NSRegisterSelf(nsISupports * aServMgr, char name[128]; char progid[128]; - for (i=0; iRegisterComponent(*(g_FactoryData[i].mCID), NULL, NULL, path, PR_TRUE, PR_TRUE); if(NS_FAILED(rv) && (NS_ERROR_FACTORY_EXISTS != rv)) goto done; @@ -988,7 +996,7 @@ extern "C" NS_EXPORT nsresult NSUnregisterSelf(nsISupports* aServMgr, const char (nsISupports**)&compMgr); if (NS_FAILED(rv)) return rv; - for (PRUint32 i=0; iUnregisterComponent(*(g_FactoryData[i].mCID), path); if(NS_FAILED(rv)) goto done; } diff --git a/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.cpp b/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.cpp index f5bc6f07bc1..456f4d16069 100644 --- a/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.cpp +++ b/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.cpp @@ -335,6 +335,54 @@ NS_IMETHODIMP nsOneByteDecoderSupport::Reset() return NS_OK; } +//---------------------------------------------------------------------- +// Class nsBasicEncoder [implementation] +nsBasicEncoder::nsBasicEncoder() +{ + NS_INIT_REFCNT(); + PR_AtomicIncrement(&g_InstanceCount); +} + +nsBasicEncoder::~nsBasicEncoder() +{ + PR_AtomicDecrement(&g_InstanceCount); +} + +//---------------------------------------------------------------------- +// Interface nsISupports [implementation] + +NS_IMPL_ADDREF(nsBasicEncoder); +NS_IMPL_RELEASE(nsBasicEncoder); + +nsresult nsBasicEncoder::QueryInterface(REFNSIID aIID, + void** aInstancePtr) +{ + if (NULL == aInstancePtr) { + return NS_ERROR_NULL_POINTER; + } + + *aInstancePtr = NULL; + + static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID); + + if (aIID.Equals(kIUnicodeEncoderIID)) { + *aInstancePtr = (void*) ((nsIUnicodeEncoder*)this); + NS_ADDREF_THIS(); + return NS_OK; + } + if (aIID.Equals(nsICharRepresentable::GetIID())) { + *aInstancePtr = (void*) ((nsICharRepresentable*)this); + NS_ADDREF_THIS(); + return NS_OK; + } + if (aIID.Equals(kISupportsIID)) { + *aInstancePtr = (void*) ((nsISupports*)((nsIUnicodeEncoder*)this)); + NS_ADDREF_THIS(); + return NS_OK; + } + + return NS_NOINTERFACE; +} //---------------------------------------------------------------------- // Class nsEncoderSupport [implementation] @@ -348,15 +396,12 @@ nsEncoderSupport::nsEncoderSupport() mErrEncoder = NULL; Reset(); - NS_INIT_REFCNT(); - PR_AtomicIncrement(&g_InstanceCount); } nsEncoderSupport::~nsEncoderSupport() { delete [] mBuffer; NS_IF_RELEASE(mErrEncoder); - PR_AtomicDecrement(&g_InstanceCount); } NS_IMETHODIMP nsEncoderSupport::ConvertNoBuff(const PRUnichar * aSrc, @@ -436,41 +481,6 @@ nsresult nsEncoderSupport::FlushBuffer(char ** aDest, const char * aDestEnd) return res; } -//---------------------------------------------------------------------- -// Interface nsISupports [implementation] - -NS_IMPL_ADDREF(nsEncoderSupport); -NS_IMPL_RELEASE(nsEncoderSupport); - -nsresult nsEncoderSupport::QueryInterface(REFNSIID aIID, - void** aInstancePtr) -{ - if (NULL == aInstancePtr) { - return NS_ERROR_NULL_POINTER; - } - - *aInstancePtr = NULL; - - static NS_DEFINE_IID(kISupportsIID, NS_ISUPPORTS_IID); - - if (aIID.Equals(kIUnicodeEncoderIID)) { - *aInstancePtr = (void*) ((nsIUnicodeEncoder*)this); - NS_ADDREF_THIS(); - return NS_OK; - } - if (aIID.Equals(nsICharRepresentable::GetIID())) { - *aInstancePtr = (void*) ((nsICharRepresentable*)this); - NS_ADDREF_THIS(); - return NS_OK; - } - if (aIID.Equals(kISupportsIID)) { - *aInstancePtr = (void*) ((nsISupports*)((nsIUnicodeEncoder*)this)); - NS_ADDREF_THIS(); - return NS_OK; - } - - return NS_NOINTERFACE; -} //---------------------------------------------------------------------- // Interface nsIUnicodeEncoder [implementation] diff --git a/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.h b/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.h index a48bfbaf827..1ea66f79332 100644 --- a/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.h +++ b/mozilla/intl/uconv/ucvlatin/nsUCvLatinSupport.h @@ -235,6 +235,25 @@ protected: NS_IMETHOD Reset(); }; +//---------------------------------------------------------------------- +// Class nsBasicEncoder [declaration] + +class nsBasicEncoder : public nsIUnicodeEncoder, public nsICharRepresentable +{ + NS_DECL_ISUPPORTS + +public: + /** + * Class constructor. + */ + nsBasicEncoder(); + + /** + * Class destructor. + */ + virtual ~nsBasicEncoder(); + +}; //---------------------------------------------------------------------- // Class nsEncoderSupport [declaration] @@ -249,9 +268,8 @@ protected: * @created 17/Feb/1999 * @author Catalin Rotaru [CATA] */ -class nsEncoderSupport : public nsIUnicodeEncoder, public nsICharRepresentable +class nsEncoderSupport : public nsBasicEncoder { - NS_DECL_ISUPPORTS protected: diff --git a/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.cpp b/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.cpp index e0757cae5c0..b78095dbf5e 100644 --- a/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.cpp +++ b/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.cpp @@ -1,4 +1,4 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- +const /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- * * The contents of this file are subject to the Netscape Public License * Version 1.0 (the "License"); you may not use this file except in @@ -59,6 +59,183 @@ NS_IMETHODIMP nsUnicodeToUCS2BE::GetMaxLength(const PRUnichar * aSrc, } NS_IMETHODIMP nsUnicodeToUCS2BE::FillInfo(PRUint32 *aInfo) { - memset(aInfo, 0xFF, (0x10000L >> 3)); + ::memset(aInfo, 0xFF, (0x10000L >> 3)); return NS_OK; } + + + +class nsUnicodeToUTF16SameEndian: public nsBasicEncoder +{ +public: + /** + * Class constructor. + */ + nsUnicodeToUTF16SameEndian( PRUnichar aBOM ) + { + mBOM = aBOM; + }; + + /** + * Class destructor. + */ + virtual ~nsUnicodeToUTF16SameEndian() {}; + + //-------------------------------------------------------------------- + // Interface nsIUnicodeEncoder [declaration] + + NS_IMETHOD Convert(const PRUnichar * aSrc, PRInt32 * aSrcLength, + char * aDest, PRInt32 * aDestLength) + { + PRInt32 srcInLen = *aSrcLength; + PRInt32 destInLen = *aDestLength; + PRInt32 srcOutLen = 0; + PRInt32 destOutLen = 0; + PRInt32 copyCharLen; + PRUnichar *p = (PRUnichar*)aDest; + + // Handle BOM if necessary + if(0!=mBOM) + { + if(destInLen <2) + goto needmoreoutput; + + *p++ = mBOM; + mBOM = 0; + destOutLen +=2; + } + // find out the length of copy + + copyCharLen = srcInLen; + if(copyCharLen > (destInLen - destOutLen) / 2) { + copyCharLen = (destInLen - destOutLen) / 2; + } + + // copy the data by swaping + CopyData((char*)p , aSrc, copyCharLen ); + + srcOutLen += copyCharLen; + destOutLen += copyCharLen * 2; + if(copyCharLen < srcInLen) + goto needmoreoutput; + + *aSrcLength = srcOutLen; + *aDestLength = destOutLen; + return NS_OK; + + needmoreoutput: + *aSrcLength = srcOutLen; + *aDestLength = destOutLen; + return NS_OK_UENC_MOREOUTPUT; + }; + + NS_IMETHOD GetMaxLength(const PRUnichar * aSrc, PRInt32 aSrcLength, + PRInt32 * aDestLength) + { + if(0 != mBOM) + *aDestLength = 2*(aSrcLength+1); + else + *aDestLength = 2*aSrcLength; + return NS_OK_UENC_EXACTLENGTH; + }; + NS_IMETHOD Finish(char * aDest, PRInt32 * aDestLength) + { + if(0 != mBOM) + { + if(*aDestLength >= 2) + { + *((PRUnichar*)aDest)= mBOM; + mBOM=0; + *aDestLength = 2; + return NS_OK; + } else { + *aDestLength = 0; + return NS_OK; // xxx should be error + } + } else { + *aDestLength = 0; + return NS_OK; + } + }; + NS_IMETHOD Reset() + { + mBOM = 0; + return NS_OK; + }; + NS_IMETHOD SetOutputErrorBehavior(PRInt32 aBehavior, + nsIUnicharEncoder * aEncoder, PRUnichar aChar) + { + return NS_OK; + }; + + //-------------------------------------------------------------------- + // Interface nsICharRepresentable [declaration] + NS_IMETHOD FillInfo(PRUint32 *aInfo) + { + ::memset(aInfo, 0xFF, (0x10000L >> 3)); + return NS_OK; + }; +protected: + PRUnichar mBOM; + virtual void CopyData(char* aDest, const PRUnichar* aSrc, PRInt32 aLen ) + { + ::memcpy(aDest, (void*) aSrc, aLen * 2); + }; +}; + +class nsUnicodeToUTF16DiffEndian: public nsUnicodeToUTF16SameEndian +{ +public: + /** + * Class constructor. + */ + nsUnicodeToUTF16DiffEndian( PRUnichar aBOM ) + : nsUnicodeToUTF16SameEndian(aBOM ) { }; + + /** + * Class destructor. + */ + virtual ~nsUnicodeToUTF16DiffEndian() {}; + + //-------------------------------------------------------------------- + // Interface nsIUnicodeEncoder [declaration] + +protected: + virtual void CopyData(char* aDest, const PRUnichar* aSrc, PRInt32 aLen ) + { + PRUnichar *p = (PRUnichar*) aDest; + // copy the data by swaping + for(PRInt32 i; i < aLen; i++) + { + PRUnichar aChar = *aSrc++; + *p++ = (0x00FF & (aChar >> 8)) | (0xFF00 & (aChar << 8)); + } + }; +}; +static char BOM[] = {(char)0xfe, (char)0xff}; +#define IsBigEndian() (0xFEFF == *((PRUint16*)BOM)) + +nsresult NEW_UnicodeToUTF16BE(nsISupports **aResult) +{ + if(IsBigEndian()) { + *aResult = (nsIUnicodeEncoder*)new nsUnicodeToUTF16SameEndian(0); + } else { + *aResult = (nsIUnicodeEncoder*)new nsUnicodeToUTF16DiffEndian(0); + } + return (NULL == *aResult) ? NS_ERROR_OUT_OF_MEMORY : NS_OK; +} +nsresult NEW_UnicodeToUTF16LE(nsISupports **aResult) +{ + if(IsBigEndian()) { + *aResult = (nsIUnicodeEncoder*)new nsUnicodeToUTF16DiffEndian(0); + } else { + *aResult = (nsIUnicodeEncoder*)new nsUnicodeToUTF16SameEndian(0); + } + return (NULL == *aResult) ? NS_ERROR_OUT_OF_MEMORY : NS_OK; +} +nsresult NEW_UnicodeToUTF16(nsISupports **aResult) +{ + *aResult = (nsIUnicodeEncoder*)new nsUnicodeToUTF16SameEndian(0xFEFF); + return (NULL == *aResult) ? NS_ERROR_OUT_OF_MEMORY : NS_OK; +} + diff --git a/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.h b/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.h index 2f1292f3c2b..72f8d6e3f7a 100644 --- a/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.h +++ b/mozilla/intl/uconv/ucvlatin/nsUnicodeToUCS2BE.h @@ -56,4 +56,8 @@ protected: PRInt32 * aDestLength); }; +nsresult NEW_UnicodeToUTF16BE(nsISupports **Result); +nsresult NEW_UnicodeToUTF16LE(nsISupports **Result); +nsresult NEW_UnicodeToUTF16(nsISupports **Result); + #endif /* nsUnicodeToUCS2BE_h___ */