Fix memory leaks found by valgrind
[infodrom/cgilib] / aux.c
1 /*
2     aux.c - Auxilliary code for CGI library
3     Copyright (C) 2007,8 by Martin Schulze <joey@infodrom.org>
4      
5     This program is free software; you can redistribute it and/or modify
6     it under the terms of the GNU General Public License as published by
7     the Free Software Foundation; either version 2 of the License, or
8     (at your option) any later version.
9     
10     This program is distributed in the hope that it will be useful,
11     but WITHOUT ANY WARRANTY; without even the implied warranty of
12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13     GNU General Public License for more details.
14     
15     You should have received a copy of the GNU General Public License
16     along with this program; if not, write to the Free Software Foundation
17     Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #include <stdlib.h>
21 #include <string.h>
22 #include <stdarg.h>
23 #include <stdio.h>
24 #include <syslog.h>
25
26 int cgiDebugLevel = 0;
27 int cgiDebugType = 1;
28
29 char *cgiEscape (char *string)
30 {
31     char *cp, *np;
32     char *buf;
33     size_t len;
34
35     for (cp=string, len=0; *cp; cp++) {
36         switch (*cp) {
37         case '&':
38             len+=5;
39             break;
40         case '<':
41         case '>':
42             len+=4;
43             break;
44         default:
45             len++;
46             break;
47         }
48     }
49
50     if (len == strlen(string))
51         return strdup(string);
52
53     if ((buf = (char *)malloc(len+1)) == NULL)
54         return NULL;
55
56     for (cp=string, np=buf; *cp; cp++) {
57         switch (*cp) {
58         case '&':
59             *np++ = '&';
60             *np++ = 'a';
61             *np++ = 'm';
62             *np++ = 'p';
63             *np++ = ';';
64             break;
65         case '<':
66             *np++ = '&';
67             *np++ = 'l';
68             *np++ = 't';
69             *np++ = ';';
70             break;
71         case '>':
72             *np++ = '&';
73             *np++ = 'g';
74             *np++ = 't';
75             *np++ = ';';
76             break;
77         default:
78             *np++ = *cp;
79             break;
80         }
81     }
82     *np = '\0';
83
84     return buf;
85 }
86
87 void cgiDebugOutput (int level, char *format, ...)
88 {
89   va_list args;
90
91   if (level <= cgiDebugLevel) {
92
93       va_start (args, format);
94
95       switch (cgiDebugType) {
96       case 0:
97           printf ("<pre>\n");
98           vprintf (format, args);
99           printf ("\n</pre>\n");
100           break;
101       case 1:
102           vfprintf (stderr, format, args);
103           printf ("\n");
104           break;
105       case 2:
106           vsyslog (LOG_DEBUG, format, args);
107           break;
108       }
109
110       va_end (args);
111   }
112 }
113
114 #define BUFSIZE 128
115
116 char *cgiGetLine (FILE *stream)
117 {
118     static char *line = NULL;
119     static size_t size = 0;
120     int len;
121     char buf[BUFSIZE];
122     char *cp;
123
124     if (!line) {
125       if ((line = (char *)malloc (BUFSIZE)) == NULL)
126         return NULL;
127       size = BUFSIZE;
128     }
129     line[0] = '\0';
130
131     while (!feof (stream)) {
132       if ((cp = fgets (buf, sizeof (buf), stream)) == NULL)
133       {
134         free(line);
135         line = NULL;
136         return NULL;
137       }
138
139       if (strlen(line)+strlen(buf)+1 > size) {
140         if ((cp = (char *)realloc (line, size + BUFSIZE)) == NULL)
141           return line;
142         cp[size] = '\0';
143         size += BUFSIZE;
144         line = cp;
145       }
146
147       strcat (line, buf);
148       len = strlen(line);
149       if (len && line[len-1] == '\n') {
150         line[len-1] = '\0';
151         len --;
152         if (len && line[len-1] == '\r')
153           line[len-1] = '\0';
154         cgiDebugOutput (4, "Read line '%s'", line);
155         return line;
156       }
157     }
158
159     free(line);
160     line = NULL;
161
162     return NULL;
163 }
164
165 /*
166  * Local variables:
167  *  c-indent-level: 4
168  *  c-basic-offset: 4
169  *  tab-width: 8
170  * End:
171  */