• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2 ***********************************************************************
3 * Copyright (C) 2016 and later: Unicode, Inc. and others.
4 * License & terms of use: http://www.unicode.org/copyright.html#License
5 ***********************************************************************
6 ***********************************************************************
7 * Copyright (c) 2002-2014, International Business Machines
8 * Corporation and others.  All Rights Reserved.
9 ***********************************************************************
10 ***********************************************************************
11 */
12 #ifndef _CONVPERF_H
13 #define _CONVPERF_H
14 
15 #include <mlang.h>
16 #include <objbase.h>
17 #include <stdlib.h>
18 #include "unicode/ucnv.h"
19 #include "unicode/uclean.h"
20 #include "unicode/ustring.h"
21 #include "cmemory.h" // for UPRV_LENGTHOF
22 
23 #include "unicode/uperf.h"
24 
25 #define CONVERSION_FLAGS (0) /*WC_DEFAULTCHAR WC_COMPOSITECHECK & WC_SEPCHARS*/
26 #define MAX_BUF_SIZE  3048
27 
28 class ICUToUnicodePerfFunction : public UPerfFunction{
29 private:
30     UConverter* conv;
31     const char* src;
32     int32_t srcLen;
33     UChar* target;
34     UChar* targetLimit;
35 
36 public:
ICUToUnicodePerfFunction(const char * name,const char * source,int32_t sourceLen,UErrorCode & status)37     ICUToUnicodePerfFunction(const char* name,  const char* source, int32_t sourceLen, UErrorCode& status){
38         conv = ucnv_open(name,&status);
39         src = source;
40         srcLen = sourceLen;
41         if(U_FAILURE(status)){
42             conv = NULL;
43             return;
44         }
45         target = NULL;
46         targetLimit = NULL;
47         int32_t reqdLen = ucnv_toUChars(conv,   target, 0,
48                                         source, srcLen, &status);
49         if(status==U_BUFFER_OVERFLOW_ERROR) {
50             status=U_ZERO_ERROR;
51             target=(UChar*)malloc((reqdLen) * U_SIZEOF_UCHAR*2);
52             targetLimit = target + reqdLen;
53             if(target == NULL){
54                 status = U_MEMORY_ALLOCATION_ERROR;
55                 return;
56             }
57         }
58     }
call(UErrorCode * status)59     virtual void call(UErrorCode* status){
60         const char* mySrc = src;
61         const char* sourceLimit = src + srcLen;
62         UChar* myTarget = target;
63         ucnv_toUnicode(conv, &myTarget, targetLimit, &mySrc, sourceLimit, NULL, TRUE, status);
64     }
getOperationsPerIteration(void)65     virtual long getOperationsPerIteration(void){
66         return srcLen;
67     }
~ICUToUnicodePerfFunction()68     ~ICUToUnicodePerfFunction(){
69         free(target);
70         ucnv_close(conv);
71     }
72 };
73 class ICUFromUnicodePerfFunction : public UPerfFunction{
74 private:
75     UConverter* conv;
76     const UChar* src;
77     int32_t srcLen;
78     char* target;
79     char* targetLimit;
80     const char* name;
81 
82 public:
ICUFromUnicodePerfFunction(const char * name,const UChar * source,int32_t sourceLen,UErrorCode & status)83     ICUFromUnicodePerfFunction(const char* name,  const UChar* source, int32_t sourceLen, UErrorCode& status){
84         conv = ucnv_open(name,&status);
85         src = source;
86         srcLen = sourceLen;
87         if(U_FAILURE(status)){
88             conv = NULL;
89             return;
90         }
91         target = NULL;
92         targetLimit = NULL;
93         int32_t reqdLen = ucnv_fromUChars(conv,   target, 0,
94                                           source, srcLen, &status);
95         if(status==U_BUFFER_OVERFLOW_ERROR) {
96             status=U_ZERO_ERROR;
97             target=(char*)malloc((reqdLen*2));
98             targetLimit = target + reqdLen;
99             if(target == NULL){
100                 status = U_MEMORY_ALLOCATION_ERROR;
101                 return;
102             }
103         }
104     }
call(UErrorCode * status)105     virtual void call(UErrorCode* status){
106         const UChar* mySrc = src;
107         const UChar* sourceLimit = src + srcLen;
108         char* myTarget = target;
109         ucnv_fromUnicode(conv,&myTarget, targetLimit, &mySrc, sourceLimit, NULL, TRUE, status);
110     }
getOperationsPerIteration(void)111     virtual long getOperationsPerIteration(void){
112         return srcLen;
113     }
~ICUFromUnicodePerfFunction()114     ~ICUFromUnicodePerfFunction(){
115         free(target);
116         ucnv_close(conv);
117     }
118 };
119 
120 class ICUOpenAllConvertersFunction : public UPerfFunction{
121 private:
122     UBool cleanup;
123     int32_t availableConverters;
124     const char **convNames;
125 public:
ICUOpenAllConvertersFunction(UBool callCleanup,UErrorCode & status)126     ICUOpenAllConvertersFunction(UBool callCleanup, UErrorCode& status){
127         int32_t idx;
128         cleanup = callCleanup;
129         availableConverters = ucnv_countAvailable();
130         convNames = new const char *[availableConverters];
131         for (idx = 0; idx < availableConverters; idx++) {
132             convNames[idx] = ucnv_getAvailableName(idx);
133         }
134     }
call(UErrorCode * status)135     virtual void call(UErrorCode* status){
136         int32_t idx;
137         if (cleanup) {
138             u_cleanup();
139         }
140         for (idx = 0; idx < availableConverters; idx++) {
141             ucnv_close(ucnv_open(convNames[idx], status));
142         }
143     }
getOperationsPerIteration(void)144     virtual long getOperationsPerIteration(void){
145         return availableConverters;
146     }
~ICUOpenAllConvertersFunction()147     ~ICUOpenAllConvertersFunction(){
148         delete []convNames;
149     }
150 };
151 
152 class WinANSIToUnicodePerfFunction : public UPerfFunction{
153 
154 private:
155     DWORD uiCodePage;
156     char* src;
157     UINT  srcLen;
158     WCHAR dest[MAX_BUF_SIZE];
159     UINT  dstLen;
160     const char* name;
161 public:
WinANSIToUnicodePerfFunction(const char * cpName,char * pszIn,UINT szLen,UErrorCode & status)162     WinANSIToUnicodePerfFunction(const char* cpName, char* pszIn,UINT szLen, UErrorCode& status){
163         name = cpName;
164         src = pszIn;
165         srcLen = szLen;
166         dstLen = UPRV_LENGTHOF(dest);
167         unsigned short bEnc[30]={'\0'};
168         const char* tenc=name;
169         for(int i=0;*tenc!='\0';i++){
170             bEnc[i]=*tenc;
171             tenc++;
172         }
173         LPMULTILANGUAGE2 pMulti;
174 
175         CoInitialize(NULL);
176 
177         /* create instance of converter object*/
178         CoCreateInstance(
179                           __uuidof(CMultiLanguage),
180                           NULL,
181                           CLSCTX_SERVER,
182                           __uuidof(IMultiLanguage2),
183                           (void**)&pMulti
184                           );
185 
186 
187 
188         MIMECSETINFO mimeInfo;
189 
190         mimeInfo.uiCodePage = 0;
191         mimeInfo.uiInternetEncoding =0;
192         /* get the charset info */
193         pMulti->GetCharsetInfo((wchar_t *)bEnc,&mimeInfo);
194         uiCodePage = (mimeInfo.uiInternetEncoding==0)?mimeInfo.uiCodePage:mimeInfo.uiInternetEncoding;
195     }
call(UErrorCode * status)196     virtual void call(UErrorCode* status){
197         int winSize =MultiByteToWideChar(uiCodePage,CONVERSION_FLAGS,src,srcLen,dest,dstLen);
198     }
getOperationsPerIteration(void)199     virtual long getOperationsPerIteration(void){
200         return srcLen;
201     }
202 };
203 
204 class WinANSIFromUnicodePerfFunction : public UPerfFunction{
205 
206 private:
207     DWORD uiCodePage;
208     WCHAR* src;
209     UINT  srcLen;
210     char dest[MAX_BUF_SIZE];
211     UINT  dstLen;
212     const char* name;
213     BOOL lpUsedDefaultChar;
214 
215 public:
WinANSIFromUnicodePerfFunction(const char * cpName,WCHAR * pszIn,UINT szLen,UErrorCode & status)216     WinANSIFromUnicodePerfFunction(const char* cpName,  WCHAR* pszIn,UINT szLen, UErrorCode& status){
217         name = cpName;
218         src = pszIn;
219         srcLen = szLen;
220         dstLen = UPRV_LENGTHOF(dest);
221         lpUsedDefaultChar=FALSE;
222         unsigned short bEnc[30]={'\0'};
223         const char* tenc=name;
224         for(int i=0;*tenc!='\0';i++){
225             bEnc[i]=*tenc;
226             tenc++;
227         }
228         LPMULTILANGUAGE2 pMulti;
229 
230         CoInitialize(NULL);
231 
232         /* create instance of converter object*/
233         CoCreateInstance(
234                           __uuidof(CMultiLanguage),
235                           NULL,
236                           CLSCTX_SERVER,
237                           __uuidof(IMultiLanguage2),
238                           (void**)&pMulti
239                           );
240 
241 
242 
243         MIMECSETINFO mimeInfo;
244         mimeInfo.uiCodePage = 0;
245         mimeInfo.uiInternetEncoding =0;
246         /* get the charset info */
247         pMulti->GetCharsetInfo((wchar_t *)bEnc,&mimeInfo);
248         uiCodePage = (mimeInfo.uiInternetEncoding==0)?mimeInfo.uiCodePage:mimeInfo.uiInternetEncoding;
249     }
call(UErrorCode * status)250     virtual void call(UErrorCode* status){
251         BOOL* pUsedDefaultChar =(uiCodePage==CP_UTF8)?NULL:&lpUsedDefaultChar;
252         int winSize = WideCharToMultiByte(uiCodePage,CONVERSION_FLAGS,src,srcLen,dest,dstLen,NULL, pUsedDefaultChar);
253     }
getOperationsPerIteration(void)254     virtual long getOperationsPerIteration(void){
255         return srcLen;
256     }
257 };
getErr(HRESULT err,UErrorCode & status)258 static inline void getErr(HRESULT err, UErrorCode& status){
259 
260     switch (err){
261 
262     case S_OK:
263         //printf("Operation %s successful\n",operation);
264         break;
265     case S_FALSE:
266         status = U_INTERNAL_PROGRAM_ERROR;
267         break;
268     case E_FAIL:
269         status = U_ILLEGAL_CHAR_FOUND;
270     }
271 }
272 class WinIMultiLanguageToUnicodePerfFunction : public UPerfFunction{
273 
274 private:
275     LPMULTILANGUAGE2 pMulti;
276     LPMLANGCONVERTCHARSET pConvToUni;
277     char* src;
278     UINT  srcLen;
279     WCHAR dst[MAX_BUF_SIZE];
280     UINT  dstLen;
281     const char* cpName;
282 
283 public:
WinIMultiLanguageToUnicodePerfFunction(const char * name,char * source,UINT sourceLen,UErrorCode & status)284     WinIMultiLanguageToUnicodePerfFunction(const char* name,char* source, UINT sourceLen, UErrorCode& status){
285 
286         CoInitialize(NULL);
287 
288         /* create instance of converter object*/
289         CoCreateInstance(
290                           __uuidof(CMultiLanguage),
291                           NULL,
292                           CLSCTX_SERVER,
293                           __uuidof(IMultiLanguage2),
294                           (void**)&pMulti
295                           );
296 
297 
298 
299         MIMECSETINFO mimeInfo;
300         mimeInfo.uiCodePage = 0;
301         mimeInfo.uiInternetEncoding =0;
302         HRESULT err=S_OK;
303         unsigned short bEnc[30]={'\0'};
304         const char* tenc=name;
305         for(int i=0;*tenc!='\0';i++){
306             bEnc[i]=*tenc;
307             tenc++;
308         }
309         /* get the charset info */
310         pMulti->GetCharsetInfo((wchar_t *)bEnc,&mimeInfo);
311         pMulti->CreateConvertCharset(mimeInfo.uiCodePage, 1200 /*unicode*/, (DWORD)0,&pConvToUni);
312         getErr(err,status);
313         src = source;
314         srcLen = sourceLen;
315         dstLen = UPRV_LENGTHOF(dst);
316         cpName = name;
317     }
318 
call(UErrorCode * status)319     virtual void call(UErrorCode* status){
320         HRESULT err= pConvToUni->DoConversionToUnicode(src,&srcLen,dst, &dstLen);
321         getErr(err,*status);
322     }
getOperationsPerIteration(void)323     virtual long getOperationsPerIteration(void){
324         return srcLen;
325     }
326 };
327 
328 class WinIMultiLanguageFromUnicodePerfFunction : public UPerfFunction{
329 
330 private:
331     LPMULTILANGUAGE2 pMulti;
332     LPMLANGCONVERTCHARSET pConvFromUni;
333     WCHAR* src;
334     UINT  srcLen;
335     char dst[MAX_BUF_SIZE];
336     UINT  dstLen;
337     const char* cpName;
338 
339 public:
WinIMultiLanguageFromUnicodePerfFunction(const char * name,WCHAR * source,UINT sourceLen,UErrorCode & status)340     WinIMultiLanguageFromUnicodePerfFunction(const char* name,WCHAR* source, UINT sourceLen, UErrorCode& status){
341 
342         CoInitialize(NULL);
343 
344         /* create instance of converter object*/
345         CoCreateInstance(
346                           __uuidof(CMultiLanguage),
347                           NULL,
348                           CLSCTX_SERVER,
349                           __uuidof(IMultiLanguage2),
350                           (void**)&pMulti
351                           );
352 
353 
354 
355         MIMECSETINFO mimeInfo;
356         mimeInfo.uiCodePage = 0;
357         mimeInfo.uiInternetEncoding =0;
358         HRESULT err=S_OK;
359         unsigned short bEnc[30]={'\0'};
360         const char* tenc=name;
361         for(int i=0;*tenc!='\0';i++){
362             bEnc[i]=*tenc;
363             tenc++;
364         }
365         /* get the charset info */
366         pMulti->GetCharsetInfo((wchar_t *)bEnc,&mimeInfo);
367         pMulti->CreateConvertCharset(1200 /*unicode*/, mimeInfo.uiCodePage, (DWORD)0,&pConvFromUni);
368         getErr(err,status);
369         src = source;
370         srcLen = sourceLen;
371         dstLen = UPRV_LENGTHOF(dst);
372         cpName = name;
373 
374     }
375 
call(UErrorCode * status)376     virtual void call(UErrorCode* status){
377         HRESULT err= pConvFromUni->DoConversionFromUnicode(src,&srcLen,dst, &dstLen);
378         getErr(err,*status);
379     }
getOperationsPerIteration(void)380     virtual long getOperationsPerIteration(void){
381         return srcLen;
382     }
383 };
384 
385 class WinIMultiLanguage2ToUnicodePerfFunction : public UPerfFunction{
386 
387 private:
388     LPMULTILANGUAGE2 pMulti;
389     char* src;
390     UINT  srcLen;
391     WCHAR dst[MAX_BUF_SIZE];
392     UINT  dstLen;
393     const char* cpName;
394     DWORD dwEnc;
395 public:
WinIMultiLanguage2ToUnicodePerfFunction(const char * name,char * source,UINT sourceLen,UErrorCode & status)396     WinIMultiLanguage2ToUnicodePerfFunction(const char* name,char* source, UINT sourceLen, UErrorCode& status){
397 
398         CoInitialize(NULL);
399 
400         /* create instance of converter object*/
401         CoCreateInstance(
402                           __uuidof(CMultiLanguage),
403                           NULL,
404                           CLSCTX_SERVER,
405                           __uuidof(IMultiLanguage2),
406                           (void**)&pMulti
407                           );
408 
409         src = source;
410         srcLen = sourceLen;
411         dstLen = UPRV_LENGTHOF(dst);
412         cpName = name;
413         unsigned short bEnc[30]={'\0'};
414         const char* tenc=name;
415         for(int i=0;*tenc!='\0';i++){
416             bEnc[i]=*tenc;
417             tenc++;
418         }
419         /* get the charset info */
420         MIMECSETINFO mimeInfo;
421         mimeInfo.uiCodePage = 0;
422         mimeInfo.uiInternetEncoding =0;
423         pMulti->GetCharsetInfo((wchar_t *)bEnc,&mimeInfo);
424         dwEnc = (mimeInfo.uiInternetEncoding==0)?mimeInfo.uiCodePage:mimeInfo.uiInternetEncoding;
425     }
426 
call(UErrorCode * status)427     virtual void call(UErrorCode* status){
428         DWORD dwMode=0;
429         HRESULT err=  pMulti->ConvertStringToUnicode(&dwMode,dwEnc,(char*)src,&srcLen,dst, &dstLen);
430         getErr(err,*status);
431     }
getOperationsPerIteration(void)432     virtual long getOperationsPerIteration(void){
433         return srcLen;
434     }
435 };
436 
437 class WinIMultiLanguage2FromUnicodePerfFunction : public UPerfFunction{
438 
439 private:
440     LPMULTILANGUAGE2 pMulti;
441     LPMLANGCONVERTCHARSET pConvFromUni;
442     WCHAR* src;
443     UINT  srcLen;
444     char dst[MAX_BUF_SIZE];
445     UINT  dstLen;
446     const char* cpName;
447     DWORD dwEnc;
448 
449 public:
WinIMultiLanguage2FromUnicodePerfFunction(const char * name,WCHAR * source,UINT sourceLen,UErrorCode & status)450     WinIMultiLanguage2FromUnicodePerfFunction(const char* name,WCHAR* source, UINT sourceLen, UErrorCode& status){
451 
452         CoInitialize(NULL);
453 
454         /* create instance of converter object*/
455         CoCreateInstance(
456                           __uuidof(CMultiLanguage),
457                           NULL,
458                           CLSCTX_SERVER,
459                           __uuidof(IMultiLanguage2),
460                           (void**)&pMulti
461                           );
462 
463 
464         unsigned short bEnc[30]={'\0'};
465         const char* tenc=name;
466         for(int i=0;*tenc!='\0';i++){
467             bEnc[i]=*tenc;
468             tenc++;
469         }
470         src = source;
471         srcLen = sourceLen;
472         dstLen = UPRV_LENGTHOF(dst);
473         cpName = name;
474         /* get the charset info */
475         MIMECSETINFO mimeInfo;
476         mimeInfo.uiCodePage = 0;
477         mimeInfo.uiInternetEncoding =0;
478 
479         pMulti->GetCharsetInfo((wchar_t *)bEnc,&mimeInfo);
480         dwEnc = (mimeInfo.uiInternetEncoding==0)?mimeInfo.uiCodePage:mimeInfo.uiInternetEncoding;
481     }
482 
call(UErrorCode * status)483     virtual void call(UErrorCode* status){
484         DWORD dwMode=0;
485         HRESULT err= pMulti->ConvertStringFromUnicode(&dwMode,dwEnc,src,&srcLen,dst, &dstLen);
486         getErr(err,*status);
487     }
getOperationsPerIteration(void)488     virtual long getOperationsPerIteration(void){
489         return srcLen;
490     }
491 };
492 
493 class  ConverterPerformanceTest : public UPerfTest{
494 
495 public:
496 
497     ConverterPerformanceTest(int32_t argc, const char* argv[], UErrorCode& status);
498     ~ConverterPerformanceTest();
499     virtual UPerfFunction* runIndexedTest(int32_t index, UBool exec,const char* &name, char* par = NULL);
500 
501     UPerfFunction* TestICU_CleanOpenAllConverters();
502     UPerfFunction* TestICU_OpenAllConverters();
503 
504     UPerfFunction* TestICU_UTF8_ToUnicode();
505     UPerfFunction* TestICU_UTF8_FromUnicode();
506     UPerfFunction* TestWinANSI_UTF8_ToUnicode();
507     UPerfFunction* TestWinANSI_UTF8_FromUnicode();
508     UPerfFunction* TestWinIML2_UTF8_ToUnicode();
509     UPerfFunction* TestWinIML2_UTF8_FromUnicode();
510 
511     UPerfFunction* TestICU_Latin1_ToUnicode();
512     UPerfFunction* TestICU_Latin1_FromUnicode();
513     UPerfFunction* TestWinANSI_Latin1_ToUnicode();
514     UPerfFunction* TestWinANSI_Latin1_FromUnicode();
515     UPerfFunction* TestWinIML2_Latin1_ToUnicode();
516     UPerfFunction* TestWinIML2_Latin1_FromUnicode();
517 
518     UPerfFunction* TestICU_EBCDIC_Arabic_ToUnicode();
519     UPerfFunction* TestICU_EBCDIC_Arabic_FromUnicode();
520     UPerfFunction* TestWinANSI_EBCDIC_Arabic_ToUnicode();
521     UPerfFunction* TestWinANSI_EBCDIC_Arabic_FromUnicode();
522     UPerfFunction* TestWinIML2_EBCDIC_Arabic_ToUnicode();
523     UPerfFunction* TestWinIML2_EBCDIC_Arabic_FromUnicode();
524 
525     UPerfFunction* TestICU_Latin8_ToUnicode();
526     UPerfFunction* TestICU_Latin8_FromUnicode();
527     UPerfFunction* TestWinANSI_Latin8_ToUnicode();
528     UPerfFunction* TestWinANSI_Latin8_FromUnicode();
529     UPerfFunction* TestWinIML2_Latin8_ToUnicode();
530     UPerfFunction* TestWinIML2_Latin8_FromUnicode();
531 
532 
533     UPerfFunction* TestICU_SJIS_ToUnicode();
534     UPerfFunction* TestICU_SJIS_FromUnicode();
535     UPerfFunction* TestWinANSI_SJIS_ToUnicode();
536     UPerfFunction* TestWinANSI_SJIS_FromUnicode();
537     UPerfFunction* TestWinIML2_SJIS_ToUnicode();
538     UPerfFunction* TestWinIML2_SJIS_FromUnicode();
539 
540     UPerfFunction* TestICU_EUCJP_ToUnicode();
541     UPerfFunction* TestICU_EUCJP_FromUnicode();
542     UPerfFunction* TestWinANSI_EUCJP_ToUnicode();
543     UPerfFunction* TestWinANSI_EUCJP_FromUnicode();
544     UPerfFunction* TestWinIML2_EUCJP_ToUnicode();
545     UPerfFunction* TestWinIML2_EUCJP_FromUnicode();
546 
547     UPerfFunction* TestICU_GB2312_ToUnicode();
548     UPerfFunction* TestICU_GB2312_FromUnicode();
549     UPerfFunction* TestWinANSI_GB2312_ToUnicode();
550     UPerfFunction* TestWinANSI_GB2312_FromUnicode();
551     UPerfFunction* TestWinIML2_GB2312_ToUnicode();
552     UPerfFunction* TestWinIML2_GB2312_FromUnicode();
553 
554 
555     UPerfFunction* TestICU_ISO2022KR_ToUnicode();
556     UPerfFunction* TestICU_ISO2022KR_FromUnicode();
557     UPerfFunction* TestWinANSI_ISO2022KR_ToUnicode();
558     UPerfFunction* TestWinANSI_ISO2022KR_FromUnicode();
559     UPerfFunction* TestWinIML2_ISO2022KR_ToUnicode();
560     UPerfFunction* TestWinIML2_ISO2022KR_FromUnicode();
561 
562     UPerfFunction* TestICU_ISO2022JP_ToUnicode();
563     UPerfFunction* TestICU_ISO2022JP_FromUnicode();
564     UPerfFunction* TestWinANSI_ISO2022JP_ToUnicode();
565     UPerfFunction* TestWinANSI_ISO2022JP_FromUnicode();
566     UPerfFunction* TestWinIML2_ISO2022JP_ToUnicode();
567     UPerfFunction* TestWinIML2_ISO2022JP_FromUnicode();
568 
569 };
570 
571 #endif
572 
573