33#define MAXSYSLOGBUF 256
41 vsyslog(priority, fmt, ap);
53ssize_t
safe_read(
int filedes,
void *buffer,
size_t size)
56 ssize_t p = read(filedes, buffer, size);
57 if (p < 0 && errno == EINTR) {
58 dsyslog(
"EINTR while reading from file handle %d - retrying", filedes);
65ssize_t
safe_write(
int filedes,
const void *buffer,
size_t size)
68 ssize_t written = size;
69 const unsigned char *ptr = (
const unsigned char *)buffer;
71 p = write(filedes, ptr, size);
74 dsyslog(
"EINTR while writing to file handle %d - retrying", filedes);
82 return p < 0 ? p : written;
94 int w = write(fd, Data + written, Length);
103 Poller.
Poll(RetryMs);
104 if (TimeoutMs > 0 && (TimeoutMs -= t.
Elapsed()) <= 0)
117 int l =
max(dest ? strlen(dest) : 0, strlen(src)) + 1;
118 dest = (
char *)realloc(dest, l);
122 esyslog(
"ERROR: out of memory");
131char *
strn0cpy(
char *dest,
const char *src,
size_t n)
134 for ( ; --n && (*dest = *src) != 0; dest++, src++) ;
154 if (!s || !s1 || !s2)
156 char *p = strstr(s, s1);
163 if (
char *NewBuffer = (
char *)realloc(s, l + l2 - l1 + 1))
166 esyslog(
"ERROR: out of memory");
172 memmove(sof + l2, sof + l1, l - of - l1 + 1);
178const char *
strchrn(
const char *s,
char c,
size_t n)
184 if (*s == c && --n == 0)
205 const char *p = strrchr(s, 0);
207 if (*p == c && --n == 0)
215 const char *p = strrchr(s, c);
216 return p ? p + 1 : s;
222 for (
char *p = s + strlen(s) - 1; p >= s; p--) {
239 memmove(p + 1, q, strlen(q) + 1);
243 memmove(s, t, strlen(t) + 1);
259 else if (t != s && n == 0) {
278 if (strchr(chars, *p)) {
280 buffer =
MALLOC(
char, 2 * strlen(s) + 1);
281 t = buffer + (p - s);
282 s = strcpy(buffer, s);
298 int l = strlen(name);
300 while (
const char *p = strstr(t, name)) {
302 if (p == s || *(p - 1) <=
' ') {
322 memmove(s, s + n, l - n + 1);
340 const char *se = s + strlen(s) - 1;
341 const char *pe = p + strlen(p) - 1;
343 if (*pe-- != *se-- || (se < s && pe >= p))
378 int64_t n = strtoll(s, &t, 10);
394 if (strcmp(*a, s) == 0)
404 if (*FileName ==
'/')
406 return cString::sprintf(
"%s/%s", DirName && *DirName ? DirName :
".", FileName);
409#define DECIMAL_POINT_C '.'
413 static lconv *loc = localeconv();
415 char buf[strlen(s) + 1];
419 *p = *loc->decimal_point;
434 static lconv *loc = localeconv();
436 snprintf(buf,
sizeof(buf), Format, d);
445 snprintf(buf,
sizeof(buf),
"%d", n);
452 if (stat(File1, &st) == 0) {
453 dev_t dev1 = st.st_dev;
454 if (stat(File2, &st) == 0)
455 return st.st_dev == dev1;
469 struct statfs statFs;
470 if (statfs(Directory, &statFs) == 0) {
471 double blocksPerMeg = 1024.0 * 1024.0 / statFs.f_bsize;
473 *UsedMB = int((statFs.f_blocks - statFs.f_bfree) / blocksPerMeg);
474 Free = int(statFs.f_bavail / blocksPerMeg);
484 if (stat(DirName, &ds) == 0) {
485 if (S_ISDIR(ds.st_mode)) {
486 if (access(DirName, R_OK | W_OK | X_OK) == 0)
489 esyslog(
"ERROR: can't access %s", DirName);
492 esyslog(
"ERROR: %s is not a directory", DirName);
499bool MakeDirs(
const char *FileName,
bool IsDirectory)
502 char *s = strdup(FileName);
506 while ((p = strchr(p,
'/')) != NULL || IsDirectory) {
510 if (stat(s, &fs) != 0 || !S_ISDIR(fs.st_mode)) {
511 dsyslog(
"creating directory %s", s);
512 if (mkdir(s, ACCESSPERMS) == -1) {
530 if (stat(FileName, &st) == 0) {
531 if (S_ISDIR(st.st_mode)) {
535 while ((e = d.
Next()) != NULL) {
537 if (FollowSymlinks) {
539 if (lstat(buffer, &st2) == 0) {
540 if (S_ISLNK(st2.st_mode)) {
541 int size = st2.st_size + 1;
542 char *l =
MALLOC(
char, size);
543 int n = readlink(buffer, l, size - 1);
557 else if (errno != ENOENT) {
562 dsyslog(
"removing %s", *buffer);
563 if (remove(buffer) < 0)
572 dsyslog(
"removing %s", FileName);
573 if (remove(FileName) < 0) {
578 else if (errno != ENOENT) {
587 bool HasIgnoredFiles =
false;
592 while ((e = d.
Next()) != NULL) {
593 if (strcmp(e->d_name,
"lost+found")) {
596 if (stat(buffer, &st) == 0) {
597 if (S_ISDIR(st.st_mode)) {
601 else if (RemoveThis && IgnoreFiles &&
StrInArray(IgnoreFiles, e->d_name))
602 HasIgnoredFiles =
true;
612 if (RemoveThis && empty) {
613 if (HasIgnoredFiles) {
614 while (*IgnoreFiles) {
616 if (access(buffer, F_OK) == 0) {
617 dsyslog(
"removing %s", *buffer);
618 if (remove(buffer) < 0) {
626 dsyslog(
"removing %s", DirName);
627 if (remove(DirName) < 0) {
645 while (size >= 0 && (e = d.
Next()) != NULL) {
648 if (stat(buffer, &st) == 0) {
649 if (S_ISDIR(st.st_mode)) {
666 else if (errno != ENOENT)
675 char *TargetName = canonicalize_file_name(FileName);
678 TargetName = strdup(FileName);
687 for (
int n = 0; n < 10; n++) {
693 if (access(buf, F_OK) != 0) {
695 gettimeofday(&tp1, NULL);
696 int f = open(buf, O_WRONLY | O_CREAT, DEFFILEMODE);
699 if (fdatasync(f) < 0)
703 gettimeofday(&tp2, NULL);
704 double seconds = (((
long long)tp2.tv_sec * 1000000 + tp2.tv_usec) - ((
long long)tp1.tv_sec * 1000000 + tp1.tv_usec)) / 1000000.0;
706 dsyslog(
"SpinUpDisk took %.2f seconds", seconds);
713 esyslog(
"ERROR: SpinUpDisk failed");
719 if (utime(FileName, NULL) == -1 && errno != ENOENT)
726 if (stat(FileName, &fs) == 0)
734 if (stat(FileName, &fs) == 0)
751#if _POSIX_TIMERS > 0 && defined(_POSIX_MONOTONIC_CLOCK)
752#define MIN_RESOLUTION 5
753 static bool initialized =
false;
754 static bool monotonic =
false;
758 if (clock_getres(CLOCK_MONOTONIC, &tp) == 0) {
759 long Resolution = tp.tv_nsec;
761 if (tp.tv_sec == 0 && tp.tv_nsec <= MIN_RESOLUTION * 1000000) {
762 if (clock_gettime(CLOCK_MONOTONIC, &tp) == 0) {
763 dsyslog(
"cTimeMs: using monotonic clock (resolution is %ld ns)", Resolution);
767 esyslog(
"cTimeMs: clock_gettime(CLOCK_MONOTONIC) failed");
770 dsyslog(
"cTimeMs: not using monotonic clock - resolution is too bad (%jd s %ld ns)", intmax_t(tp.tv_sec), tp.tv_nsec);
773 esyslog(
"cTimeMs: clock_getres(CLOCK_MONOTONIC) failed");
777 if (clock_gettime(CLOCK_MONOTONIC, &tp) == 0)
778 return (uint64_t(tp.tv_sec)) * 1000 + tp.tv_nsec / 1000000;
779 esyslog(
"cTimeMs: clock_gettime(CLOCK_MONOTONIC) failed");
784# warning Posix monotonic clock not available
787 if (gettimeofday(&t, NULL) == 0)
788 return (uint64_t(t.tv_sec)) * 1000 + t.tv_usec / 1000;
815#define MT(s, m, v) ((*(s) & (m)) == (v))
816 if (
MT(s, 0xE0, 0xC0) &&
MT(s + 1, 0xC0, 0x80))
818 if (
MT(s, 0xF0, 0xE0) &&
MT(s + 1, 0xC0, 0x80) &&
MT(s + 2, 0xC0, 0x80))
820 if (
MT(s, 0xF8, 0xF0) &&
MT(s + 1, 0xC0, 0x80) &&
MT(s + 2, 0xC0, 0x80) &&
MT(s + 3, 0xC0, 0x80))
832 case 2:
return ((*s & 0x1F) << 6) | (*(s + 1) & 0x3F);
833 case 3:
return ((*s & 0x0F) << 12) | ((*(s + 1) & 0x3F) << 6) | (*(s + 2) & 0x3F);
834 case 4:
return ((*s & 0x07) << 18) | ((*(s + 1) & 0x3F) << 12) | ((*(s + 2) & 0x3F) << 6) | (*(s + 3) & 0x3F);
849 *s++ = ((c >> 6) & 0x1F) | 0xC0;
850 *s = (c & 0x3F) | 0x80;
856 *s++ = ((c >> 12) & 0x0F) | 0xE0;
857 *s++ = ((c >> 6) & 0x3F) | 0x80;
858 *s = (c & 0x3F) | 0x80;
864 *s++ = ((c >> 18) & 0x07) | 0xF0;
865 *s++ = ((c >> 12) & 0x3F) | 0x80;
866 *s++ = ((c >> 6) & 0x3F) | 0x80;
867 *s = (c & 0x3F) | 0x80;
879 while (*s && Symbols--) {
921 while (*s && --Size > 0) {
923 *a++ = (
uchar)(*s++);
940 while (*a && NumChars < Size) {
941 if (Max >= 0 && NumSyms++ >= Max)
949 if (NumChars + sl <= Size) {
974 cd = iconv_open(ToCode, FromCode);
982 if (
cd != (iconv_t)-1)
990 if (!strcasestr(CharacterTable,
"UTF-8")) {
993 for (
int i = 0; i < 128; i++)
997 const char *s = csc.
Convert(buf);
1011 if (
cd != (iconv_t)-1 && From && *From) {
1012 char *FromPtr = (
char *)From;
1013 size_t FromLength = strlen(From);
1016 int NewLength =
max(
length, FromLength * 2);
1017 if (
char *NewBuffer = (
char *)realloc(
result, NewLength)) {
1022 esyslog(
"ERROR: out of memory");
1031 char *Converted = ToPtr;
1032 while (FromLength > 0) {
1033 if (iconv(
cd, &FromPtr, &FromLength, &ToPtr, &ToLength) ==
size_t(-1)) {
1034 if (errno == E2BIG || errno == EILSEQ && ToLength < 1) {
1038 size_t d = ToPtr -
result;
1040 int NewLength =
length + r;
1041 if (
char *NewBuffer = (
char *)realloc(
result, NewLength)) {
1043 Converted =
result = NewBuffer;
1046 esyslog(
"ERROR: out of memory");
1052 if (errno == EILSEQ) {
1059 else if (errno != E2BIG)
1073 s = TakePointer ? (
char *)S : S ? strdup(S) : NULL;
1092 s = String.
s ? strdup(String.
s) : NULL;
1102 if (
this == &String)
1105 s = String.
s ? strdup(String.
s) : NULL;
1122 s = String ? strdup(String) : NULL;
1129 int l1 =
s ? strlen(
s) : 0;
1130 int l2 = strlen(String);
1131 if (
char *p = (
char *)realloc(
s, l1 + l2 + 1)) {
1133 strcpy(
s + l1, String);
1136 esyslog(
"ERROR: out of memory");
1144 int l1 =
s ? strlen(
s) : 0;
1146 if (
char *p = (
char *)realloc(
s, l1 + l2 + 1)) {
1152 esyslog(
"ERROR: out of memory");
1162 if (Index >= 0 && Index < l)
1178 if (!fmt || vasprintf(&buffer, fmt, ap) < 0) {
1179 esyslog(
"error in vasprintf('%s', ...)", fmt);
1180 buffer = strdup(
"???");
1189 if (!fmt || vasprintf(&buffer, fmt, ap) < 0) {
1190 esyslog(
"error in vasprintf('%s', ...)", fmt);
1191 buffer = strdup(
"???");
1199 WeekDay = WeekDay == 0 ? 6 : WeekDay - 1;
1200 if (0 <= WeekDay && WeekDay <= 6) {
1202 const char *day =
tr(
"MonTueWedThuFriSatSun");
1214 return WeekDayName(localtime_r(&t, &tm_r)->tm_wday);
1219 WeekDay = WeekDay == 0 ? 6 : WeekDay - 1;
1221 case 0:
return tr(
"Monday");
1222 case 1:
return tr(
"Tuesday");
1223 case 2:
return tr(
"Wednesday");
1224 case 3:
return tr(
"Thursday");
1225 case 4:
return tr(
"Friday");
1226 case 5:
return tr(
"Saturday");
1227 case 6:
return tr(
"Sunday");
1228 default:
return "???";
1244 tm *tm = localtime_r(&t, &tm_r);
1245 snprintf(buffer,
sizeof(buffer),
"%s %02d.%02d. %02d:%02d", *
WeekDayName(tm->tm_wday), tm->tm_mday, tm->tm_mon + 1, tm->tm_hour, tm->tm_min);
1252 if (ctime_r(&t, buffer)) {
1253 buffer[strlen(buffer) - 1] = 0;
1263 tm *tm = localtime_r(&t, &tm_r);
1266 strftime(p,
sizeof(buf) - (p - buf),
"%d.%m.%Y", tm);
1274 tm *tm = localtime_r(&t, &tm_r);
1275 strftime(buf,
sizeof(buf),
"%d.%m.%y", tm);
1283 strftime(buf,
sizeof(buf),
"%R", localtime_r(&t, &tm_r));
1289#define JPEGCOMPRESSMEM 500000
1309 int Used = jcd->
size;
1311 if (
uchar *NewBuffer = (
uchar *)realloc(jcd->
mem, NewSize)) {
1312 jcd->
size = NewSize;
1313 jcd->
mem = NewBuffer;
1316 esyslog(
"ERROR: out of memory");
1320 cinfo->dest->next_output_byte = jcd->
mem + Used;
1321 cinfo->dest->free_in_buffer = jcd->
size - Used;
1332 int Used = cinfo->dest->next_output_byte - jcd->
mem;
1333 if (Used < jcd->size) {
1336 jcd->
mem = NewBuffer;
1339 esyslog(
"ERROR: out of memory");
1348 else if (Quality > 100)
1351 jpeg_destination_mgr jdm;
1357 struct jpeg_compress_struct cinfo;
1358 struct jpeg_error_mgr jerr;
1359 cinfo.err = jpeg_std_error(&jerr);
1360 jpeg_create_compress(&cinfo);
1363 cinfo.client_data = &jcd;
1364 cinfo.image_width = Width;
1365 cinfo.image_height = Height;
1366 cinfo.input_components = 3;
1367 cinfo.in_color_space = JCS_RGB;
1369 jpeg_set_defaults(&cinfo);
1370 jpeg_set_quality(&cinfo, Quality, TRUE);
1371 jpeg_start_compress(&cinfo, TRUE);
1374 JSAMPROW rp[Height];
1375 for (
int k = 0; k < Height; k++)
1376 rp[k] = &Mem[rs * k];
1377 jpeg_write_scanlines(&cinfo, rp, Height);
1378 jpeg_finish_compress(&cinfo);
1379 jpeg_destroy_compress(&cinfo);
1389 static char buffer[HOST_NAME_MAX] =
"";
1391 if (gethostname(buffer,
sizeof(buffer)) < 0) {
1393 strcpy(buffer,
"vdr");
1401const char *
cBase64Encoder::b64 =
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
1424 c |= (
data[
i] >> 4) & 0x0F;
1427 c = (
data[
i] << 2) & 0x3F;
1429 c |= (
data[
i] >> 6) & 0x03;
1528 Add(FileHandle, Out);
1533 if (FileHandle >= 0) {
1535 if (
pfd[i].fd == FileHandle &&
pfd[i].events == (Out ? POLLOUT : POLLIN))
1545 esyslog(
"ERROR: too many file handles in cPoller");
1552 if (FileHandle >= 0) {
1554 if (
pfd[i].fd == FileHandle &&
pfd[i].events == (Out ? POLLOUT : POLLIN)) {
1589#if !__GLIBC_PREREQ(2, 24)
1594 if (strcmp(
result->d_name,
".") && strcmp(
result->d_name,
".."))
1610 for (
int i = 0; i < Size(); i++) {
1611 if (!strcmp(s, At(i)))
1619 for (
int i = 0; i < Size(); i++)
1629 Load(Directory, DirsOnly);
1639 while ((e =
d.Next()) != NULL) {
1642 if (stat(
AddDirectory(Directory, e->d_name), &ds) == 0) {
1643 if (!S_ISDIR(ds.st_mode))
1647 Append(strdup(e->d_name));
1661bool cFile::files[FD_SETSIZE] = {
false };
1662int cFile::maxFiles = 0;
1678 return Open(open(FileName, Flags, Mode));
1679 esyslog(
"ERROR: attempt to re-open %s", FileName);
1690 if (f < FD_SETSIZE) {
1696 esyslog(
"ERROR: file descriptor %d already in files[]", f);
1700 esyslog(
"ERROR: file descriptor %d is larger than FD_SETSIZE (%d)", f, FD_SETSIZE);
1705 esyslog(
"ERROR: attempt to re-open file descriptor %d", FileDes);
1723 return f >= 0 && FileReady(f, Wait ? 1000 : 0);
1727bool cFile::AnyFileReady(
int FileDes,
int TimeoutMs)
1731 for (
int i = 0; i < maxFiles; i++) {
1735 if (0 <= FileDes && FileDes < FD_SETSIZE && !files[FileDes])
1736 FD_SET(FileDes, &set);
1739 struct timeval timeout;
1740 timeout.tv_sec = TimeoutMs / 1000;
1741 timeout.tv_usec = (TimeoutMs % 1000) * 1000;
1742 return select(FD_SETSIZE, &set, NULL, NULL, &timeout) > 0 && (FileDes < 0 || FD_ISSET(FileDes, &set));
1749 struct timeval timeout;
1751 FD_SET(FileDes, &set);
1752 if (TimeoutMs >= 0) {
1753 if (TimeoutMs < 100)
1755 timeout.tv_sec = TimeoutMs / 1000;
1756 timeout.tv_usec = (TimeoutMs % 1000) * 1000;
1758 return select(FD_SETSIZE, &set, NULL, NULL, (TimeoutMs >= 0) ? &timeout : NULL) > 0 && FD_ISSET(FileDes, &set);
1762bool cFile::FileReadyForWriting(
int FileDes,
int TimeoutMs)
1765 struct timeval timeout;
1767 FD_SET(FileDes, &set);
1768 if (TimeoutMs < 100)
1771 timeout.tv_usec = TimeoutMs * 1000;
1772 return select(FD_SETSIZE, NULL, &set, NULL, &timeout) > 0 && FD_ISSET(FileDes, &set);
1782 tempName = fileName ?
MALLOC(
char, strlen(fileName) + 5) : NULL;
1784 strcat(strcpy(tempName, fileName),
".$$$");
1798 if (!f && fileName && tempName) {
1799 f = fopen(tempName,
"w");
1810 if (ferror(f) != 0) {
1816 if (fclose(f) < 0) {
1821 if (
result && rename(tempName, fileName) < 0) {
1833#ifndef USE_FADVISE_READ
1834#define USE_FADVISE_READ 0
1836#ifndef USE_FADVISE_WRITE
1837#define USE_FADVISE_WRITE 1
1840#define WRITE_BUFFER KILOBYTE(800)
1855 fd = open(FileName, Flags, Mode);
1857#if USE_FADVISE_READ || USE_FADVISE_WRITE
1858 begin = lastpos = ahead = 0;
1865 posix_fadvise(fd, 0, 0, POSIX_FADV_RANDOM);
1873#if USE_FADVISE_READ || USE_FADVISE_WRITE
1876 posix_fadvise(fd, 0, 0, POSIX_FADV_DONTNEED);
1880 return close(OldFd);
1891#define FADVGRAN KILOBYTE(4)
1892#define READCHUNK MEGABYTE(8)
1902 return posix_fadvise(fd, Offset - (
FADVGRAN - 1), Len + (
FADVGRAN - 1) * 2, POSIX_FADV_DONTNEED);
1907 if (Whence == SEEK_SET && Offset == curpos)
1909 curpos = lseek(fd, Offset, Whence);
1917 off_t jumped = curpos-lastpos;
1918 if ((cachedstart < cachedend) && (curpos < cachedstart || curpos > cachedend)) {
1920 FadviseDrop(cachedstart, cachedend-cachedstart);
1921 cachedstart = curpos;
1924 cachedstart =
min(cachedstart, curpos);
1926 ssize_t bytesRead =
safe_read(fd, Data, Size);
1927 if (bytesRead > 0) {
1928 curpos += bytesRead;
1930 cachedend =
max(cachedend, curpos);
1934 if (jumped >= 0 && jumped <= (off_t)readahead) {
1938 if (ahead - curpos < (off_t)(readahead / 2)) {
1939 posix_fadvise(fd, curpos, readahead, POSIX_FADV_WILLNEED);
1940 ahead = curpos + readahead;
1941 cachedend =
max(cachedend, ahead);
1943 if (readahead < Size * 32) {
1944 readahead = Size * 32;
1952 if (cachedstart < cachedend) {
1953 if (curpos - cachedstart >
READCHUNK * 2) {
1955 FadviseDrop(cachedstart, curpos -
READCHUNK - cachedstart);
1958 else if (cachedend > ahead && cachedend - curpos >
READCHUNK * 2) {
1974 ssize_t bytesWritten =
safe_write(fd, Data, Size);
1975#if USE_FADVISE_WRITE
1976 if (bytesWritten > 0) {
1977 begin =
min(begin, curpos);
1978 curpos += bytesWritten;
1979 written += bytesWritten;
1980 lastpos =
max(lastpos, curpos);
1982 if (lastpos > begin) {
1992 posix_fadvise(fd, begin - headdrop, lastpos - begin + headdrop, POSIX_FADV_DONTNEED);
1994 begin = lastpos = curpos;
1995 totwritten += written;
2010 off_t headdrop =
min(off_t(curpos - totwritten), off_t(totwritten * 2));
2011 posix_fadvise(fd, curpos - totwritten - headdrop, totwritten + headdrop, POSIX_FADV_DONTNEED);
2017 return bytesWritten;
2025 if (File->
Open(FileName, Flags, Mode) < 0) {
2034#define LOCKFILENAME ".lock-vdr"
2035#define LOCKFILESTALETIME 600
2053 if (f < 0 && fileName) {
2054 time_t Timeout = time(NULL) + WaitSeconds;
2056 f = open(fileName, O_WRONLY | O_CREAT | O_EXCL, DEFFILEMODE);
2058 if (errno == EEXIST) {
2060 if (stat(fileName, &fs) == 0) {
2062 esyslog(
"ERROR: removing stale lock file '%s'", fileName);
2063 if (remove(fileName) < 0) {
2070 else if (errno != ENOENT) {
2077 if (errno == ENOSPC) {
2078 esyslog(
"ERROR: can't create lock file '%s' - assuming lock anyway!", fileName);
2086 }
while (f < 0 && time(NULL) < Timeout);
2114 Object->
prev =
this;
2120 Object->
next =
this;
2146#define LIST_GARBAGE_COLLECTOR_TIMEOUT 5
2159 esyslog(
"ERROR: ListGarbageCollector destroyed without prior Purge()!");
2165 Object->
next = objects;
2167 lastPut = time(NULL);
2180 objects = Object->next;
2190:stateLock(NeedsLocking)
2208 esyslog(
"ERROR: cListBase::Lock() called for a list that doesn't require locking");
2230 if (Before && Before !=
objects) {
2267 if (From && To && From != To) {
2324 while (
object && Index-- > 0)
2325 object =
object->
Next();
2344 while (
object && i < n) {
2346 object =
object->
Next();
2350 for (i = 0; i < n; i++) {
2374 if (
size < NewSize) {
2381 esyslog(
"ERROR: out of memory");
2413 unsigned int hash =
hashfn(Id);
2424 if (hob->object == Object) {
2434 for (
int i = 0; i <
size; i++) {
cBase64Encoder(const uchar *Data, int Length, int MaxResult=64)
Sets up a new base 64 encoder for the given Data, with the given Length.
const char * NextLine(void)
Returns the next line of encoded data (terminated by '\0'), or NULL if there is no more encoded data.
bool SetLength(int Length)
cCharSetConv(const char *FromCode=NULL, const char *ToCode=NULL)
Sets up a character set converter to convert from FromCode to ToCode.
static const char * SystemCharacterTable(void)
static void SetSystemCharacterTable(const char *CharacterTable)
static char * systemCharacterTable
const char * Convert(const char *From, char *To=NULL, size_t ToLength=0)
Converts the given Text from FromCode to ToCode (as set in the constructor).
static void SleepMs(int TimeoutMs)
Creates a cCondWait object and uses it to sleep for TimeoutMs milliseconds, immediately giving up the...
cDynamicBuffer(int InitialSize=1024)
bool Realloc(int NewSize)
void Append(const uchar *Data, int Length)
bool Load(const char *Directory, bool DirsOnly=false)
cFileNameList(const char *Directory=NULL, bool DirsOnly=false)
static bool FileReady(int FileDes, int TimeoutMs=1000)
bool Ready(bool Wait=true)
bool Open(const char *FileName, int Flags, mode_t Mode=DEFFILEMODE)
void Del(cListObject *Object, unsigned int Id)
cListObject * Get(unsigned int Id) const
cList< cHashObject > ** hashTable
cList< cHashObject > * GetList(unsigned int Id) const
cHashBase(int Size, bool OwnObjects)
Creates a new hash of the given Size.
void Add(cListObject *Object, unsigned int Id)
unsigned int hashfn(unsigned int Id) const
void Ins(cListObject *Object, cListObject *Before=NULL)
bool Contains(const cListObject *Object) const
If a pointer to an object contained in this list has been obtained while holding a lock,...
void Del(cListObject *Object, bool DeleteObject=true)
virtual void Move(int From, int To)
void SetExplicitModify(void)
If you have obtained a write lock on this list, and you don't want it to be automatically marked as m...
void SetModified(void)
Unconditionally marks this list as modified.
bool Lock(cStateKey &StateKey, bool Write=false, int TimeoutMs=0) const
Tries to get a lock on this list and returns true if successful.
const char * needsLocking
cListBase(const char *NeedsLocking=NULL)
const cListObject * Get(int Index) const
void Add(cListObject *Object, cListObject *After=NULL)
void Purge(bool Force=false)
cListGarbageCollector(void)
void Put(cListObject *Object)
cListObject * Prev(void) const
virtual int Compare(const cListObject &ListObject) const
Must return 0 if this object is equal to ListObject, a positive value if it is "greater",...
void Insert(cListObject *Object)
cListObject * Next(void) const
void Append(cListObject *Object)
const T * First(void) const
Returns the first element in this list, or NULL if the list is empty.
const T * Next(const T *Object) const
< Returns the element immediately before Object in this list, or NULL if Object is the first element ...
bool Lock(int WaitSeconds=0)
cLockFile(const char *Directory)
cPoller(int FileHandle=-1, bool Out=false)
bool Add(int FileHandle, bool Out)
bool Poll(int TimeoutMs=0)
void Del(int FileHandle, bool Out)
cReadDir(const char *Directory)
struct dirent * Next(void)
cSafeFile(const char *FileName)
void SetExplicitModify(void)
If you have obtained a write lock on this lock, and you don't want its state to be automatically incr...
void SetModified(void)
Sets this lock to have its state incremented when the current write lock state key is removed.
bool Lock(cStateKey &StateKey, bool Write=false, int TimeoutMs=0)
Tries to get a lock and returns true if successful.
int Find(const char *s) const
cString & CompactChars(char c)
Compact any sequence of characters 'c' to a single character, and strip all of them from the beginnin...
static cString static cString vsprintf(const char *fmt, va_list &ap)
cString(const char *S=NULL, bool TakePointer=false)
static cString sprintf(const char *fmt,...) __attribute__((format(printf
cString & operator=(const cString &String)
cString & Append(const char *String)
cString & Truncate(int Index)
Truncate the string at the given Index (if Index is < 0 it is counted from the end of the string).
static tThreadId ThreadId(void)
uint64_t Elapsed(void) const
void Set(int Ms=0)
Sets the timer.
bool TimedOut(void) const
cTimeMs(int Ms=0)
Creates a timer with ms resolution and an initial timeout of Ms.
static uint64_t Now(void)
cUnbufferedFile is used for large files that are mainly written or read in a streaming manner,...
static cUnbufferedFile * Create(const char *FileName, int Flags, mode_t Mode=DEFFILEMODE)
void SetReadAhead(size_t ra)
ssize_t Write(const void *Data, size_t Size)
int Open(const char *FileName, int Flags, mode_t Mode=DEFFILEMODE)
ssize_t Read(void *Data, size_t Size)
int FadviseDrop(off_t Offset, off_t Len)
off_t Seek(off_t Offset, int Whence)