1 /*
2 *******************************************************************************
3 * Copyright (C) 2013-2015, International Business Machines
4 * Corporation and others.  All Rights Reserved.
5 *******************************************************************************
6 * collationinfo.cpp
7 *
8 * created on: 2013aug05
9 * created by: Markus W. Scherer
10 */
11 
12 #include <stdio.h>
13 #include <string.h>
14 
15 #include "unicode/utypes.h"
16 
17 #if !UCONFIG_NO_COLLATION
18 
19 #include "collationdata.h"
20 #include "collationdatareader.h"
21 #include "collationinfo.h"
22 #include "uassert.h"
23 #include "uvectr32.h"
24 
25 U_NAMESPACE_BEGIN
26 
27 void
printSizes(int32_t sizeWithHeader,const int32_t indexes[])28 CollationInfo::printSizes(int32_t sizeWithHeader, const int32_t indexes[]) {
29     int32_t totalSize = indexes[CollationDataReader::IX_TOTAL_SIZE];
30     if(sizeWithHeader > totalSize) {
31         printf("  header size:                  %6ld\n", (long)(sizeWithHeader - totalSize));
32     }
33 
34     int32_t length = indexes[CollationDataReader::IX_INDEXES_LENGTH];
35     printf("  indexes:          %6ld *4 = %6ld\n", (long)length, (long)length * 4);
36 
37     length = getDataLength(indexes, CollationDataReader::IX_REORDER_CODES_OFFSET);
38     if(length != 0) {
39         printf("  reorder codes:    %6ld *4 = %6ld\n", (long)length / 4, (long)length);
40     }
41 
42     length = getDataLength(indexes, CollationDataReader::IX_REORDER_TABLE_OFFSET);
43     if(length != 0) {
44         U_ASSERT(length >= 256);
45         printf("  reorder table:                %6ld\n", (long)length);
46     }
47 
48     length = getDataLength(indexes, CollationDataReader::IX_TRIE_OFFSET);
49     if(length != 0) {
50         printf("  trie size:                    %6ld\n", (long)length);
51     }
52 
53     length = getDataLength(indexes, CollationDataReader::IX_RESERVED8_OFFSET);
54     if(length != 0) {
55         printf("  reserved (offset 8):          %6ld\n", (long)length);
56     }
57 
58     length = getDataLength(indexes, CollationDataReader::IX_CES_OFFSET);
59     if(length != 0) {
60         printf("  CEs:              %6ld *8 = %6ld\n", (long)length / 8, (long)length);
61     }
62 
63     length = getDataLength(indexes, CollationDataReader::IX_RESERVED10_OFFSET);
64     if(length != 0) {
65         printf("  reserved (offset 10):         %6ld\n", (long)length);
66     }
67 
68     length = getDataLength(indexes, CollationDataReader::IX_CE32S_OFFSET);
69     if(length != 0) {
70         printf("  CE32s:            %6ld *4 = %6ld\n", (long)length / 4, (long)length);
71     }
72 
73     length = getDataLength(indexes, CollationDataReader::IX_ROOT_ELEMENTS_OFFSET);
74     if(length != 0) {
75         printf("  rootElements:     %6ld *4 = %6ld\n", (long)length / 4, (long)length);
76     }
77 
78     length = getDataLength(indexes, CollationDataReader::IX_CONTEXTS_OFFSET);
79     if(length != 0) {
80         printf("  contexts:         %6ld *2 = %6ld\n", (long)length / 2, (long)length);
81     }
82 
83     length = getDataLength(indexes, CollationDataReader::IX_UNSAFE_BWD_OFFSET);
84     if(length != 0) {
85         printf("  unsafeBwdSet:     %6ld *2 = %6ld\n", (long)length / 2, (long)length);
86     }
87 
88     length = getDataLength(indexes, CollationDataReader::IX_FAST_LATIN_TABLE_OFFSET);
89     if(length != 0) {
90         printf("  fastLatin table:  %6ld *2 = %6ld\n", (long)length / 2, (long)length);
91     }
92 
93     length = getDataLength(indexes, CollationDataReader::IX_SCRIPTS_OFFSET);
94     if(length != 0) {
95         printf("  scripts data:     %6ld *2 = %6ld\n", (long)length / 2, (long)length);
96     }
97 
98     length = getDataLength(indexes, CollationDataReader::IX_COMPRESSIBLE_BYTES_OFFSET);
99     if(length != 0) {
100         U_ASSERT(length >= 256);
101         printf("  compressibleBytes:            %6ld\n", (long)length);
102     }
103 
104     length = getDataLength(indexes, CollationDataReader::IX_RESERVED18_OFFSET);
105     if(length != 0) {
106         printf("  reserved (offset 18):         %6ld\n", (long)length);
107     }
108 
109     printf(" collator binary total size:    %6ld\n", (long)sizeWithHeader);
110 }
111 
112 int32_t
getDataLength(const int32_t indexes[],int32_t startIndex)113 CollationInfo::getDataLength(const int32_t indexes[], int32_t startIndex) {
114     return indexes[startIndex + 1] - indexes[startIndex];
115 }
116 
117 void
printReorderRanges(const CollationData & data,const int32_t * codes,int32_t length)118 CollationInfo::printReorderRanges(const CollationData &data, const int32_t *codes, int32_t length) {
119     UErrorCode errorCode = U_ZERO_ERROR;
120     UVector32 ranges(errorCode);
121     data.makeReorderRanges(codes, length, ranges, errorCode);
122     if(U_FAILURE(errorCode)) {
123         printf("  error building reorder ranges: %s\n", u_errorName(errorCode));
124         return;
125     }
126 
127     int32_t start = 0;
128     for(int32_t i = 0; i < ranges.size(); ++i) {
129         int32_t pair = ranges.elementAti(i);
130         int32_t limit = (pair >> 16) & 0xffff;
131         int16_t offset = (int16_t)pair;
132         if(offset == 0) {
133             // [inclusive-start, exclusive-limit[
134             printf("          [%04x, %04x[\n", start, limit);
135         } else if(offset > 0) {
136             printf("  reorder [%04x, %04x[ by offset  %02x to [%04x, %04x[\n",
137                     start, limit, offset,
138                     start + (offset << 8), limit + (offset << 8));
139         } else /* offset < 0 */ {
140             printf("  reorder [%04x, %04x[ by offset -%02x to [%04x, %04x[\n",
141                     start, limit, -offset,
142                     start + (offset << 8), limit + (offset << 8));
143         }
144         start = limit;
145     }
146 }
147 
148 U_NAMESPACE_END
149 
150 #endif  // !UCONFIG_NO_COLLATION
151