]> git.saurik.com Git - apple/icu.git/blame - icuSources/tools/toolutil/unewdata.c
ICU-400.42.tar.gz
[apple/icu.git] / icuSources / tools / toolutil / unewdata.c
CommitLineData
b75a7d8f
A
1/*
2*******************************************************************************
3*
46f4442e 4* Copyright (C) 1999,2008, International Business Machines
b75a7d8f
A
5* Corporation and others. All Rights Reserved.
6*
7*******************************************************************************
8* file name: unewdata.c
9* encoding: US-ASCII
10* tab size: 8 (not used)
11* indentation:4
12*
13* created on: 1999oct25
14* created by: Markus W. Scherer
15*/
16
17#include "unicode/utypes.h"
18#include "unicode/putil.h"
19#include "unicode/ustring.h"
20#include "cmemory.h"
21#include "cstring.h"
22#include "filestrm.h"
23#include "unicode/udata.h"
24#include "unewdata.h"
25
26struct UNewDataMemory {
27 FileStream *file;
28 uint16_t headerSize;
29 uint8_t magic1, magic2;
30};
31
32U_CAPI UNewDataMemory * U_EXPORT2
33udata_create(const char *dir, const char *type, const char *name,
34 const UDataInfo *pInfo,
35 const char *comment,
36 UErrorCode *pErrorCode) {
37 UNewDataMemory *pData;
38 uint16_t headerSize, commentLength;
39 char filename[512];
40 uint8_t bytes[16];
46f4442e 41 int length;
b75a7d8f
A
42
43 if(pErrorCode==NULL || U_FAILURE(*pErrorCode)) {
44 return NULL;
45 } else if(name==NULL || *name==0 || pInfo==NULL) {
46 *pErrorCode=U_ILLEGAL_ARGUMENT_ERROR;
47 return NULL;
48 }
49
50 /* allocate the data structure */
51 pData=(UNewDataMemory *)uprv_malloc(sizeof(UNewDataMemory));
52 if(pData==NULL) {
53 *pErrorCode=U_MEMORY_ALLOCATION_ERROR;
54 return NULL;
55 }
46f4442e
A
56
57 /* Check that the full path won't be too long */
58 length = 0; /* Start with nothing */
59 if(dir != NULL && *dir !=0) /* Add directory length if one was given */
60 {
61 length += strlen(dir);
62
63 /* Add 1 if dir doesn't end with path sep */
64 if (dir[strlen(dir) - 1]!= U_FILE_SEP_CHAR) {
65 length++;
66 }
67 }
68 length += strlen(name); /* Add the filename length */
b75a7d8f 69
46f4442e
A
70 if(type != NULL && *type !=0) { /* Add directory length if given */
71 length += strlen(type);
72 }
73
74
75 /* LDH buffer Length error check */
76 if(length > (sizeof(filename) - 1))
77 {
78 *pErrorCode = U_BUFFER_OVERFLOW_ERROR;
79 uprv_free(pData);
80 return NULL;
81 }
82
b75a7d8f
A
83 /* open the output file */
84 if(dir!=NULL && *dir!=0) { /* if dir has a value, we prepend it to the filename */
85 char *p=filename+strlen(dir);
86 uprv_strcpy(filename, dir);
87 if (*(p-1)!=U_FILE_SEP_CHAR) {
88 *p++=U_FILE_SEP_CHAR;
89 *p=0;
90 }
91 } else { /* otherwise, we'll output to the current dir */
92 filename[0]=0;
93 }
94 uprv_strcat(filename, name);
95 if(type!=NULL && *type!=0) {
96 uprv_strcat(filename, ".");
97 uprv_strcat(filename, type);
98 }
99 pData->file=T_FileStream_open(filename, "wb");
100 if(pData->file==NULL) {
101 uprv_free(pData);
102 *pErrorCode=U_FILE_ACCESS_ERROR;
103 return NULL;
104 }
105
106 /* write the header information */
107 headerSize=(uint16_t)(pInfo->size+4);
108 if(comment!=NULL && *comment!=0) {
109 commentLength=(uint16_t)(uprv_strlen(comment)+1);
110 headerSize+=commentLength;
111 } else {
112 commentLength=0;
113 }
114
115 /* write the size of the header, take padding into account */
116 pData->headerSize=(uint16_t)((headerSize+15)&~0xf);
117 pData->magic1=0xda;
118 pData->magic2=0x27;
119 T_FileStream_write(pData->file, &pData->headerSize, 4);
120
121 /* write the information data */
122 T_FileStream_write(pData->file, pInfo, pInfo->size);
123
124 /* write the comment */
125 if(commentLength>0) {
126 T_FileStream_write(pData->file, comment, commentLength);
127 }
128
129 /* write padding bytes to align the data section to 16 bytes */
130 headerSize&=0xf;
131 if(headerSize!=0) {
132 headerSize=(uint16_t)(16-headerSize);
133 uprv_memset(bytes, 0, headerSize);
134 T_FileStream_write(pData->file, bytes, headerSize);
135 }
136
137 return pData;
138}
139
140U_CAPI uint32_t U_EXPORT2
141udata_finish(UNewDataMemory *pData, UErrorCode *pErrorCode) {
142 uint32_t fileLength=0;
143
144 if(pErrorCode==NULL || U_FAILURE(*pErrorCode)) {
145 return 0;
146 }
147
148 if(pData!=NULL) {
149 if(pData->file!=NULL) {
150 /* fflush(pData->file);*/
151 fileLength=T_FileStream_size(pData->file);
152 if(T_FileStream_error(pData->file)) {
153 *pErrorCode=U_FILE_ACCESS_ERROR;
154 } else {
155 fileLength-=pData->headerSize;
156 }
157 T_FileStream_close(pData->file);
158 }
159 uprv_free(pData);
160 }
161
162 return fileLength;
163}
164
165U_CAPI void U_EXPORT2
166udata_write8(UNewDataMemory *pData, uint8_t byte) {
167 if(pData!=NULL && pData->file!=NULL) {
168 T_FileStream_write(pData->file, &byte, 1);
169 }
170}
171
172U_CAPI void U_EXPORT2
173udata_write16(UNewDataMemory *pData, uint16_t word) {
174 if(pData!=NULL && pData->file!=NULL) {
175 T_FileStream_write(pData->file, &word, 2);
176 }
177}
178
179U_CAPI void U_EXPORT2
180udata_write32(UNewDataMemory *pData, uint32_t wyde) {
181 if(pData!=NULL && pData->file!=NULL) {
182 T_FileStream_write(pData->file, &wyde, 4);
183 }
184}
185
186U_CAPI void U_EXPORT2
187udata_writeBlock(UNewDataMemory *pData, const void *s, int32_t length) {
188 if(pData!=NULL && pData->file!=NULL) {
189 if(length>0) {
190 T_FileStream_write(pData->file, s, length);
191 }
192 }
193}
194
195U_CAPI void U_EXPORT2
196udata_writePadding(UNewDataMemory *pData, int32_t length) {
374ca955 197 static const uint8_t padding[16]={
b75a7d8f
A
198 0xaa, 0xaa, 0xaa, 0xaa,
199 0xaa, 0xaa, 0xaa, 0xaa,
200 0xaa, 0xaa, 0xaa, 0xaa,
201 0xaa, 0xaa, 0xaa, 0xaa
202 };
203 if(pData!=NULL && pData->file!=NULL) {
204 while(length>=16) {
205 T_FileStream_write(pData->file, padding, 16);
206 length-=16;
207 }
208 if(length>0) {
209 T_FileStream_write(pData->file, padding, length);
210 }
211 }
212}
213
214U_CAPI void U_EXPORT2
215udata_writeString(UNewDataMemory *pData, const char *s, int32_t length) {
216 if(pData!=NULL && pData->file!=NULL) {
217 if(length==-1) {
218 length=(int32_t)uprv_strlen(s);
219 }
220 if(length>0) {
221 T_FileStream_write(pData->file, s, length);
222 }
223 }
224}
225
226U_CAPI void U_EXPORT2
227udata_writeUString(UNewDataMemory *pData, const UChar *s, int32_t length) {
228 if(pData!=NULL && pData->file!=NULL) {
229 if(length==-1) {
230 length=u_strlen(s);
231 }
232 if(length>0) {
233 T_FileStream_write(pData->file, s, length*sizeof(UChar));
234 }
235 }
236}
237
238/*
239 * Hey, Emacs, please set the following:
240 *
241 * Local Variables:
242 * indent-tabs-mode: nil
243 * End:
244 *
245 */
246