]>
git.saurik.com Git - apple/icu.git/blob - icuSources/io/ufmt_cmn.c
2 ******************************************************************************
4 * Copyright (C) 1998-2014, International Business Machines
5 * Corporation and others. All Rights Reserved.
7 ******************************************************************************
11 * Modification History:
13 * Date Name Description
14 * 12/02/98 stephen Creation.
15 * 03/12/99 stephen Modified for new C API.
16 * 03/15/99 stephen Added defaultCPToUnicode, unicodeToDefaultCP
17 * 07/19/99 stephen Fixed bug in defaultCPToUnicode
18 ******************************************************************************
24 #include "unicode/uchar.h"
25 #include "unicode/ucnv.h"
28 #if !UCONFIG_NO_CONVERSION
31 #define DIGIT_0 0x0030
32 #define DIGIT_9 0x0039
33 #define LOWERCASE_A 0x0061
34 #define UPPERCASE_A 0x0041
35 #define LOWERCASE_Z 0x007A
36 #define UPPERCASE_Z 0x005A
39 ufmt_digitvalue(UChar c
)
41 if( ((c
>=DIGIT_0
)&&(c
<=DIGIT_9
)) ||
42 ((c
>=LOWERCASE_A
)&&(c
<=LOWERCASE_Z
)) ||
43 ((c
>=UPPERCASE_A
)&&(c
<=UPPERCASE_Z
)) )
45 return c
- DIGIT_0
- (c
>= 0x0041 ? (c
>= 0x0061 ? 39 : 7) : 0);
57 int digitVal
= ufmt_digitvalue(c
);
59 return (UBool
)(digitVal
< radix
&& digitVal
>= 0);
62 #define TO_UC_DIGIT(a) a <= 9 ? (DIGIT_0 + a) : (0x0037 + a)
63 #define TO_LC_DIGIT(a) a <= 9 ? (DIGIT_0 + a) : (0x0057 + a)
66 ufmt_64tou(UChar
*buffer
,
75 UChar
*left
, *right
, temp
;
78 digit
= (uint32_t)(value
% radix
);
79 value
= value
/ radix
;
80 buffer
[length
++] = (UChar
)(uselower
? TO_LC_DIGIT(digit
)
81 : TO_UC_DIGIT(digit
));
84 /* pad with zeroes to make it minDigits long */
85 if(minDigits
!= -1 && length
< minDigits
) {
86 while(length
< minDigits
&& length
< *len
)
87 buffer
[length
++] = DIGIT_0
; /*zero padding */
90 /* reverse the buffer */
92 right
= buffer
+ length
;
93 while(left
< --right
) {
103 ufmt_ptou(UChar
*buffer
,
110 uint8_t *ptrIdx
= (uint8_t *)&value
;
113 for (i
= 0; i
< (int32_t)sizeof(void *); i
++)
115 for (i
= (int32_t)sizeof(void *)-1; i
>= 0 ; i
--)
118 uint8_t byteVal
= ptrIdx
[i
];
119 uint16_t firstNibble
= (uint16_t)(byteVal
>>4);
120 uint16_t secondNibble
= (uint16_t)(byteVal
&0xF);
122 buffer
[length
++]=TO_LC_DIGIT(firstNibble
);
123 buffer
[length
++]=TO_LC_DIGIT(secondNibble
);
126 buffer
[length
++]=TO_UC_DIGIT(firstNibble
);
127 buffer
[length
++]=TO_UC_DIGIT(secondNibble
);
135 ufmt_uto64(const UChar
*buffer
,
144 /* intialize parameters */
145 limit
= buffer
+ *len
;
149 /* iterate through buffer */
150 while(ufmt_isdigit(*buffer
, radix
) && buffer
< limit
) {
152 /* read the next digit */
154 result
+= ufmt_digitvalue(*buffer
++);
156 /* increment our count */
164 #define NIBBLE_PER_BYTE 2
166 ufmt_utop(const UChar
*buffer
,
169 int32_t count
, resultIdx
, incVal
, offset
;
170 /* This union allows the pointer to be written as an array. */
173 uint8_t bytes
[sizeof(void*)];
176 /* intialize variables */
181 /* Skip the leading zeros */
182 while(buffer
[count
] == DIGIT_0
|| u_isspace(buffer
[count
])) {
187 /* iterate through buffer, stop when you hit the end */
188 while(ufmt_isdigit(buffer
[count
], 16) && count
< *len
) {
189 /* increment the count consumed */
193 /* detect overflow */
194 if (count
- offset
> (int32_t)(sizeof(void*)*NIBBLE_PER_BYTE
)) {
195 offset
= count
- (int32_t)(sizeof(void*)*NIBBLE_PER_BYTE
);
198 /* Initialize the direction of the input */
201 resultIdx
= (int32_t)(sizeof(void*) - 1);
206 /* Write how much was consumed. */
208 while(--count
>= offset
) {
209 /* Get the first nibble of the byte */
210 uint8_t byte
= (uint8_t)ufmt_digitvalue(buffer
[count
]);
212 if (count
> offset
) {
213 /* Get the second nibble of the byte when available */
214 byte
= (uint8_t)(byte
+ (ufmt_digitvalue(buffer
[--count
]) << 4));
216 /* Write the byte into the array */
217 result
.bytes
[resultIdx
] = byte
;
225 ufmt_defaultCPToUnicode(const char *s
, int32_t sSize
,
226 UChar
*target
, int32_t tSize
)
229 UErrorCode status
= U_ZERO_ERROR
;
230 UConverter
*defConverter
= u_getDefaultConverter(&status
);
232 if(U_FAILURE(status
) || defConverter
== 0)
236 sSize
= uprv_strlen(s
) + 1;
239 /* perform the conversion in one swoop */
243 ucnv_toUnicode(defConverter
, &alias
, alias
+ tSize
, &s
, s
+ sSize
- 1,
244 NULL
, TRUE
, &status
);
247 /* add the null terminator */
251 u_releaseDefaultConverter(defConverter
);