]> git.stg.codes - stg.git/blob - stglibs/common.lib/common.cpp
Include unistd.h for close and usleep
[stg.git] / stglibs / common.lib / common.cpp
1 /*
2  *    This program is free software; you can redistribute it and/or modify
3  *    it under the terms of the GNU General Public License as published by
4  *    the Free Software Foundation; either version 2 of the License, or
5  *    (at your option) any later version.
6  *
7  *    This program is distributed in the hope that it will be useful,
8  *    but WITHOUT ANY WARRANTY; without even the implied warranty of
9  *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  *    GNU General Public License for more details.
11  *
12  *    You should have received a copy of the GNU General Public License
13  *    along with this program; if not, write to the Free Software
14  *    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
15  */
16
17 /*
18  *    Date: 27.10.2002
19  */
20
21 /*
22  *    Author : Boris Mikhailenko <stg34@stargazer.dp.ua>
23  */
24
25  /*
26  $Revision: 1.42 $
27  $Date: 2010/11/08 10:11:19 $
28  $Author: faust $
29  */
30
31
32 /*#include <sys/stat.h>
33 #include <fcntl.h>
34 #include <stdlib.h>
35 #include <errno.h>
36 #include <string.h>
37 #include <stdio.h>
38 #include <iconv.h>
39
40
41 #include <stdarg.h>
42
43
44 #include <sys/types.h>
45 #include <math.h>
46
47 #ifdef WIN32
48 #include <sysutils.hpp>
49 #else
50 #include <unistd.h>
51 #include <sys/wait.h>
52 #include <netinet/in.h>
53 #include <arpa/inet.h>
54 #include <sys/socket.h>
55 #endif*/
56
57 #ifdef FREE_BSD
58 #include <sys/types.h>
59 #endif
60
61 #ifdef WIN32
62 #include <winsock2.h>
63 #else
64 #include <sys/socket.h>
65 #include <netinet/in.h>
66 #include <arpa/inet.h>
67 #endif
68
69 #include <iconv.h>
70
71 #include <cstdlib>
72 #include <cstdarg>
73 #include <cstdio>
74 #include <cstring>
75 #include <cerrno>
76 #include <cassert>
77
78 #include "common.h"
79
80 #ifndef INET_ADDRSTRLEN
81 #   define INET_ADDRSTRLEN 16
82 #endif
83
84 using namespace std;
85
86 #ifdef WIN32
87 //-----------------------------------------------------------------------------
88 const char * inet_ntop(int af, const void * src, char * dst, unsigned long length)
89 {
90 struct sockaddr_in addr;
91 addr.sin_family = af;
92 addr.sin_port = 0;
93 memcpy(&addr.sin_addr.s_addr, src, sizeof(addr.sin_addr.s_addr));
94 if (WSAAddressToStringA(reinterpret_cast<struct sockaddr *>(&addr), sizeof(addr), 0, dst, &length))
95     {
96     return NULL;
97     }
98 return dst;
99 }
100 //-----------------------------------------------------------------------------
101 int inet_pton(int af, const char * src, void * dst)
102 {
103 // Fuck you Microsoft!
104 // Why the hell not to use const char *?
105 size_t slen = strlen(src);
106 char * buf = new char[slen + 1];
107 strncpy(buf, src, slen + 1);
108 buf[slen] = 0;
109 struct sockaddr_in addr;
110 addr.sin_family = af;
111 addr.sin_port = 0;
112 addr.sin_addr.s_addr = 0;
113 int length = sizeof(addr);
114 if (WSAStringToAddressA(buf, af, 0, reinterpret_cast<struct sockaddr *>(&addr), &length))
115     {
116     delete[] buf;
117     return -1;
118     }
119 memcpy(dst, &addr, sizeof(addr));
120 delete[] buf;
121 return 1;
122 }
123 #endif
124 //-----------------------------------------------------------------------------
125 int strtodouble2(const char * s, double &a)
126 {
127 char *res;
128
129 a = strtod(s, &res);
130
131 if (*res != 0)
132     return EINVAL;
133
134 return 0;
135 }
136 //-----------------------------------------------------------------------------
137 #ifdef DEBUG
138 int printfd(const char * __file__, const char * fmt, ...)
139 #else
140 int printfd(const char *, const char *, ...)
141 #endif
142 {
143 #ifdef DEBUG
144 char buff[1024];
145
146 time_t t = time(NULL);
147
148 va_list vl;
149 va_start(vl, fmt);
150 vsnprintf(buff, sizeof(buff), fmt, vl);
151 va_end(vl);
152
153 printf("%18s > %s > ", __file__, LogDate(t)+11);
154 printf("%s", buff);
155
156 #endif
157 return 0;
158 }
159 //-----------------------------------------------------------------------------
160 int strprintf(string * str, const char * fmt, ...)
161 {
162 char buff[1024];
163
164 va_list vl;
165 va_start(vl, fmt);
166 int n = vsnprintf(buff, sizeof(buff), fmt, vl);
167 va_end(vl);
168 buff[1023] = 0;
169 *str = buff;
170
171 return n;
172 }
173 //-----------------------------------------------------------------------------
174 const char *IntToKMG(long long a, int stat)
175 {
176 static int64_t M = 1024*1024;
177 static int64_t G = 1024*1024*1024;
178 static char str[30];
179
180 switch (stat)
181     {
182     case ST_B:
183         #ifdef __WIN32__
184         sprintf(str, "%Ld", a);
185         #else
186         sprintf(str, "%lld", a);
187         #endif
188         break;
189     case ST_KB:
190         sprintf(str, "%.2f kb", double(a)/1024.0);
191         break;
192     case ST_MB:
193         sprintf(str, "%.2f Mb", double(a)/(1024.0*1024.0));
194         break;
195     default:
196         if (a > G)
197             {
198             sprintf(str, "%.2f Gb", double(a)/double(G));
199             return &str[0];
200             }
201         if (a < -G)
202             {
203             sprintf(str, "%.2f Gb", double(a)/double(G));
204             return &str[0];
205             }
206         if (a > M)
207             {
208             sprintf(str, "%.2f Mb", double(a)/double(M));
209             return &str[0];
210             }
211         if (a < -M)
212             {
213             sprintf(str, "%.2f Mb", double(a)/double(M));
214             return &str[0];
215             }
216
217         sprintf(str, "%.2f kb", double(a)/1024.0);
218         break;
219     }
220 return str;
221 }
222 //---------------------------------------------------------------------------
223 unsigned char koi2win[] = {
224         0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
225         0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
226         0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
227         0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F,
228         0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
229         0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F,
230         0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
231         0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F,
232         0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
233         0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F,
234         0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
235         0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F,
236         0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
237         0x68, 0x69, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F,
238         0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
239         0x78, 0x79, 0x7A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F,
240         0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
241         0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F,
242         0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
243         0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F,
244         0xA0, 0xA1, 0xA2, 0xB8, 0xBA, 0xA5, 0xB3, 0xBF,
245         0xA8, 0xA9, 0xAA, 0xAB, 0xAC, 0xB4, 0xAE, 0xAF,
246         0xB0, 0xB1, 0xB2, 0xA8, 0xAA, 0xB5, 0xB2, 0xAF,
247         0xB8, 0xB9, 0xBA, 0xBB, 0xBC, 0xA5, 0xBE, 0xBF,
248         0xFE, 0xE0, 0xE1, 0xF6, 0xE4, 0xE5, 0xF4, 0xE3,
249         0xF5, 0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE,
250         0xEF, 0xFF, 0xF0, 0xF1, 0xF2, 0xF3, 0xE6, 0xE2,
251         0xFC, 0xFB, 0xE7, 0xF8, 0xFD, 0xF9, 0xF7, 0xFA,
252         0xDE, 0xC0, 0xC1, 0xD6, 0xC4, 0xC5, 0xD4, 0xC3,
253         0xD5, 0xC8, 0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE,
254         0xCF, 0xDF, 0xD0, 0xD1, 0xD2, 0xD3, 0xC6, 0xC2,
255         0xDC, 0xDB, 0xC7, 0xD8, 0xDD, 0xD9, 0xD7, 0xDA};
256
257
258 unsigned char win2koi[] = {
259         0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
260         0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
261         0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
262         0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F,
263         0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
264         0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F,
265         0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
266         0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F,
267         0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
268         0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F,
269         0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
270         0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F,
271         0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
272         0x68, 0x69, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F,
273         0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
274         0x78, 0x79, 0x7A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F,
275         0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
276         0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F,
277         0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
278         0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F,
279         0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xBD, 0xA6, 0xA7,
280         0xB3, 0xA9, 0xB4, 0xAB, 0xAC, 0xAD, 0xAE, 0xB7,
281         0xB0, 0xB1, 0xB6, 0xA6, 0xAD, 0xB5, 0xB6, 0xB7,
282         0xA3, 0xB9, 0xA4, 0xBB, 0xBC, 0xBD, 0xBE, 0xA7,
283         0xE1, 0xE2, 0xF7, 0xE7, 0xE4, 0xE5, 0xF6, 0xFA,
284         0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF, 0xF0,
285         0xF2, 0xF3, 0xF4, 0xF5, 0xE6, 0xE8, 0xE3, 0xFE,
286         0xFB, 0xFD, 0xFF, 0xF9, 0xF8, 0xFC, 0xE0, 0xF1,
287         0xC1, 0xC2, 0xD7, 0xC7, 0xC4, 0xC5, 0xD6, 0xDA,
288         0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, 0xD0,
289         0xD2, 0xD3, 0xD4, 0xD5, 0xC6, 0xC8, 0xC3, 0xDE,
290         0xDB, 0xDD, 0xDF, 0xD9, 0xD8, 0xDC, 0xC0, 0xD1};
291 //---------------------------------------------------------------------------
292 void KOIToWin(const char * s1, char * s2, int l)
293 {
294 unsigned char t;
295 for (int j = 0; j < l; j++)
296     {
297     t = s1[j];
298     s2[j] = koi2win[t];
299
300     if (s1[j] == 0)
301         break;
302     }
303 }
304 //---------------------------------------------------------------------------
305 void WinToKOI(const char * s1, char * s2, int l)
306 {
307 unsigned char t;
308 for (int j = 0; j < l; j++)
309     {
310     t = s1[j];
311     s2[j] = win2koi[t];
312
313     if (s1[j] == 0)
314         break;
315     }
316 }
317 //---------------------------------------------------------------------------
318 void KOIToWin(const string & s1, string * s2)
319 {
320 s2->erase(s2->begin(), s2->end());
321 unsigned char t;
322 s2->reserve(s1.length());
323 for (int j = 0; j < (int)s1.length(); j++)
324     {
325     t = s1[j];
326     s2->push_back(koi2win[t]);
327     }
328 }
329 //---------------------------------------------------------------------------
330 void WinToKOI(const string & s1, string * s2)
331 {
332 s2->erase(s2->begin(), s2->end());
333 unsigned char t;
334 s2->reserve(s1.length());
335 for (int j = 0; j < (int)s1.length(); j++)
336     {
337     t = s1[j];
338     s2->push_back(win2koi[t]);
339     }
340 }
341 //---------------------------------------------------------------------------
342 void Encode12str(string & dst, const string & src)
343 {
344 dst.erase(dst.begin(), dst.end());
345 for (size_t i = 0; i < src.length(); i++)
346     {
347     dst.push_back('a' + (src[i] & 0x0f));
348     dst.push_back('a' + ((src[i] & 0xf0) >> 4));
349     }
350 }
351 //---------------------------------------------------------------------------
352 void Decode21str(std::string & dst, const std::string & src)
353 {
354 dst.erase(dst.begin(), dst.end());
355 for (size_t i = 0; i < src.length() / 2; i++)
356     {
357     char c1 = src[i * 2];
358     char c2 = src[i * 2 + 1];
359
360     c1 -= 'a';
361     c2 -= 'a';
362
363     dst.push_back(c1 + (c2 << 4));
364     }
365 }
366 //---------------------------------------------------------------------------
367 void Encode12(char * dst, const char * src, size_t srcLen)
368 {
369 for (size_t i = 0; i <= srcLen; i++)
370     {
371     if (src[i] == 0)
372         {
373         dst[i * 2] = 'a';
374         dst[i * 2 + 1] = 'a';
375         break;
376         }
377     char c1 = src[i] & 0x0f;
378     char c2 = (src[i] & 0xf0) >> 4;
379
380     c1 += 'a';
381     c2 += 'a';
382
383     dst[i * 2] = c1;
384     dst[i * 2 + 1] = c2;
385     }
386 dst[srcLen * 2] = 0;
387 }
388 //---------------------------------------------------------------------------
389 void Decode21(char * dst, const char * src)
390 {
391 for (size_t i = 0; ; i++)
392     {
393     if (src[i * 2] == 0)
394         break;
395
396     char c1 = src[i * 2];
397     char c2 = src[i * 2 + 1];
398
399     c1 -= 'a';
400     c2 -= 'a';
401
402     dst[i] = c1 + (c2 << 4);
403     }
404 dst[strlen(src) / 2] = 0;
405 }
406 //---------------------------------------------------------------------------
407 int ParseIPString(const char * str, uint32_t * ips, int maxIP)
408 {
409 /*
410  *Function Name:ParseIPString
411  *
412  *Parameters:
413  ÓÔÒÏËÁ ÄÌÑ ÒÁÚÂÏÒÁ É ÍÁÓÓÉ× ËÕÄÁ ÚÁÎÏÓÉÔØ ÐÏÌÕÞÅÎÎÙÅ ÁÄÒÅÓÁ
414  *
415  *Description:
416  îÁ ×ÈÏÄÅ ÄÏÌÖÎÁ ÂÙÔØ ÓÔÒÏËÁ ×ÉÄÁ "ip1,ip2,ip3" ÉÌÉ "*"
417  ÷ ÐÅÒ×ÏÍ ÓÌÕÞÁÅ × ÍÁÓÓÉ× ÚÁÎÏÓÑÔÓÑ ÒÁÚÏÂÒÁÎÎÙÅ ÁÄÒÅÓÁ.
418  åÓÌÉ ÉÈ ÍÅÎØÛÅ MAX_IP?, ÔÏ ÐÏÓÌÅÄÎÉÊ ÁÄÒÅÓ ÂÕÄÅÔ 255.255.255.255
419  åÓÌÉ ÓÔÒÏËÁ * , ÔÏ ÐÅÒ×ÁÙÊ ÁÄÒÅÓ ÂÕÄÅÔ 0.0.0.0, Ô.Å. ÌÀÂÏÊ
420  *
421  *Returns: 0 ÅÓÌÉ ×ÓÅ ïë
422  *
423  */
424
425 char p[255];
426 char * p1, *pp;
427 int n = 0;
428
429 strncpy(p, str, 254);
430 pp = p;
431
432 memset(ips, 0xFF, sizeof(unsigned long) * maxIP);
433
434 if (str[0] == '*' && strlen(str) == 1)
435     {
436     ips[0] = 0;
437     return 0;
438     }
439
440 for (int i = 0; i < maxIP; i++)
441     {
442     p1 = strtok(pp, ",\n ");
443     pp = NULL;
444
445     if (p1 == NULL && n == 0)// ÕËÁÚÁÔÅÌØ ÎÕÌØ É ÐÒÏÞÉÔÁÎÏ ÁÄÒÅÓÏ× ÔÏÖÅ ÎÏÌØ
446         {
447         return EINVAL;
448         }
449
450     if (p1 == NULL && n)
451         {
452         return 0;
453         }
454
455     struct in_addr in;
456     if (inet_pton(AF_INET, p1, &in) != 1)
457         {
458         //printf("INADDR_NONE\n");
459         return EINVAL;
460         }
461
462     ips[n] = in.s_addr;
463
464     /*if (ips[n] == INADDR_NONE)
465         return EINVAL;*/
466
467     n++;
468
469     if (n >= maxIP)
470         return 0;
471
472     }
473
474 return 0;
475 }
476 //-----------------------------------------------------------------------------
477 int DaysInCurrentMonth()
478 {
479 time_t t = time(NULL);
480
481 struct tm * lt = localtime(&t);
482
483 return DaysInMonth(lt->tm_year, lt->tm_mon);
484 }
485 //-----------------------------------------------------------------------------
486 int DaysInMonth(unsigned year, unsigned mon)
487 {
488 assert(mon < 12 && "Month number should be 0 - 11");
489 switch (mon)
490     {
491     case 0: return 31;  //jan
492     case 1:
493         if (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0))
494             return 29;
495         return 28;      //feb
496     case 2: return 31;  //mar
497     case 3: return 30;  //apr
498     case 4: return 31;  //may
499     case 5: return 30;  //june
500     case 6: return 31;  //jule
501     case 7: return 31;  //aug
502     case 8: return 30;  //sep
503     case 9: return 31;  //oct
504     case 10: return 30; //nov
505     case 11: return 31; //dec
506     }
507 return -1; // We will never reach here
508 }
509 //-----------------------------------------------------------------------------
510 int Min8(int a)
511 {
512 /*
513 æÕÎËÃÉÑ ×ÏÚ×ÒÁÝÁÅÔ ÎÁÉÍÅÎØÛÅÅ ÞÉÓÌÏ ËÒÁÔÎÏÅ 8-ÍÉ ÂÏÌØÛÅÅ ÉÌÉ ÒÁ×ÎÏÅ ÚÁÄÁÎÎÏÍÕ
514  * */
515 if (a % 8 == 0)
516     return a;
517
518 return a + (8 - a % 8);
519 }
520 //-----------------------------------------------------------------------------
521 /*char * inet_ntostr(unsigned long ip)
522 {
523 struct in_addr addr = {ip};
524 return inet_ntoa(addr);
525 }*/
526 //-----------------------------------------------------------------------------
527 std::string inet_ntostring(uint32_t ip)
528 {
529     char buf[INET_ADDRSTRLEN + 1];
530     return inet_ntop(AF_INET, &ip, buf, INET_ADDRSTRLEN);
531 }
532 //-----------------------------------------------------------------------------
533 uint32_t inet_strington(const std::string & value)
534 {
535     uint32_t result;
536
537     if (inet_pton(AF_INET, value.c_str(), &result) <= 0)
538         return 0;
539
540     return result;
541 }
542 //-----------------------------------------------------------------------------
543 int ParseTariffTimeStr(const char * str, int &h1, int &m1, int &h2, int &m2)
544 {
545 char hs1[10], ms1[10], hs2[10], ms2[10];
546 char s1[25], s2[25];
547 char ss[49];
548 char *p1, *p2;
549
550 strncpy(ss, str, 48);
551
552 p1 = strtok(ss, "-");
553 if (!p1)
554     return -1;
555
556 strncpy(s1, p1, 24);
557
558 p2 = strtok(NULL, "-");
559 if (!p2)
560     return -1;
561
562 strncpy(s2, p2, 24);
563
564 p1 = strtok(s1, ":");
565 if (!p1)
566     return -1;
567
568 strncpy(hs1, p1, 9);
569
570 p2 = strtok(NULL, ":");
571 if (!p2)
572     return -1;
573
574 strncpy(ms1, p2, 9);
575
576 p1 = strtok(s2, ":");
577 if (!p1)
578     return -1;
579
580 strncpy(hs2, p1, 9);
581
582 p2 = strtok(NULL, ":");
583 if (!p2)
584     return -1;
585
586 strncpy(ms2, p2, 9);
587
588 if (str2x(hs1, h1) != 0)
589     return -1;
590
591 if (str2x(ms1, m1) != 0)
592     return -1;
593
594 if (str2x(hs2, h2) != 0)
595     return -1;
596
597 if (str2x(ms2, m2) != 0)
598     return -1;
599
600 return 0;
601 }
602 /*//---------------------------------------------------------------------------
603 bool IsDigit(char c)
604 {
605 if (c >= '0' && c <= '9')
606     return true;
607 return false;
608 }
609 //-----------------------------------------------------------------------------
610 bool IsAlpha(char c)
611 {
612 if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z'))
613     return true;
614 return false;
615 }*/
616 //-----------------------------------------------------------------------------
617 const char * LogDate(time_t t)
618 {
619 static char s[32];
620 struct tm * tt = localtime(&t);
621
622 snprintf(s, 20, "%d-%s%d-%s%d %s%d:%s%d:%s%d",
623          tt->tm_year + 1900,
624          tt->tm_mon + 1 < 10 ? "0" : "", tt->tm_mon + 1,
625          tt->tm_mday    < 10 ? "0" : "", tt->tm_mday,
626          tt->tm_hour    < 10 ? "0" : "", tt->tm_hour,
627          tt->tm_min     < 10 ? "0" : "", tt->tm_min,
628          tt->tm_sec     < 10 ? "0" : "", tt->tm_sec);
629
630 return s;
631 }
632 //-----------------------------------------------------------------------------
633 uint32_t CalcMask(uint32_t msk)
634 {
635 if (msk >= 32) return 0xFFffFFff;
636 if (msk == 0) return 0;
637 return htonl(0xFFffFFff << (32 - msk));
638 }
639 //---------------------------------------------------------------------------
640 void TouchFile(const string & fileName)
641 {
642 FILE * f = fopen(fileName.c_str(), "w");
643 if (f)
644     fclose(f);
645 }
646 //---------------------------------------------------------------------------
647 #ifdef WIN32
648 void EncodeStr(char * str, unsigned long serial, int useHDD)
649 {
650 int len = strlen(str);
651 char stren[100];
652 int i, j = 0;
653 char c1, c2;
654 char serial_c[sizeof(serial)];
655 memcpy(serial_c, &serial, sizeof(serial));
656
657 for (i = 0; i < len; i++)
658     {
659     if (!useHDD)
660         str[i] = str[i]^49;
661     else
662         {
663         str[i] = str[i]^serial_c[j%sizeof(serial)];
664         j++;
665         }
666     }
667
668 for (i = 0; i < 2*len; i++)
669     {
670     if (i%2)
671         {
672         c1 = (str[i/2] >> 4);
673         c1 = c1 + 50;
674         stren[i] = c1;
675         }
676     else
677         {
678         c2 = (str[i/2] & 0x0f);
679         c2 += 50;
680         stren[i] = c2;
681         }
682     }
683 stren[i] = 0;
684 strcpy(str, stren);
685 }
686 //---------------------------------------------------------------------------
687 void DecodeStr(char * str, unsigned long serial, int useHDD)
688 {
689 int len = strlen(str);
690 char strdc[100];
691 int i, j = 0;
692 char c1, c2;
693 char serial_c[sizeof(serial)];
694 memcpy(serial_c, &serial, sizeof(serial));
695
696 for (i = 0; i < len; i += 2)
697     {
698     c1 = (str[i] - 50);
699     c2 = (str[i+1] - 50)<<4;
700     strdc[i/2] = c1+c2;
701     }
702 for (i = 0; i < len/2; i++)
703     {
704     if (!useHDD)
705         strdc[i] = strdc[i]^49;
706     else
707         {
708         strdc[i] = strdc[i]^serial_c[j%sizeof(serial)];
709         j++;
710         }
711     }
712 strdc[i] = 0;
713 strcpy(str, strdc);
714 }
715 //---------------------------------------------------------------------------
716 #endif //WIN32
717 void SwapBytes(uint16_t & value)
718 {
719     value = (value >> 8) |
720             (value << 8);
721 }
722 //---------------------------------------------------------------------------
723 void SwapBytes(uint32_t & value)
724 {
725     value = (value >> 24) |
726             ((value << 8) &  0x00FF0000L)|
727             ((value >> 8) &  0x0000FF00L)|
728             (value << 24);
729 }
730 //---------------------------------------------------------------------------
731 void SwapBytes(uint64_t & value)
732 {
733     value = (value >> 56) |
734             ((value << 40) & 0x00FF000000000000LL) |
735             ((value << 24) & 0x0000FF0000000000LL) |
736             ((value << 8)  & 0x000000FF00000000LL) |
737             ((value >> 8)  & 0x00000000FF000000LL) |
738             ((value >> 24) & 0x0000000000FF0000LL) |
739             ((value >> 40) & 0x000000000000FF00LL) |
740             (value << 56);
741 }
742 //---------------------------------------------------------------------------
743 void SwapBytes(int16_t & value)
744 {
745     uint16_t temp = value;
746     SwapBytes(temp);
747     value = temp;
748 }
749 //---------------------------------------------------------------------------
750 void SwapBytes(int32_t & value)
751 {
752     uint32_t temp = value;
753     SwapBytes(temp);
754     value = temp;
755 }
756 //---------------------------------------------------------------------------
757 void SwapBytes(int64_t & value)
758 {
759     uint64_t temp = value;
760     SwapBytes(temp);
761     value = temp;
762 }
763 //---------------------------------------------------------------------------
764 int str2x(const std::string & str, int & x)
765 {
766 x = strtol(str.c_str(), NULL, 10);
767
768 if (errno == ERANGE)
769     return -1;
770
771 return 0;
772 }
773 //---------------------------------------------------------------------------
774 int str2x(const std::string & str, unsigned & x)
775 {
776 x = strtoul(str.c_str(), NULL, 10);
777
778 if (errno == ERANGE)
779     return -1;
780
781 return 0;
782 }
783 //---------------------------------------------------------------------------
784 int str2x(const std::string & str, long & x)
785 {
786 x = strtol(str.c_str(), NULL, 10);
787
788 if (errno == ERANGE)
789     return -1;
790
791 return 0;
792 }
793 //---------------------------------------------------------------------------
794 int str2x(const std::string & str, unsigned long & x)
795 {
796 x = strtoul(str.c_str(), NULL, 10);
797
798 if (errno == ERANGE)
799     return -1;
800
801 return 0;
802 }
803 #ifndef WIN32
804 //---------------------------------------------------------------------------
805 int str2x(const std::string & str, long long & x)
806 {
807 x = strtoll(str.c_str(), NULL, 10);
808
809 if (errno == ERANGE)
810     return -1;
811
812 return 0;
813 }
814 //---------------------------------------------------------------------------
815 int str2x(const std::string & str, unsigned long long & x)
816 {
817 x = strtoull(str.c_str(), NULL, 10);
818
819 if (errno == ERANGE)
820     return -1;
821
822 return 0;
823 }
824 #endif
825 //---------------------------------------------------------------------------
826 const std::string & x2str(unsigned x, std::string & s)
827 {
828 return unsigned2str(x, s);
829 }
830 //---------------------------------------------------------------------------
831 const std::string & x2str(unsigned long x, std::string & s)
832 {
833 return unsigned2str(x, s);
834 }
835 //---------------------------------------------------------------------------
836 const std::string & x2str(unsigned long long x, std::string & s)
837 {
838 return unsigned2str(x, s);
839 }
840 //---------------------------------------------------------------------------
841 std::string & TrimL(std::string & val)
842 {
843 size_t pos = val.find_first_not_of(" \t");
844 if (pos == std::string::npos)
845     {
846     val.erase(val.begin(), val.end());
847     }
848 else
849     {
850     val.erase(0, pos);
851     }
852 return val;
853 }
854 //---------------------------------------------------------------------------
855 std::string & TrimR(std::string & val)
856 {
857 size_t pos = val.find_last_not_of(" \t");
858 if (pos != std::string::npos)
859     {
860     val.erase(pos + 1);
861     }
862 return val;
863 }
864 //---------------------------------------------------------------------------
865 std::string & Trim(std::string & val)
866 {
867 return TrimR(TrimL(val));
868 }
869 //---------------------------------------------------------------------------
870 #ifdef WIN32
871 static int is_leap(unsigned y)
872 {
873     y += 1900;
874     return (y % 4) == 0 && ((y % 100) != 0 || (y % 400) == 0);
875 }
876 #endif
877 //---------------------------------------------------------------------------
878
879 time_t stg_timegm(struct tm * brokenTime)
880 {
881 #ifdef WIN32
882 static const unsigned ndays[2][12] ={
883     {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
884     {31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}};
885 time_t res = 0;
886 for (int i = 70; i < brokenTime->tm_year; ++i)
887     res += is_leap(i) ? 366 : 365;
888 for (int i = 0; i < brokenTime->tm_mon; ++i)
889     res += ndays[is_leap(brokenTime->tm_year)][i];
890 res += brokenTime->tm_mday - 1;
891 res *= 24;
892 res += brokenTime->tm_hour;
893 res *= 60;
894 res += brokenTime->tm_min;
895 res *= 60;
896 res += brokenTime->tm_sec;
897 return res;
898 #else
899 #ifdef HAVE_TIMEGM
900 return timegm(brokenTime);
901 #else
902 time_t ret;
903 char *tz;
904 tz = getenv("TZ");
905 setenv("TZ", "", 1);
906 tzset();
907 ret = mktime(brokenTime);
908 if (tz)
909     setenv("TZ", tz, 1);
910 else
911     unsetenv("TZ");
912 tzset();
913 return ret;
914 #endif // HAVE_TIMEGM
915 #endif // WIN32
916 }
917 //---------------------------------------------------------------------------
918 std::string IconvString(const std::string & source,
919                         const std::string & from,
920                         const std::string & to)
921 {
922 if (source.empty())
923     return std::string();
924
925 size_t inBytesLeft = source.length() + 1;
926 size_t outBytesLeft = source.length() * 2 + 1;
927
928 char * inBuf = new char[inBytesLeft];
929 char * outBuf = new char[outBytesLeft];
930
931 strncpy(inBuf, source.c_str(), source.length());
932
933 inBuf[source.length()] = 0;
934
935 #if defined(FREE_BSD) || defined(FREE_BSD5) || defined(WIN32)
936 const char * srcPos = inBuf;
937 #else
938 char * srcPos = inBuf;
939 #endif
940 char * dstPos = outBuf;
941
942 iconv_t handle = iconv_open(to.c_str(),
943                             from.c_str());
944
945 if (handle == iconv_t(-1))
946     {
947     if (errno == EINVAL)
948         {
949         printfd(__FILE__, "IconvString(): iconv from %s to %s failed\n", from.c_str(), to.c_str());
950         delete[] outBuf;
951         delete[] inBuf;
952         return source;
953         }
954     else
955         printfd(__FILE__, "IconvString(): iconv_open error\n");
956
957     delete[] outBuf;
958     delete[] inBuf;
959     return source;
960     }
961
962 size_t res = iconv(handle,
963                    &srcPos, &inBytesLeft,
964                    &dstPos, &outBytesLeft);
965
966 if (res == size_t(-1))
967     {
968     printfd(__FILE__, "IconvString(): '%s'\n", strerror(errno));
969
970     iconv_close(handle);
971     delete[] outBuf;
972     delete[] inBuf;
973     return source;
974     }
975
976 dstPos = 0;
977
978 std::string dst(outBuf);
979
980 iconv_close(handle);
981
982 delete[] outBuf;
983 delete[] inBuf;
984
985 return dst;
986 }
987 //---------------------------------------------------------------------------