1 : /**********************************************************************
2 : * $Id: iom_utilities.cpp 16745 2009-04-07 20:26:08Z warmerdam $
3 : *
4 : * Project: iom - The INTERLIS Object Model
5 : * Purpose: For more information, please see <http://iom.sourceforge.net>
6 : * Author: Claude Eisenhut
7 : *
8 : **********************************************************************
9 : * Copyright (c) 2007, Claude Eisenhut
10 : *
11 : * Permission is hereby granted, free of charge, to any person obtaining a
12 : * copy of this software and associated documentation files (the "Software"),
13 : * to deal in the Software without restriction, including without limitation
14 : * the rights to use, copy, modify, merge, publish, distribute, sublicense,
15 : * and/or sell copies of the Software, and to permit persons to whom the
16 : * Software is furnished to do so, subject to the following conditions:
17 : *
18 : * The above copyright notice and this permission notice shall be included
19 : * in all copies or substantial portions of the Software.
20 : *
21 : * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
22 : * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
23 : * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
24 : * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
25 : * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
26 : * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
27 : * DEALINGS IN THE SOFTWARE.
28 : ****************************************************************************/
29 :
30 : /** @file
31 : * implementation of utility functions
32 : * @defgroup utilities utility functions
33 : * @{
34 : */
35 :
36 : #include <cstdio>
37 : #include <iostream>
38 : #include <string>
39 : #include <string.h>
40 :
41 : #include <iom/iom_p.h>
42 :
43 :
44 :
45 :
46 : #include <sys/types.h>
47 : #include <sys/stat.h>
48 :
49 : #if defined(__MSVCRT__) || defined(_MSC_VER)
50 : #define stat _stat
51 : #else
52 : #include <unistd.h>
53 : #endif
54 :
55 : #if !defined(__MSVCRT__) && !defined(_MSC_VER)
56 :
57 : #include <stdlib.h>
58 : #include <string.h>
59 :
60 : #define PATHSEP ':'
61 :
62 : /*
63 : _searchenv is a function provided by the MSVC library that finds
64 : files which may be anywhere along a path which appears in an
65 : environment variable.
66 : */
67 :
68 0 : static void _searchenv(const char *name, const char *envname, char *hitfile)
69 : {
70 :
71 : // Default failure indication
72 0 : *hitfile = '\0';
73 :
74 : // If the given name is absolute, then don't search the
75 : // path, but use it as is.
76 0 : if(
77 : #ifdef WIN32
78 : strchr(name, ':') != NULL || // Contain a drive spec?
79 : name[0] == '\\' || // Start with absolute ref?
80 : #endif
81 : name[0] == '/') // Start with absolute ref?
82 : {
83 : // Copy to target
84 0 : strcpy(hitfile, name);
85 0 : return;
86 : }
87 :
88 : char *cp;
89 0 : cp = getenv(envname);
90 0 : if(cp == NULL){
91 : // Variable not defined, no search.
92 0 : return;
93 : }
94 :
95 0 : while(*cp)
96 : {
97 0 : *hitfile = '\0';
98 : char *concat;
99 0 : concat=hitfile;
100 : // skip PATHSEP (and empty entries)
101 0 : while(*cp && *cp==PATHSEP){
102 0 : cp++;
103 : }
104 : // copy path
105 0 : while(*cp && *cp!=PATHSEP){
106 0 : *concat=*cp;
107 0 : cp++;
108 0 : concat++;
109 : }
110 : // end of variable value reached?
111 0 : if(concat==hitfile){
112 : // file not found
113 0 : *hitfile = '\0';
114 0 : return;
115 : }
116 : // does no trailing '/' exists?
117 0 : if(*(concat-1) != '/' && *(concat-1) != '\\'){
118 : // append it
119 0 : *concat='/';
120 0 : concat++;
121 : }
122 : // append file name
123 0 : strcpy(concat, name);
124 : // does file exist?
125 0 : if(iom_fileexists(hitfile))
126 : {
127 : // file found
128 0 : return;
129 : }
130 : }
131 : // file not found
132 0 : *hitfile = '\0';
133 : }
134 :
135 : #endif
136 :
137 :
138 :
139 : static char *tmpdir=0;
140 : static XMLTranscoder *utf8_transcoder=0;
141 :
142 : /** Perform iom library initialization.
143 : */
144 0 : extern "C" void iom_init()
145 : {
146 : //__asm { int 3 };
147 :
148 : try {
149 0 : XMLPlatformUtils::Initialize();
150 : }
151 0 : catch (const XMLException& toCatch) {
152 0 : char* message = XMLString::transcode(toCatch.getMessage());
153 0 : iom_issueerr(message);
154 0 : XMLString::release(&message);
155 0 : return;
156 : }
157 : XMLTransService::Codes resCode;
158 : utf8_transcoder = XMLPlatformUtils::fgTransService->makeNewTranscoderFor
159 : (
160 : "UTF-8"
161 : , resCode
162 : , 16 * 1024
163 0 : );
164 0 : tags::clear();
165 :
166 : }
167 :
168 : /* Compatibility stuff due to change of Xerces-C API signature (#2616) */
169 : #if XERCES_VERSION_MAJOR >= 3
170 : #define LEN_SIZE_TYPE XMLSize_t
171 : #else
172 : #define LEN_SIZE_TYPE unsigned int
173 : #endif
174 :
175 : /** transcode a xerces unicode string to an utf8 encoded one.
176 : */
177 0 : char *iom_toUTF8(const XMLCh *src)
178 : {
179 0 : LEN_SIZE_TYPE srcLen=XMLString::stringLen(src);
180 0 : LEN_SIZE_TYPE destLen=srcLen+10;
181 : XMLByte *dest;
182 0 : dest=dbgnew XMLByte[destLen+1];
183 : LEN_SIZE_TYPE eaten;
184 : LEN_SIZE_TYPE endDest;
185 0 : endDest=utf8_transcoder->transcodeTo(src,srcLen,dest,destLen,eaten,XMLTranscoder::UnRep_RepChar);
186 0 : while(eaten<srcLen){
187 0 : delete[] dest;
188 0 : destLen=destLen+srcLen-eaten+10;
189 0 : dest=dbgnew XMLByte[destLen+1];
190 0 : endDest=utf8_transcoder->transcodeTo(src,srcLen,dest,destLen,eaten,XMLTranscoder::UnRep_RepChar);
191 : }
192 0 : dest[endDest]=0;
193 0 : return (char*)dest; /* should be a unsigned char* == XMLByte* instead */
194 : }
195 :
196 : /** transcode an utf8 encoded string to a xerces unicode one.
197 : */
198 0 : XMLCh *iom_fromUTF8(const char *src)
199 : {
200 0 : LEN_SIZE_TYPE srcLen=XMLString::stringLen(src);
201 0 : LEN_SIZE_TYPE destLen=srcLen;
202 0 : XMLCh *dest=dbgnew XMLCh[destLen+1];
203 0 : unsigned char *charSizes=dbgnew unsigned char[destLen];
204 : LEN_SIZE_TYPE eaten;
205 0 : LEN_SIZE_TYPE endDest=utf8_transcoder->transcodeFrom((const XMLByte *)src,srcLen,dest,destLen,eaten,charSizes);
206 0 : dest[endDest]=0;
207 0 : delete[] charSizes;
208 0 : return dest;
209 : }
210 :
211 : /** Perform iom library termination.
212 : */
213 0 : extern "C" void iom_end()
214 : {
215 :
216 0 : ParserHandler::at_iom_end();
217 0 : ErrorUtility::at_iom_end();
218 0 : tags::clear();
219 0 : XMLPlatformUtils::Terminate();
220 0 : }
221 :
222 : /** sets the directory where iom writes temporary files.
223 : */
224 0 : extern "C" void iom_settmpdir(const char *dirname)
225 : {
226 0 : if(tmpdir)free(tmpdir);
227 0 : tmpdir=strdup(dirname);
228 0 : }
229 :
230 : /** creates a temporary filename.
231 : * The caller should free the returned buffer.
232 : */
233 0 : extern "C" char *iom_gettmpnam()
234 : {
235 : #ifdef _MSC_VER
236 : return _tempnam(tmpdir,"iom");
237 : #else
238 0 : return tempnam(tmpdir,"iom");
239 : #endif
240 : }
241 :
242 : /** Searches for a file in
243 : * a directory specified by an environment variable.
244 : * Returns 0 if file not found.
245 : * Returns a pointer to a static buffer.
246 : */
247 0 : extern "C" char *iom_searchenv(const char *filename, const char *varname)
248 : {
249 : static char pathbuffer[IOM_PATH_MAX];
250 0 : _searchenv( filename, varname, pathbuffer );
251 0 : if( *pathbuffer != '\0' ){
252 0 : return pathbuffer;
253 : }
254 : // file not found
255 0 : return 0;
256 : }
257 :
258 : /** Tests if a file exists.
259 : * Returns !0 if file exists.
260 : */
261 0 : extern "C" int iom_fileexists(const char *filename)
262 : {
263 : struct stat info;
264 : // does file exist?
265 0 : if(!stat(filename, &info))
266 : {
267 : // file found
268 0 : return true;
269 : }
270 0 : return false;
271 : }
272 :
273 : /** Returns the current time in milliseconds.
274 : */
275 0 : extern "C" unsigned long iom_currentmilis()
276 : {
277 0 : return XMLPlatformUtils::getCurrentMillis();
278 896 : }
279 448 :
280 : /**
281 : * @}
282 : */
|