File: cal_misc.c

package info (click to toggle)
libmcal 0.6-12
  • links: PTS
  • area: main
  • in suites: woody
  • size: 556 kB
  • ctags: 472
  • sloc: ansic: 4,397; makefile: 180; sh: 111
file content (97 lines) | stat: -rw-r--r-- 2,814 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
#include <stdlib.h>
#include "cal_misc.h"

bool
cal_decode_dt(datetime_t *dt, const char *s)
{
        unsigned long   n;
        char            *endp;

        dt_init(dt);

        if (*s != 'T' && *s != 't') {
                n = strtoul(s, &endp, 10);
                if (endp - s != 8)
                        return false;
                if (!dt_setdate(dt, n/10000, (n/100)%100, n%100))
                        return false;
                if (*endp == '\0')
                        return true;
                s = endp;
        }

        if (*s == 'T' || *s == 't') {
                n = strtoul(++s, &endp, 10);
                if (endp - s != 6)
                        return false;
                if (!dt_settime(dt, n/10000, (n/100)%100, n%100))
                        return false;
                if (*endp && *endp != 'Z' && *endp != 'z')
                        return false;
        }
        else {
                return false;
        }

        return true;
}

unsigned char*
cal_decode_base64(unsigned char *buf, size_t *size)
{
        size_t          left;
        unsigned char   *in;
        unsigned char   *out;
        int             bsize;
        int             i;

        if (*size % 4)
                return NULL;

        left = *size;
        *size = 0;
        for (in=buf,out=buf; left>0; in+=4,left-=4) {
                if (in[0]=='=' || in[1]=='=')
                        return NULL;
                if (in[2]=='=' && in[3]!='=')
                        return NULL;
                if (in[3]=='=' && left>4)
                        return NULL;

                bsize = 3;
                for (i=0; i<4; i++) {
		  switch (in[i]) {
		  case '=':
                                in[i] = 0;
                                bsize--;
                                break;
		  case '+':
                                in[i] = 62; break;
		  case '/':
                                in[i] = 63; break;
		  default:
                                if (in[i]>='A' && in[i]<='Z')
                                        in[i] -= 'A';
                                else if (in[i]>='a' && in[i]<='z')
                                        in[i] -= 'a' - 26;
                                else if (in[i]>='0' && in[i]<='9')
                                        in[i] -= '0' - 52;
                                else
                                        return NULL;
		  }
                }

                out[0] = (0xfc&in[0]<<2) | (0x03&in[1]>>4);
                if (bsize>0)
                        out[1] = (0xf0&in[1]<<4) | (0x0f&in[2]>>2);
                if (bsize>1)
                        out[2] = (0xc0&in[2]<<6) | (0x3f&in[3]);

                out += bsize;
        }

        *out = '\0';
        *size = out - buf;

        return buf;
}