Back to index

lightning-sunbird  0.9+nobinonly
nsUnicodeToISO2022JP.cpp
Go to the documentation of this file.
00001 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
00002 /* ***** BEGIN LICENSE BLOCK *****
00003  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
00004  *
00005  * The contents of this file are subject to the Mozilla Public License Version
00006  * 1.1 (the "License"); you may not use this file except in compliance with
00007  * the License. You may obtain a copy of the License at
00008  * http://www.mozilla.org/MPL/
00009  *
00010  * Software distributed under the License is distributed on an "AS IS" basis,
00011  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
00012  * for the specific language governing rights and limitations under the
00013  * License.
00014  *
00015  * The Original Code is Mozilla Communicator client code.
00016  *
00017  * The Initial Developer of the Original Code is
00018  * Netscape Communications Corporation.
00019  * Portions created by the Initial Developer are Copyright (C) 1998
00020  * the Initial Developer. All Rights Reserved.
00021  *
00022  * Contributor(s):
00023  *
00024  * Alternatively, the contents of this file may be used under the terms of
00025  * either of the GNU General Public License Version 2 or later (the "GPL"),
00026  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
00027  * in which case the provisions of the GPL or the LGPL are applicable instead
00028  * of those above. If you wish to allow use of your version of this file only
00029  * under the terms of either the GPL or the LGPL, and not to allow others to
00030  * use your version of this file under the terms of the MPL, indicate your
00031  * decision by deleting the provisions above and replace them with the notice
00032  * and other provisions required by the GPL or the LGPL. If you do not delete
00033  * the provisions above, a recipient may use your version of this file under
00034  * the terms of any one of the MPL, the GPL or the LGPL.
00035  *
00036  * ***** END LICENSE BLOCK ***** */
00037 
00038 #include "nsUnicodeToISO2022JP.h"
00039 #include "nsIComponentManager.h"
00040 #include "nsUCVJADll.h"
00041 
00042 // Class ID for our UnicodeEncoderHelper implementation
00043 // {1767FC50-CAA4-11d2-8AA9-00600811A836}
00044 static NS_DEFINE_CID(kUnicodeEncodeHelperCID, NS_UNICODEENCODEHELPER_CID);
00045 
00046 //----------------------------------------------------------------------
00047 // Global functions and data [declaration]
00048 
00049 static const PRUint16 g_ufAsciiMapping [] = {
00050   0x0001, 0x0004, 0x0005, 0x0008, 0x0000, 0x0000, 0x007F, 0x0000
00051 };
00052 
00053 static const PRInt16 g_ufAsciiShift [] =  { 
00054   0, u1ByteCharset, 
00055   ShiftCell(0,0,0,0,0,0,0,0) 
00056 };
00057 
00058 static const PRInt16 g_uf0201Shift [] =  {
00059   2, u1ByteCharset ,
00060   ShiftCell(u1ByteChar,   1, 0x00, 0x7F, 0x00, 0x00, 0x00, 0x7F),
00061   ShiftCell(u1ByteChar,   1, 0xA1, 0xDF, 0x00, 0xA1, 0x00, 0xDF),
00062 };
00063 
00064 static const PRInt16 g_uf0208Shift [] =  {
00065   0, u2BytesCharset,
00066   ShiftCell(0,0,0,0,0,0,0,0)
00067 };
00068 
00069 #define SIZE_OF_TABLES 5
00070 static const PRUint16 * g_ufMappingTables[SIZE_OF_TABLES] = {
00071   g_ufAsciiMapping,             // ASCII           ISOREG 6
00072   g_uf0201GLMapping,            // JIS X 0201-1976 ISOREG 14
00073   g_uf0208Mapping,              // JIS X 0208-1983 ISOREG 87
00074   g_uf0208extMapping,           // JIS X 0208 - cp932 ext
00075   g_uf0208Mapping,              // JIS X 0208-1978 ISOREG 42
00076 };
00077 
00078 static const PRInt16 * g_ufShiftTables[SIZE_OF_TABLES] = {
00079   g_ufAsciiShift,               // ASCII           ISOREG 6
00080   g_uf0201Shift,                // JIS X 0201-1976 ISOREG 14
00081   g_uf0208Shift,                // JIS X 0208-1983 ISOREG 87
00082   g_uf0208Shift,                // JIS X 0208- cp932 ext
00083   g_uf0208Shift,                // JIS X 0208-1978 ISOREG 42
00084 };
00085 
00086 //----------------------------------------------------------------------
00087 // Class nsUnicodeToISO2022JP [implementation]
00088 
00089 // worst case max length: 
00090 //  1  2 3  4  5  6  7 8
00091 // ESC $ B XX XX ESC ( B
00092 nsUnicodeToISO2022JP::nsUnicodeToISO2022JP() 
00093 : nsEncoderSupport(8)
00094 {
00095   mHelper = NULL;
00096   Reset();
00097 }
00098 
00099 nsUnicodeToISO2022JP::~nsUnicodeToISO2022JP() 
00100 {
00101   NS_IF_RELEASE(mHelper);
00102 }
00103 
00104 nsresult nsUnicodeToISO2022JP::ChangeCharset(PRInt32 aCharset,
00105                                              char * aDest, 
00106                                              PRInt32 * aDestLength)
00107 {
00108   // both 2 and 3 generate the same escape sequence. 2 is for
00109   // the standard JISx0208 table, and 3 is for theCP932 extensions
00110   // therefore, we treat them as the same one.
00111   if(((2 == aCharset) && ( 3 == mCharset)) ||
00112      ((3 == aCharset) && ( 2 == mCharset)) )
00113   {
00114     mCharset = aCharset;
00115   }
00116 
00117   if(aCharset == mCharset) 
00118   {
00119     *aDestLength = 0;
00120     return NS_OK;
00121   } 
00122   
00123   if (*aDestLength < 3) {
00124     *aDestLength = 0;
00125     return NS_OK_UENC_MOREOUTPUT;
00126   }
00127 
00128   switch (aCharset) {
00129     case 0: // ASCII ISOREG 6
00130       aDest[0] = 0x1b;
00131       aDest[1] = '(';
00132       aDest[2] = 'B';
00133       break;
00134     case 1: // JIS X 0201-1976 ("Roman" set) ISOREG 14
00135       aDest[0] = 0x1b;
00136       aDest[1] = '(';
00137       aDest[2] = 'J';
00138       break;
00139     case 2: // JIS X 0208-1983 ISOREG 87
00140     case 3: // JIS X 0208-1983 
00141             // we currently use this for CP932 ext
00142       aDest[0] = 0x1b;
00143       aDest[1] = '$';
00144       aDest[2] = 'B';
00145       break;
00146     case 4: // JIS X 0201-1978 ISOREG 87- 
00147             // we currently do not have a diff mapping for it.
00148       aDest[0] = 0x1b;
00149       aDest[1] = '$';
00150       aDest[2] = '@';
00151       break;
00152   }
00153 
00154   mCharset = aCharset;
00155   *aDestLength = 3;
00156   return NS_OK;
00157 }
00158 
00159 //----------------------------------------------------------------------
00160 // Subclassing of nsTableEncoderSupport class [implementation]
00161 
00162 NS_IMETHODIMP nsUnicodeToISO2022JP::FillInfo(PRUint32* aInfo)
00163 {
00164   nsresult res;
00165 
00166   if (mHelper == nsnull) {
00167     res = CallCreateInstance(kUnicodeEncodeHelperCID, &mHelper);
00168     if (NS_FAILED(res)) return NS_ERROR_UENC_NOHELPER;
00169   }
00170   return mHelper->FillInfo(aInfo, 
00171                   SIZE_OF_TABLES, 
00172                   (uMappingTable **) g_ufMappingTables);
00173 
00174 }
00175 NS_IMETHODIMP nsUnicodeToISO2022JP::ConvertNoBuffNoErr(
00176                                     const PRUnichar * aSrc, 
00177                                     PRInt32 * aSrcLength, 
00178                                     char * aDest, 
00179                                     PRInt32 * aDestLength)
00180 {
00181   nsresult res = NS_OK;
00182 
00183   if (mHelper == nsnull) {
00184     res = CallCreateInstance(kUnicodeEncodeHelperCID, &mHelper);
00185     if (NS_FAILED(res)) return NS_ERROR_UENC_NOHELPER;
00186   }
00187 
00188   const PRUnichar * src = aSrc;
00189   const PRUnichar * srcEnd = aSrc + *aSrcLength;
00190   char * dest = aDest;
00191   char * destEnd = aDest + *aDestLength;
00192   PRInt32 bcr, bcw;
00193   PRInt32 i;
00194 
00195   while (src < srcEnd) {
00196     for (i=0; i< SIZE_OF_TABLES ; i++) {
00197       bcr = 1;
00198       bcw = destEnd - dest;
00199       res = mHelper->ConvertByTable(src, &bcr, dest, &bcw, 
00200           (uShiftTable *) g_ufShiftTables[i], 
00201           (uMappingTable *) g_ufMappingTables[i]);
00202       if (res != NS_ERROR_UENC_NOMAPPING) break;
00203     }
00204 
00205     if ( i>=  SIZE_OF_TABLES) {
00206       res = NS_ERROR_UENC_NOMAPPING;
00207       src++;
00208     }
00209     if (res != NS_OK) break;
00210 
00211     bcw = destEnd - dest;
00212     res = ChangeCharset(i, dest, &bcw);
00213     dest += bcw;
00214     if (res != NS_OK) break;
00215 
00216     bcr = srcEnd - src;
00217     bcw = destEnd - dest;
00218     res = mHelper->ConvertByTable(src, &bcr, dest, &bcw, 
00219         (uShiftTable *) g_ufShiftTables[i], 
00220         (uMappingTable *) g_ufMappingTables[i]);
00221     src += bcr;
00222     dest += bcw;
00223 
00224     if ((res != NS_OK) && (res != NS_ERROR_UENC_NOMAPPING)) break;
00225     if (res == NS_ERROR_UENC_NOMAPPING) src--;
00226   }
00227 
00228   *aSrcLength = src - aSrc;
00229   *aDestLength  = dest - aDest;
00230   return res;
00231 }
00232 
00233 NS_IMETHODIMP nsUnicodeToISO2022JP::FinishNoBuff(char * aDest, 
00234                                                  PRInt32 * aDestLength)
00235 {
00236   ChangeCharset(0, aDest, aDestLength);
00237   return NS_OK;
00238 }
00239 
00240 NS_IMETHODIMP nsUnicodeToISO2022JP::Reset()
00241 {
00242   mCharset = 0;
00243   return nsEncoderSupport::Reset();
00244 }