1 // © 2016 and later: Unicode, Inc. and others.
2 // License & terms of use: http://www.unicode.org/copyright.html
4 *******************************************************************************
6 * Copyright (C) 2003-2014, International Business Machines
7 * Corporation and others. All Rights Reserved.
9 *******************************************************************************
10 * file name: nfsprep.c
12 * tab size: 8 (not used)
15 * created on: 2003jul11
16 * created by: Ram Viswanadha
19 #include "unicode/utypes.h"
28 #define NFS4_MAX_BUFFER_SIZE 1000
29 #define PREFIX_SUFFIX_SEPARATOR 0x0040 /* '@' */
32 const char* NFS4DataFileNames
[5] ={
42 nfs4_prepare( const char* src
, int32_t srcLength
,
43 char* dest
, int32_t destCapacity
,
44 NFS4ProfileState state
,
45 UParseError
* parseError
,
48 UChar b1Stack
[NFS4_MAX_BUFFER_SIZE
],
49 b2Stack
[NFS4_MAX_BUFFER_SIZE
];
50 char b3Stack
[NFS4_MAX_BUFFER_SIZE
];
52 /* initialize pointers to stack buffers */
53 UChar
*b1
= b1Stack
, *b2
= b2Stack
;
55 int32_t b1Len
=0, b2Len
=0, b3Len
=0,
56 b1Capacity
= NFS4_MAX_BUFFER_SIZE
,
57 b2Capacity
= NFS4_MAX_BUFFER_SIZE
,
58 b3Capacity
= NFS4_MAX_BUFFER_SIZE
,
61 UStringPrepProfile
* profile
= NULL
;
62 /* get the test data path */
63 const char *testdatapath
= NULL
;
65 if(status
==NULL
|| U_FAILURE(*status
)){
68 if((src
==NULL
) || (srcLength
< -1) || (destCapacity
<0) || (!dest
&& destCapacity
> 0)){
69 *status
= U_ILLEGAL_ARGUMENT_ERROR
;
72 testdatapath
= loadTestData(status
);
74 /* convert the string from UTF-8 to UTF-16 */
75 u_strFromUTF8(b1
,b1Capacity
,&b1Len
,src
,srcLength
,status
);
76 if(*status
== U_BUFFER_OVERFLOW_ERROR
){
78 /* reset the status */
79 *status
= U_ZERO_ERROR
;
81 b1
= (UChar
*) malloc(b1Len
* U_SIZEOF_UCHAR
);
83 *status
= U_MEMORY_ALLOCATION_ERROR
;
88 u_strFromUTF8(b1
, b1Capacity
, &b1Len
, src
, srcLength
, status
);
91 /* open the profile */
92 profile
= usprep_open(testdatapath
, NFS4DataFileNames
[state
], status
);
93 /* prepare the string */
94 b2Len
= usprep_prepare(profile
, b1
, b1Len
, b2
, b2Capacity
, USPREP_DEFAULT
, parseError
, status
);
95 if(*status
== U_BUFFER_OVERFLOW_ERROR
){
96 *status
= U_ZERO_ERROR
;
97 b2
= (UChar
*) malloc(b2Len
* U_SIZEOF_UCHAR
);
99 *status
= U_MEMORY_ALLOCATION_ERROR
;
102 b2Len
= usprep_prepare(profile
, b1
, b1Len
, b2
, b2Len
, USPREP_DEFAULT
, parseError
, status
);
105 /* convert the string back to UTF-8 */
106 u_strToUTF8(b3
,b3Capacity
, &b3Len
, b2
, b2Len
, status
);
107 if(*status
== U_BUFFER_OVERFLOW_ERROR
){
108 *status
= U_ZERO_ERROR
;
109 b3
= (char*) malloc(b3Len
);
111 *status
= U_MEMORY_ALLOCATION_ERROR
;
115 u_strToUTF8(b3
,b3Capacity
, &b3Len
, b2
, b2Len
, status
);
119 if(dest
!=NULL
&& reqLength
<= destCapacity
){
120 memmove(dest
, b3
, reqLength
);
134 return u_terminateChars(dest
, destCapacity
, reqLength
, status
);
137 /* sorted array for binary search*/
138 static const char* special_prefixes
[]={
139 "\x0041\x004e\x004f\x004e\x0059\x004d\x004f\x0055\x0053",
140 "\x0041\x0055\x0054\x0048\x0045\x004e\x0054\x0049\x0043\x0041\x0054\x0045\x0044",
141 "\x0042\x0041\x0054\x0043\x0048",
142 "\x0044\x0049\x0041\x004c\x0055\x0050",
143 "\x0045\x0056\x0045\x0052\x0059\x004f\x004e\x0045",
144 "\x0047\x0052\x004f\x0055\x0050",
145 "\x0049\x004e\x0054\x0045\x0052\x0041\x0043\x0054\x0049\x0056\x0045",
146 "\x004e\x0045\x0054\x0057\x004f\x0052\x004b",
147 "\x004f\x0057\x004e\x0045\x0052",
151 /* binary search the sorted array */
153 findStringIndex(const char* const *sortedArr
, int32_t sortedArrLen
, const char* target
, int32_t targetLen
){
155 int left
, middle
, right
,rc
;
158 right
= sortedArrLen
-1;
160 while(left
<= right
){
161 middle
= (left
+right
)/2;
162 rc
=strncmp(sortedArr
[middle
],target
, targetLen
);
176 getPrefixSuffix(const char *src
, int32_t srcLength
,
177 const char **prefix
, int32_t *prefixLen
,
178 const char **suffix
, int32_t *suffixLen
,
184 if(src
[i
] == PREFIX_SUFFIX_SEPARATOR
){
185 if((i
+1) == srcLength
){
186 /* we reached the end of the string */
191 i
++;/* the prefix contains the separator */
198 *suffixLen
= srcLength
- i
;
199 /* special prefixes must not be followed by suffixes! */
200 if((findStringIndex(special_prefixes
,UPRV_LENGTHOF(special_prefixes
), *prefix
, *prefixLen
-1) != -1) && (*suffix
!= NULL
)){
201 *status
= U_PARSE_ERROR
;
208 nfs4_mixed_prepare( const char* src
, int32_t srcLength
,
209 char* dest
, int32_t destCapacity
,
210 UParseError
* parseError
,
213 const char *prefix
= NULL
, *suffix
= NULL
;
214 int32_t prefixLen
=0, suffixLen
=0;
215 char pStack
[NFS4_MAX_BUFFER_SIZE
],
216 sStack
[NFS4_MAX_BUFFER_SIZE
];
217 char *p
=pStack
, *s
=sStack
;
218 int32_t pLen
=0, sLen
=0, reqLen
=0,
219 pCapacity
= NFS4_MAX_BUFFER_SIZE
,
220 sCapacity
= NFS4_MAX_BUFFER_SIZE
;
223 if(status
==NULL
|| U_FAILURE(*status
)){
226 if((src
==NULL
) || (srcLength
< -1) || (destCapacity
<0) || (!dest
&& destCapacity
> 0)){
227 *status
= U_ILLEGAL_ARGUMENT_ERROR
;
231 srcLength
= (int32_t)strlen(src
);
233 getPrefixSuffix(src
, srcLength
, &prefix
, &prefixLen
, &suffix
, &suffixLen
, status
);
235 /* prepare the prefix */
236 pLen
= nfs4_prepare(prefix
, prefixLen
, p
, pCapacity
, NFS4_MIXED_PREP_PREFIX
, parseError
, status
);
237 if(*status
== U_BUFFER_OVERFLOW_ERROR
){
238 *status
= U_ZERO_ERROR
;
239 p
= (char*) malloc(pLen
);
241 *status
= U_MEMORY_ALLOCATION_ERROR
;
244 pLen
= nfs4_prepare(prefix
, prefixLen
, p
, pLen
, NFS4_MIXED_PREP_PREFIX
, parseError
, status
);
247 /* prepare the suffix */
249 sLen
= nfs4_prepare(suffix
, suffixLen
, s
, sCapacity
, NFS4_MIXED_PREP_SUFFIX
, parseError
, status
);
250 if(*status
== U_BUFFER_OVERFLOW_ERROR
){
251 *status
= U_ZERO_ERROR
;
252 s
= (char*) malloc(pLen
);
254 *status
= U_MEMORY_ALLOCATION_ERROR
;
257 sLen
= nfs4_prepare(suffix
, suffixLen
, s
, sLen
, NFS4_MIXED_PREP_SUFFIX
, parseError
, status
);
260 reqLen
= pLen
+sLen
+1 /* for the delimiter */;
261 if(dest
!= NULL
&& reqLen
<= destCapacity
){
262 memmove(dest
, p
, pLen
);
265 dest
[pLen
++] = PREFIX_SUFFIX_SEPARATOR
;
266 memmove(dest
+pLen
, s
, sLen
);
278 return u_terminateChars(dest
, destCapacity
, reqLen
, status
);
282 nfs4_cis_prepare( const char* src
, int32_t srcLength
,
283 char* dest
, int32_t destCapacity
,
284 UParseError
* parseError
,
286 return nfs4_prepare(src
, srcLength
, dest
, destCapacity
, NFS4_CIS_PREP
, parseError
, status
);
291 nfs4_cs_prepare( const char* src
, int32_t srcLength
,
292 char* dest
, int32_t destCapacity
,
293 UBool isCaseSensitive
,
294 UParseError
* parseError
,
297 return nfs4_prepare(src
, srcLength
, dest
, destCapacity
, NFS4_CS_PREP_CS
, parseError
, status
);
299 return nfs4_prepare(src
, srcLength
, dest
, destCapacity
, NFS4_CS_PREP_CI
, parseError
, status
);
305 * Hey, Emacs, please set the following:
308 * indent-tabs-mode: nil