|
1 /* |
|
2 * Copyright (c) 1997-2009 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of "Eclipse Public License v1.0" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: |
|
15 * |
|
16 */ |
|
17 |
|
18 |
|
19 #include <e32std.h> |
|
20 #include <charconv.h> |
|
21 #include <convutils.h> |
|
22 #include "jisx0201.h" |
|
23 #include "jisx0208.h" |
|
24 #include "jisx0212.h" |
|
25 #include <ecom/implementationproxy.h> |
|
26 #include <charactersetconverter.h> |
|
27 |
|
28 const TUint KSingleShift2=0x8e; |
|
29 const TUint KSingleShift3=0x8f; |
|
30 |
|
31 _LIT8(KLit8EucJpPackedReplacementForUnconvertibleUnicodeCharacters, "\xa1\xa9"); // fullwidth question mark |
|
32 |
|
33 #if defined(_DEBUG) |
|
34 |
|
35 _LIT(KLitPanicText, "EUCJP_PACKED"); |
|
36 |
|
37 enum TPanic |
|
38 { |
|
39 EPanicNothingToConvert1=1, |
|
40 EPanicNothingToConvert2, |
|
41 EPanicNothingToConvert3, |
|
42 EPanicNothingToConvert4, |
|
43 EPanicNothingToConvert5, |
|
44 EPanicNothingToConvert6, |
|
45 EPanicOddNumberOfBytes1, |
|
46 EPanicOddNumberOfBytes2, |
|
47 EPanicOddNumberOfBytes3, |
|
48 EPanicOddNumberOfBytes4, |
|
49 EPanicOddNumberOfBytes5, |
|
50 EPanicOddNumberOfBytes6, |
|
51 EPanicBadHighBit1, |
|
52 EPanicBadHighBit2, |
|
53 EPanicBadHighBit3, |
|
54 EPanicBadHighBit4, |
|
55 EPanicBadHighBit5, |
|
56 EPanicBadHighBit6, |
|
57 EPanicBadHighBit7, |
|
58 EPanicBadPointers1, |
|
59 EPanicBadPointers2, |
|
60 EPanicBadPointers3, |
|
61 EPanicBadPointers4, |
|
62 EPanicBadPointers5, |
|
63 EPanicBadPointers6, |
|
64 EPanicBadPointers7, |
|
65 EPanicBadPointers8, |
|
66 EPanicBadPointers9, |
|
67 EPanicBadPointers10, |
|
68 EPanicBadPointers11, |
|
69 EPanicBadPointers12, |
|
70 EPanicBadPointers13, |
|
71 EPanicBadPointers14, |
|
72 EPanicBadPointers15, |
|
73 EPanicBadPointers16, |
|
74 EPanicBadPointers17, |
|
75 EPanicBadPointers18, |
|
76 EPanicBadPointers19, |
|
77 EPanicBadPointers20, |
|
78 EPanicBadPointers21, |
|
79 EPanicBadPointers22, |
|
80 EPanicBadPointers23, |
|
81 EPanicBadPointers24, |
|
82 EPanicBadPointers25, |
|
83 EPanicBadPointers26, |
|
84 EPanicBadPointers27, |
|
85 EPanicBadPointers28, |
|
86 EPanicBadPointers29, |
|
87 EPanicBadPointers30, |
|
88 EPanicBadPointers31, |
|
89 EPanicBadPointers32, |
|
90 EPanicBadPointers33, |
|
91 EPanicBadPointers34, |
|
92 EPanicBadPointers35, |
|
93 EPanicBadPointers36, |
|
94 EPanicBadCalculation1, |
|
95 EPanicBadCalculation2, |
|
96 EPanicNumberOfBytesIsNotMultipleOfThree1, |
|
97 EPanicNumberOfBytesIsNotMultipleOfThree2, |
|
98 EPanicSingleShift2Expected, |
|
99 EPanicSingleShift3Expected |
|
100 }; |
|
101 |
|
102 LOCAL_C void Panic(TPanic aPanic) |
|
103 { |
|
104 User::Panic(KLitPanicText, aPanic); |
|
105 } |
|
106 |
|
107 #endif |
|
108 |
|
109 |
|
110 class CEucjpPackedConverterImpl : public CCharacterSetConverterPluginInterface |
|
111 { |
|
112 |
|
113 public: |
|
114 virtual const TDesC8& ReplacementForUnconvertibleUnicodeCharacters(); |
|
115 |
|
116 virtual TInt ConvertFromUnicode( |
|
117 CCnvCharacterSetConverter::TEndianness aDefaultEndiannessOfForeignCharacters, |
|
118 const TDesC8& aReplacementForUnconvertibleUnicodeCharacters, |
|
119 TDes8& aForeign, |
|
120 const TDesC16& aUnicode, |
|
121 CCnvCharacterSetConverter::TArrayOfAscendingIndices& aIndicesOfUnconvertibleCharacters); |
|
122 |
|
123 virtual TInt ConvertToUnicode( |
|
124 CCnvCharacterSetConverter::TEndianness aDefaultEndiannessOfForeignCharacters, |
|
125 TDes16& aUnicode, |
|
126 const TDesC8& aForeign, |
|
127 TInt& aState, |
|
128 TInt& aNumberOfUnconvertibleCharacters, |
|
129 TInt& aIndexOfFirstByteOfFirstUnconvertibleCharacter); |
|
130 |
|
131 virtual TBool IsInThisCharacterSetL( |
|
132 TBool& aSetToTrue, |
|
133 TInt& aConfidenceLevel, |
|
134 const TDesC8& aSample); |
|
135 |
|
136 static CEucjpPackedConverterImpl* NewL(); |
|
137 virtual ~CEucjpPackedConverterImpl(); |
|
138 |
|
139 private: |
|
140 CEucjpPackedConverterImpl(); |
|
141 |
|
142 }; |
|
143 |
|
144 |
|
145 |
|
146 |
|
147 |
|
148 const TDesC8& CEucjpPackedConverterImpl::ReplacementForUnconvertibleUnicodeCharacters() |
|
149 { |
|
150 return KLit8EucJpPackedReplacementForUnconvertibleUnicodeCharacters; |
|
151 } |
|
152 |
|
153 LOCAL_C void DummyConvertFromIntermediateBufferInPlace(TInt, TDes8&, TInt& aNumberOfCharactersThatDroppedOut) |
|
154 { |
|
155 aNumberOfCharactersThatDroppedOut=0; |
|
156 } |
|
157 |
|
158 LOCAL_C void ConvertFromJisX0208ToEucJpPackedInPlace(TInt aStartPositionInDescriptor, TDes8& aDescriptor, TInt& aNumberOfCharactersThatDroppedOut) |
|
159 { |
|
160 aNumberOfCharactersThatDroppedOut=0; |
|
161 const TInt descriptorLength=aDescriptor.Length(); |
|
162 __ASSERT_DEBUG(descriptorLength>aStartPositionInDescriptor, Panic(EPanicNothingToConvert1)); |
|
163 __ASSERT_DEBUG((descriptorLength-aStartPositionInDescriptor)%2==0, Panic(EPanicOddNumberOfBytes1)); |
|
164 TUint8* pointerToCurrentByte=CONST_CAST(TUint8*, aDescriptor.Ptr()); |
|
165 const TUint8* const pointerToLastByte=pointerToCurrentByte+(descriptorLength-1); |
|
166 pointerToCurrentByte+=aStartPositionInDescriptor; |
|
167 FOREVER |
|
168 { |
|
169 const TUint currentByte=*pointerToCurrentByte; |
|
170 __ASSERT_DEBUG((currentByte&0x80)==0, Panic(EPanicBadHighBit1)); |
|
171 *pointerToCurrentByte=STATIC_CAST(TUint8, currentByte|0x80); |
|
172 __ASSERT_DEBUG(pointerToCurrentByte<=pointerToLastByte, Panic(EPanicBadPointers1)); |
|
173 if (pointerToCurrentByte>=pointerToLastByte) |
|
174 { |
|
175 break; |
|
176 } |
|
177 ++pointerToCurrentByte; |
|
178 } |
|
179 } |
|
180 |
|
181 LOCAL_C void ConvertFromHalfWidthKatakana8ToEucJpPackedInPlace(TInt aStartPositionInDescriptor, TDes8& aDescriptor, TInt& aNumberOfCharactersThatDroppedOut) |
|
182 { |
|
183 TInt descriptorLength=aDescriptor.Length(); |
|
184 __ASSERT_DEBUG(descriptorLength>aStartPositionInDescriptor, Panic(EPanicNothingToConvert2)); |
|
185 aNumberOfCharactersThatDroppedOut=Max(0, (descriptorLength-aStartPositionInDescriptor)-((aDescriptor.MaxLength()-aStartPositionInDescriptor)/2)); |
|
186 descriptorLength-=aNumberOfCharactersThatDroppedOut; |
|
187 __ASSERT_DEBUG(descriptorLength>=aStartPositionInDescriptor, Panic(EPanicBadCalculation1)); |
|
188 if (descriptorLength<=aStartPositionInDescriptor) |
|
189 { |
|
190 aDescriptor.SetLength(descriptorLength); |
|
191 } |
|
192 else |
|
193 { |
|
194 TUint8* pointerToTargetByte=CONST_CAST(TUint8*, aDescriptor.Ptr()); // pointerToTargetByte is initialized properly when descriptorLength has been offset to the actual final length of aDescriptor |
|
195 const TUint8* const pointerToFirstByte=pointerToTargetByte+aStartPositionInDescriptor; |
|
196 const TUint8* pointerToSourceByte=pointerToTargetByte+(descriptorLength-1); |
|
197 descriptorLength=((descriptorLength-aStartPositionInDescriptor)*2)+aStartPositionInDescriptor; |
|
198 __ASSERT_DEBUG((descriptorLength-aStartPositionInDescriptor)%2==0, Panic(EPanicOddNumberOfBytes2)); |
|
199 aDescriptor.SetLength(descriptorLength); |
|
200 pointerToTargetByte+=descriptorLength-1; // pointerToTargetByte is is initialized properly here |
|
201 FOREVER |
|
202 { |
|
203 *pointerToTargetByte=*pointerToSourceByte; |
|
204 __ASSERT_DEBUG(pointerToTargetByte>pointerToFirstByte, Panic(EPanicBadPointers2)); |
|
205 --pointerToTargetByte; |
|
206 *pointerToTargetByte=KSingleShift2; |
|
207 __ASSERT_DEBUG(pointerToTargetByte>=pointerToFirstByte, Panic(EPanicBadPointers3)); |
|
208 if (pointerToTargetByte<=pointerToFirstByte) |
|
209 { |
|
210 break; |
|
211 } |
|
212 --pointerToTargetByte; |
|
213 __ASSERT_DEBUG(pointerToSourceByte>pointerToFirstByte, Panic(EPanicBadPointers4)); |
|
214 --pointerToSourceByte; |
|
215 } |
|
216 __ASSERT_DEBUG(pointerToTargetByte==pointerToFirstByte, Panic(EPanicBadPointers5)); |
|
217 __ASSERT_DEBUG(pointerToSourceByte==pointerToFirstByte, Panic(EPanicBadPointers6)); |
|
218 } |
|
219 } |
|
220 |
|
221 LOCAL_C void ConvertFromJisX0212ToEucJpPackedInPlace(TInt aStartPositionInDescriptor, TDes8& aDescriptor, TInt& aNumberOfCharactersThatDroppedOut) |
|
222 { |
|
223 TInt descriptorLength=aDescriptor.Length(); |
|
224 __ASSERT_DEBUG(descriptorLength>aStartPositionInDescriptor, Panic(EPanicNothingToConvert3)); |
|
225 __ASSERT_DEBUG((descriptorLength-aStartPositionInDescriptor)%2==0, Panic(EPanicOddNumberOfBytes3)); |
|
226 aNumberOfCharactersThatDroppedOut=Max(0, ((descriptorLength-aStartPositionInDescriptor)/2)-((aDescriptor.MaxLength()-aStartPositionInDescriptor)/3)); |
|
227 descriptorLength-=aNumberOfCharactersThatDroppedOut*2; |
|
228 __ASSERT_DEBUG(descriptorLength>=aStartPositionInDescriptor, Panic(EPanicBadCalculation2)); |
|
229 if (descriptorLength<=aStartPositionInDescriptor) |
|
230 { |
|
231 aDescriptor.SetLength(descriptorLength); |
|
232 } |
|
233 else |
|
234 { |
|
235 __ASSERT_DEBUG((descriptorLength-aStartPositionInDescriptor)%2==0, Panic(EPanicOddNumberOfBytes4)); |
|
236 TUint8* pointerToTargetByte=CONST_CAST(TUint8*, aDescriptor.Ptr()); // pointerToTargetByte is initialized properly when descriptorLength has been offset to the actual final length of aDescriptor |
|
237 const TUint8* const pointerToFirstByte=pointerToTargetByte+aStartPositionInDescriptor; |
|
238 const TUint8* pointerToSourceByte=pointerToTargetByte+(descriptorLength-1); |
|
239 descriptorLength=(((descriptorLength-aStartPositionInDescriptor)*3)/2)+aStartPositionInDescriptor; |
|
240 __ASSERT_DEBUG((descriptorLength-aStartPositionInDescriptor)%3==0, Panic(EPanicNumberOfBytesIsNotMultipleOfThree1)); |
|
241 aDescriptor.SetLength(descriptorLength); |
|
242 pointerToTargetByte+=descriptorLength-1; // pointerToTargetByte is is initialized properly here |
|
243 FOREVER |
|
244 { |
|
245 __ASSERT_DEBUG((*pointerToSourceByte&0x80)==0, Panic(EPanicBadHighBit2)); |
|
246 *pointerToTargetByte=STATIC_CAST(TUint8, *pointerToSourceByte|0x80); |
|
247 __ASSERT_DEBUG(pointerToTargetByte>pointerToFirstByte, Panic(EPanicBadPointers7)); |
|
248 --pointerToTargetByte; |
|
249 __ASSERT_DEBUG(pointerToSourceByte>pointerToFirstByte, Panic(EPanicBadPointers8)); |
|
250 --pointerToSourceByte; |
|
251 __ASSERT_DEBUG((*pointerToSourceByte&0x80)==0, Panic(EPanicBadHighBit3)); |
|
252 *pointerToTargetByte=STATIC_CAST(TUint8, *pointerToSourceByte|0x80); |
|
253 __ASSERT_DEBUG(pointerToTargetByte>pointerToFirstByte, Panic(EPanicBadPointers9)); |
|
254 --pointerToTargetByte; |
|
255 *pointerToTargetByte=KSingleShift3; |
|
256 __ASSERT_DEBUG(pointerToTargetByte>=pointerToFirstByte, Panic(EPanicBadPointers10)); |
|
257 if (pointerToTargetByte<=pointerToFirstByte) |
|
258 { |
|
259 break; |
|
260 } |
|
261 --pointerToTargetByte; |
|
262 __ASSERT_DEBUG(pointerToSourceByte>pointerToFirstByte, Panic(EPanicBadPointers11)); |
|
263 --pointerToSourceByte; |
|
264 } |
|
265 __ASSERT_DEBUG(pointerToTargetByte==pointerToFirstByte, Panic(EPanicBadPointers12)); |
|
266 __ASSERT_DEBUG(pointerToSourceByte==pointerToFirstByte, Panic(EPanicBadPointers13)); |
|
267 } |
|
268 } |
|
269 |
|
270 TInt CEucjpPackedConverterImpl::ConvertFromUnicode( |
|
271 CCnvCharacterSetConverter::TEndianness aDefaultEndiannessOfForeignCharacters, |
|
272 const TDesC8& aReplacementForUnconvertibleUnicodeCharacters, |
|
273 TDes8& aForeign, |
|
274 const TDesC16& aUnicode, |
|
275 CCnvCharacterSetConverter::TArrayOfAscendingIndices& aIndicesOfUnconvertibleCharacters) |
|
276 { |
|
277 TFixedArray<CnvUtilities::SCharacterSet, 4> characterSets; |
|
278 characterSets[0].iConversionData=&CnvJisRoman::ConversionData(); |
|
279 characterSets[0].iConvertFromIntermediateBufferInPlace=DummyConvertFromIntermediateBufferInPlace; |
|
280 characterSets[0].iEscapeSequence=&KNullDesC8; |
|
281 characterSets[1].iConversionData=&CnvJisX0208::ConversionData(); |
|
282 characterSets[1].iConvertFromIntermediateBufferInPlace=ConvertFromJisX0208ToEucJpPackedInPlace; |
|
283 characterSets[1].iEscapeSequence=&KNullDesC8; |
|
284 characterSets[2].iConversionData=&CnvHalfWidthKatakana8::ConversionData(); |
|
285 characterSets[2].iConvertFromIntermediateBufferInPlace=ConvertFromHalfWidthKatakana8ToEucJpPackedInPlace; |
|
286 characterSets[2].iEscapeSequence=&KNullDesC8; |
|
287 characterSets[3].iConversionData=&CnvJisX0212::ConversionData(); |
|
288 characterSets[3].iConvertFromIntermediateBufferInPlace=ConvertFromJisX0212ToEucJpPackedInPlace; |
|
289 characterSets[3].iEscapeSequence=&KNullDesC8; |
|
290 return CnvUtilities::ConvertFromUnicode(aDefaultEndiannessOfForeignCharacters, aReplacementForUnconvertibleUnicodeCharacters, aForeign, aUnicode, aIndicesOfUnconvertibleCharacters, characterSets.Array()); |
|
291 } |
|
292 |
|
293 LOCAL_C TInt NumberOfBytesAbleToConvertToJisRoman(const TDesC8& aDescriptor) |
|
294 { |
|
295 const TUint8* pointerToPreviousByte=aDescriptor.Ptr()-1; |
|
296 const TUint8* const pointerToLastByte=pointerToPreviousByte+aDescriptor.Length(); |
|
297 if (pointerToPreviousByte==pointerToLastByte) |
|
298 { |
|
299 return 0; |
|
300 } |
|
301 FOREVER |
|
302 { |
|
303 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers14)); |
|
304 const TUint currentByte=*(pointerToPreviousByte+1); |
|
305 if (currentByte&0x80) |
|
306 { |
|
307 break; |
|
308 } |
|
309 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers15)); |
|
310 ++pointerToPreviousByte; |
|
311 __ASSERT_DEBUG(pointerToPreviousByte<=pointerToLastByte, Panic(EPanicBadPointers16)); |
|
312 if (pointerToPreviousByte>=pointerToLastByte) |
|
313 { |
|
314 break; |
|
315 } |
|
316 } |
|
317 return (pointerToPreviousByte+1)-aDescriptor.Ptr(); |
|
318 } |
|
319 |
|
320 LOCAL_C TInt NumberOfBytesAbleToConvertToJisX0208(const TDesC8& aDescriptor) |
|
321 { |
|
322 const TUint8* pointerToPreviousByte=aDescriptor.Ptr()-1; |
|
323 const TUint8* const pointerToLastByte=pointerToPreviousByte+aDescriptor.Length(); |
|
324 if (pointerToPreviousByte==pointerToLastByte) |
|
325 { |
|
326 return 0; |
|
327 } |
|
328 FOREVER |
|
329 { |
|
330 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers17)); |
|
331 TUint currentByte=*(pointerToPreviousByte+1); |
|
332 if (currentByte<0xa0) |
|
333 { |
|
334 break; |
|
335 } |
|
336 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers18)); |
|
337 if (pointerToLastByte-pointerToPreviousByte<2) |
|
338 { |
|
339 break; |
|
340 } |
|
341 ++pointerToPreviousByte; |
|
342 currentByte=*(pointerToPreviousByte+1); |
|
343 if (currentByte<0xa0) |
|
344 { |
|
345 return CCnvCharacterSetConverter::EErrorIllFormedInput; |
|
346 } |
|
347 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers19)); |
|
348 ++pointerToPreviousByte; |
|
349 __ASSERT_DEBUG(pointerToPreviousByte<=pointerToLastByte, Panic(EPanicBadPointers20)); |
|
350 if (pointerToPreviousByte>=pointerToLastByte) |
|
351 { |
|
352 break; |
|
353 } |
|
354 } |
|
355 return (pointerToPreviousByte+1)-aDescriptor.Ptr(); |
|
356 } |
|
357 |
|
358 LOCAL_C TInt NumberOfBytesAbleToConvertToHalfWidthKatakana8(const TDesC8& aDescriptor) |
|
359 { |
|
360 const TUint8* pointerToPreviousByte=aDescriptor.Ptr()-1; |
|
361 const TUint8* const pointerToLastByte=pointerToPreviousByte+aDescriptor.Length(); |
|
362 if (pointerToPreviousByte==pointerToLastByte) |
|
363 { |
|
364 return 0; |
|
365 } |
|
366 FOREVER |
|
367 { |
|
368 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers21)); |
|
369 TUint currentByte=*(pointerToPreviousByte+1); |
|
370 if (currentByte!=KSingleShift2) |
|
371 { |
|
372 break; |
|
373 } |
|
374 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers22)); |
|
375 if (pointerToLastByte-pointerToPreviousByte<2) |
|
376 { |
|
377 break; |
|
378 } |
|
379 ++pointerToPreviousByte; |
|
380 currentByte=*(pointerToPreviousByte+1); |
|
381 if (currentByte<0xa0) |
|
382 { |
|
383 return CCnvCharacterSetConverter::EErrorIllFormedInput; |
|
384 } |
|
385 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers23)); |
|
386 ++pointerToPreviousByte; |
|
387 __ASSERT_DEBUG(pointerToPreviousByte<=pointerToLastByte, Panic(EPanicBadPointers24)); |
|
388 if (pointerToPreviousByte>=pointerToLastByte) |
|
389 { |
|
390 break; |
|
391 } |
|
392 } |
|
393 return (pointerToPreviousByte+1)-aDescriptor.Ptr(); |
|
394 } |
|
395 |
|
396 LOCAL_C TInt NumberOfBytesAbleToConvertToJisX0212(const TDesC8& aDescriptor) |
|
397 { |
|
398 const TUint8* pointerToPreviousByte=aDescriptor.Ptr()-1; |
|
399 const TUint8* const pointerToLastByte=pointerToPreviousByte+aDescriptor.Length(); |
|
400 if (pointerToPreviousByte==pointerToLastByte) |
|
401 { |
|
402 return 0; |
|
403 } |
|
404 FOREVER |
|
405 { |
|
406 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers25)); |
|
407 TUint currentByte=*(pointerToPreviousByte+1); |
|
408 if (currentByte!=KSingleShift3) |
|
409 { |
|
410 break; |
|
411 } |
|
412 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers26)); |
|
413 if (pointerToLastByte-pointerToPreviousByte<3) |
|
414 { |
|
415 break; |
|
416 } |
|
417 ++pointerToPreviousByte; |
|
418 currentByte=*(pointerToPreviousByte+1); |
|
419 if (currentByte<0xa0) |
|
420 { |
|
421 return CCnvCharacterSetConverter::EErrorIllFormedInput; |
|
422 } |
|
423 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers27)); |
|
424 ++pointerToPreviousByte; |
|
425 currentByte=*(pointerToPreviousByte+1); |
|
426 if (currentByte<0xa0) |
|
427 { |
|
428 return CCnvCharacterSetConverter::EErrorIllFormedInput; |
|
429 } |
|
430 __ASSERT_DEBUG(pointerToPreviousByte<pointerToLastByte, Panic(EPanicBadPointers28)); |
|
431 ++pointerToPreviousByte; |
|
432 __ASSERT_DEBUG(pointerToPreviousByte<=pointerToLastByte, Panic(EPanicBadPointers29)); |
|
433 if (pointerToPreviousByte>=pointerToLastByte) |
|
434 { |
|
435 break; |
|
436 } |
|
437 } |
|
438 return (pointerToPreviousByte+1)-aDescriptor.Ptr(); |
|
439 } |
|
440 |
|
441 LOCAL_C void DummyConvertToIntermediateBufferInPlace(TDes8&) |
|
442 { |
|
443 } |
|
444 |
|
445 LOCAL_C void ConvertToJisX0208FromEucJpPackedInPlace(TDes8& aDescriptor) |
|
446 { |
|
447 const TInt descriptorLength=aDescriptor.Length(); |
|
448 __ASSERT_DEBUG(descriptorLength>0, Panic(EPanicNothingToConvert4)); |
|
449 __ASSERT_DEBUG(descriptorLength%2==0, Panic(EPanicOddNumberOfBytes5)); |
|
450 TUint8* pointerToCurrentByte=CONST_CAST(TUint8*, aDescriptor.Ptr()); |
|
451 const TUint8* const pointerToLastByte=pointerToCurrentByte+(descriptorLength-1); |
|
452 FOREVER |
|
453 { |
|
454 const TUint currentByte=*pointerToCurrentByte; |
|
455 __ASSERT_DEBUG(currentByte&0x80, Panic(EPanicBadHighBit4)); |
|
456 *pointerToCurrentByte=STATIC_CAST(TUint8, currentByte&~0x80); |
|
457 __ASSERT_DEBUG(pointerToCurrentByte<=pointerToLastByte, Panic(EPanicBadPointers30)); |
|
458 if (pointerToCurrentByte>=pointerToLastByte) |
|
459 { |
|
460 break; |
|
461 } |
|
462 ++pointerToCurrentByte; |
|
463 } |
|
464 } |
|
465 |
|
466 LOCAL_C void ConvertToHalfWidthKatakana8FromEucJpPackedInPlace(TDes8& aDescriptor) |
|
467 { |
|
468 const TInt descriptorLength=aDescriptor.Length(); |
|
469 __ASSERT_DEBUG(descriptorLength>0, Panic(EPanicNothingToConvert5)); |
|
470 __ASSERT_DEBUG(descriptorLength%2==0, Panic(EPanicOddNumberOfBytes6)); |
|
471 TUint8* pointerToTargetByte=CONST_CAST(TUint8*, aDescriptor.Ptr()); |
|
472 const TUint8* pointerToSourceByte=pointerToTargetByte; |
|
473 const TUint8* const pointerToLastByte=pointerToSourceByte+(descriptorLength-1); |
|
474 FOREVER |
|
475 { |
|
476 __ASSERT_DEBUG(*pointerToSourceByte==KSingleShift2, Panic(EPanicSingleShift2Expected)); |
|
477 __ASSERT_DEBUG(pointerToSourceByte<pointerToLastByte, Panic(EPanicBadPointers31)); |
|
478 ++pointerToSourceByte; |
|
479 const TUint sourceByte=*pointerToSourceByte; |
|
480 __ASSERT_DEBUG(sourceByte&0x80, Panic(EPanicBadHighBit5)); |
|
481 *pointerToTargetByte=STATIC_CAST(TUint8, sourceByte); |
|
482 __ASSERT_DEBUG(pointerToSourceByte<=pointerToLastByte, Panic(EPanicBadPointers32)); |
|
483 if (pointerToSourceByte>=pointerToLastByte) |
|
484 { |
|
485 break; |
|
486 } |
|
487 ++pointerToSourceByte; |
|
488 ++pointerToTargetByte; |
|
489 } |
|
490 aDescriptor.SetLength(descriptorLength/2); |
|
491 } |
|
492 |
|
493 LOCAL_C void ConvertToJisX0212FromEucJpPackedInPlace(TDes8& aDescriptor) |
|
494 { |
|
495 const TInt descriptorLength=aDescriptor.Length(); |
|
496 __ASSERT_DEBUG(descriptorLength>0, Panic(EPanicNothingToConvert6)); |
|
497 __ASSERT_DEBUG(descriptorLength%3==0, Panic(EPanicNumberOfBytesIsNotMultipleOfThree2)); |
|
498 TUint8* pointerToTargetByte=CONST_CAST(TUint8*, aDescriptor.Ptr()); |
|
499 const TUint8* pointerToSourceByte=pointerToTargetByte; |
|
500 const TUint8* const pointerToLastByte=pointerToSourceByte+(descriptorLength-1); |
|
501 FOREVER |
|
502 { |
|
503 __ASSERT_DEBUG(*pointerToSourceByte==KSingleShift3, Panic(EPanicSingleShift3Expected)); |
|
504 __ASSERT_DEBUG(pointerToSourceByte<pointerToLastByte, Panic(EPanicBadPointers33)); |
|
505 ++pointerToSourceByte; |
|
506 TUint sourceByte=*pointerToSourceByte; |
|
507 __ASSERT_DEBUG(sourceByte&0x80, Panic(EPanicBadHighBit6)); |
|
508 *pointerToTargetByte=STATIC_CAST(TUint8, sourceByte&~0x80); |
|
509 __ASSERT_DEBUG(pointerToSourceByte<pointerToLastByte, Panic(EPanicBadPointers34)); |
|
510 ++pointerToSourceByte; |
|
511 sourceByte=*pointerToSourceByte; |
|
512 __ASSERT_DEBUG(sourceByte&0x80, Panic(EPanicBadHighBit7)); |
|
513 __ASSERT_DEBUG(pointerToTargetByte<pointerToLastByte, Panic(EPanicBadPointers35)); |
|
514 ++pointerToTargetByte; |
|
515 *pointerToTargetByte=STATIC_CAST(TUint8, sourceByte&~0x80); |
|
516 __ASSERT_DEBUG(pointerToSourceByte<=pointerToLastByte, Panic(EPanicBadPointers36)); |
|
517 if (pointerToSourceByte>=pointerToLastByte) |
|
518 { |
|
519 break; |
|
520 } |
|
521 ++pointerToSourceByte; |
|
522 ++pointerToTargetByte; |
|
523 } |
|
524 aDescriptor.SetLength((descriptorLength/3)*2); |
|
525 } |
|
526 |
|
527 TInt CEucjpPackedConverterImpl::ConvertToUnicode( |
|
528 CCnvCharacterSetConverter::TEndianness aDefaultEndiannessOfForeignCharacters, |
|
529 TDes16& aUnicode, |
|
530 const TDesC8& aForeign, |
|
531 TInt& /*aState*/, |
|
532 TInt& aNumberOfUnconvertibleCharacters, |
|
533 TInt& aIndexOfFirstByteOfFirstUnconvertibleCharacter) |
|
534 { |
|
535 TFixedArray<CnvUtilities::SMethod, 4> methods; |
|
536 methods[0].iNumberOfBytesAbleToConvert=NumberOfBytesAbleToConvertToJisRoman; |
|
537 methods[0].iConvertToIntermediateBufferInPlace=DummyConvertToIntermediateBufferInPlace; |
|
538 methods[0].iConversionData=&CnvJisRoman::ConversionData(); |
|
539 methods[0].iNumberOfBytesPerCharacter=1; |
|
540 methods[0].iNumberOfCoreBytesPerCharacter=1; |
|
541 methods[1].iNumberOfBytesAbleToConvert=NumberOfBytesAbleToConvertToJisX0208; |
|
542 methods[1].iConvertToIntermediateBufferInPlace=ConvertToJisX0208FromEucJpPackedInPlace; |
|
543 methods[1].iConversionData=&CnvJisX0208::ConversionData(); |
|
544 methods[1].iNumberOfBytesPerCharacter=2; |
|
545 methods[1].iNumberOfCoreBytesPerCharacter=2; |
|
546 methods[2].iNumberOfBytesAbleToConvert=NumberOfBytesAbleToConvertToHalfWidthKatakana8; |
|
547 methods[2].iConvertToIntermediateBufferInPlace=ConvertToHalfWidthKatakana8FromEucJpPackedInPlace; |
|
548 methods[2].iConversionData=&CnvHalfWidthKatakana8::ConversionData(); |
|
549 methods[2].iNumberOfBytesPerCharacter=2; |
|
550 methods[2].iNumberOfCoreBytesPerCharacter=1; |
|
551 methods[3].iNumberOfBytesAbleToConvert=NumberOfBytesAbleToConvertToJisX0212; |
|
552 methods[3].iConvertToIntermediateBufferInPlace=ConvertToJisX0212FromEucJpPackedInPlace; |
|
553 methods[3].iConversionData=&CnvJisX0212::ConversionData(); |
|
554 methods[3].iNumberOfBytesPerCharacter=3; |
|
555 methods[3].iNumberOfCoreBytesPerCharacter=2; |
|
556 return CnvUtilities::ConvertToUnicodeFromHeterogeneousForeign(aDefaultEndiannessOfForeignCharacters, aUnicode, aForeign, aNumberOfUnconvertibleCharacters, aIndexOfFirstByteOfFirstUnconvertibleCharacter, methods.Array()); |
|
557 } |
|
558 |
|
559 TBool CEucjpPackedConverterImpl::IsInThisCharacterSetL( |
|
560 TBool& aSetToTrue, |
|
561 TInt& aConfidenceLevel, |
|
562 const TDesC8& aSample) |
|
563 { |
|
564 aSetToTrue=ETrue; |
|
565 // check for the SS2 and SS3 which specifies Code Set 2 & 3 respectively from the Code space |
|
566 // between 00-7f only... then ambiguous |
|
567 aSetToTrue = ETrue; |
|
568 TInt sampleLength = aSample.Length(); |
|
569 TInt eucjpPacked = 0; |
|
570 aConfidenceLevel = 0; |
|
571 |
|
572 for (TInt i = 0; i < sampleLength; ++i) |
|
573 { |
|
574 // Code set 1 JISX 0208 support |
|
575 TInt increment1 = i+1; |
|
576 if (increment1 >= sampleLength) |
|
577 break; |
|
578 if (((aSample[i] >= 0xa1) && (aSample[i] <= 0xfe)) && |
|
579 ((aSample[increment1] >= 0xa1) && (aSample[increment1] <= 0xfe))) |
|
580 { |
|
581 eucjpPacked = eucjpPacked +2; |
|
582 i++; |
|
583 } |
|
584 // Single Shift 2 (SS2) sequence - Code Set 2 |
|
585 if (aSample[i]==0x8e) |
|
586 { |
|
587 TInt increment1 = i+1; |
|
588 if (increment1 >= sampleLength) |
|
589 break; |
|
590 if ((aSample[increment1] >= 0xa1) && (aSample[increment1] <= 0xdf)) |
|
591 { |
|
592 eucjpPacked = eucjpPacked+2; |
|
593 i++; |
|
594 } |
|
595 else |
|
596 { |
|
597 eucjpPacked = 0; |
|
598 break; |
|
599 } |
|
600 } |
|
601 // Single Shift 3 (SS3) sequence - Code Set 3 |
|
602 if (aSample[i]==0x8f) |
|
603 { |
|
604 TInt increment1 = i+1; |
|
605 TInt increment2 = i+2; |
|
606 if ((increment1 >= sampleLength) || (increment2 >= sampleLength)) |
|
607 break; |
|
608 if (((aSample[increment1] >= 0xa1) && (aSample[increment1] <= 0xfe)) && |
|
609 ((aSample[increment2] >= 0xa1) && (aSample[increment2] <= 0xfe))) |
|
610 { |
|
611 eucjpPacked = eucjpPacked +3; |
|
612 i+=2; |
|
613 } |
|
614 else |
|
615 { |
|
616 eucjpPacked =0; |
|
617 break; |
|
618 } |
|
619 } |
|
620 } |
|
621 if (eucjpPacked) |
|
622 aConfidenceLevel = (eucjpPacked*100)/sampleLength; |
|
623 else |
|
624 aConfidenceLevel = 0; |
|
625 aConfidenceLevel=(aConfidenceLevel >100)?100:aConfidenceLevel; |
|
626 return ETrue; |
|
627 } |
|
628 |
|
629 CEucjpPackedConverterImpl* CEucjpPackedConverterImpl::NewL() |
|
630 { |
|
631 CEucjpPackedConverterImpl* self = new(ELeave) CEucjpPackedConverterImpl(); |
|
632 return self; |
|
633 } |
|
634 |
|
635 CEucjpPackedConverterImpl::~CEucjpPackedConverterImpl() |
|
636 { |
|
637 } |
|
638 |
|
639 CEucjpPackedConverterImpl::CEucjpPackedConverterImpl() |
|
640 { |
|
641 } |
|
642 |
|
643 const TImplementationProxy ImplementationTable[] = |
|
644 { |
|
645 IMPLEMENTATION_PROXY_ENTRY(0x10006067,CEucjpPackedConverterImpl::NewL) |
|
646 }; |
|
647 |
|
648 EXPORT_C const TImplementationProxy* ImplementationGroupProxy(TInt& aTableCount) |
|
649 { |
|
650 aTableCount = sizeof(ImplementationTable) / sizeof(TImplementationProxy); |
|
651 |
|
652 return ImplementationTable; |
|
653 } |
|
654 |