/[libspopc]/format.c
ViewVC logotype

Contents of /format.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 6 - (show annotations)
Sun Apr 18 11:05:58 2010 UTC (10 years, 6 months ago) by ben
File MIME type: text/plain
File size: 7588 byte(s)
windows version revival (dev-cpp)
1 /* this is format.c file, part of the libspopc library sources
2 * copyright © 2002- Benoit Rouits <brouits@free.fr>
3 * released under the terms of the GNU Lesser General Public Licence.
4 *
5 * libspopc offers simple API for a pop3 client.
6 * See RFC 1725 for pop3 specifications.
7 * more information on http://herewe.servebeer.com/libspopc/
8 *
9 * This library is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Lesser General Public
11 * License as published by the Free Software Foundation; either
12 * version 2.1 of the License, or (at your option) any later version.
13 *
14 * This library is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * Lesser General Public License for more details.
18 *
19 * You should have received a copy of the GNU Lesser General Public
20 * License along with this library; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22 */
23
24 #include <stdlib.h>
25 #include <string.h>
26 #include <stdio.h>
27 #include "libspopc.h"
28
29 /************************************************************
30 * libspopc functions to format pop data returned by server *
31 ************************************************************/
32
33 DLLIMPORT char* nextline(char* string){
34 /* returns a pointer to the next line of given string */
35 while(((*string) != '\n')&&((*string) != '\0')){
36 string++;
37 }
38 if(!(*string)){
39 return (NULL);
40 }
41 return(string+1);
42 }
43
44 DLLIMPORT char* retr2msg(char* data){
45 /* retruns formatted mail from a pop RETR X query */
46 /* should only be called on data returned by pop3_retr() */
47 char* msg=NULL;
48 char* cur;
49
50 if((!data)||pop3_error(data)){
51 return(NULL);/* any suggestions ? */
52 }
53 while (( data != NULL ) && (strncmp("+OK", data, 3) != 0)){
54 data=nextline(data); /* skip ...\n before +OK */
55 }
56 if(( data != NULL ) && (strncmp("+OK", data, 3) == 0)) {
57 data=nextline(data); /* skip +OK ...\n */
58 }
59 msg=data?(char*)malloc(strlen(data)):NULL;
60 if(!msg){
61 return(NULL);
62 }
63 cur=msg;
64 while(*data){
65 if(DOTBEGIN(data)){
66 (*cur)=(*data); /* keep \n */
67 data+=2; /* skip first dot */
68 cur++;
69 }else{
70 (*cur)=(*data);
71 cur++;data++;
72 }
73 }
74 (*(cur-2))='\0'; /* erase \r\n */
75 return(msg);
76 }
77
78 DLLIMPORT void freemsg(char* msg){
79 free(msg);
80 }
81
82 DLLIMPORT int* list2array(char* poplist){
83 /* returns an int array of sizes of messages from a LIST pop query */
84 /* array[0] holds id of the array's element */
85 /* should only be called on data received by a pop3_list() request */
86 int* array=NULL;
87 int len,size;
88 int id=0;
89 char* cur;
90
91 if((!poplist)||pop3_error(poplist)){
92 return(NULL); /* any suggestions ? */
93 }
94 if(!dotline(poplist)){/* if simple element list */
95 /* one should't use this function for simple element... */
96 /* one should better use listi2size() */
97 /* skip '+OK ': look for first mail int id */
98 for(cur=poplist;(*cur<'0')||(*cur>'9');cur++);
99 /* not dot line here */
100 sscanf(cur,"%d %d\n",&id,&size);
101 array=(int*)malloc((id+1)*sizeof(int));
102 memset(array,0,(id+1)*sizeof(int));
103 array[0]=id;
104 array[id]=size;
105 return(array);
106 }
107 /* else this is a true list */
108 /* skip '+OK\r\n' :*/
109 for(cur=poplist;(*cur!='.')&&(*cur!='\n'); cur++);
110 cur ++; /* one more time to get behind '\n' */
111 len=1; /* array len */
112 while((*cur)!='.'){
113 sscanf(cur,"%d %d\n",&id,&size);
114 while(id > len){ /* pad array while id > len */
115 len++;
116 array=(int*)realloc(array,len*sizeof(int));
117 array[len-1]=0; /* no mail */
118 }
119 len++;
120 array=(int*)realloc(array,len*sizeof(int));
121 array[id]=size;
122 cur=nextline(cur);
123 }
124 if(id){
125 array[0]=id; /* last id */
126 }else{ /* no mail */
127 array=(int*)realloc(array, 1*sizeof(int));
128 array[0]=0;
129 }
130 return(array);
131 }
132
133 DLLIMPORT void freelistarray(int* array){
134 /* free array allocated by list2array() */
135 free(array);
136 }
137
138 DLLIMPORT int listi2size(char* resp){
139 /* grep the given size (in bytes) in resp after a pop3_list(sock,ID) request */
140 int i;
141 int r;
142
143 if(pop3_error(resp)){
144 return(0); /* no message ! */
145 }
146 r=sscanf(resp+5,"%d\n",&i);/* skip '+OK ' should be safer FIXME */
147 if(!r){ /* special case when no messages on server */
148 return(0);
149 }
150 return(i);
151 }
152
153 DLLIMPORT int stat2num(char* resp){
154 /* returns the num of retrievable (non-deleted) messages */
155 /* should only be called just after a pop3_stat() request */
156 int n,s,r;
157
158 if((!resp)||pop3_error(resp)){
159 return(-1);
160 }
161 r=sscanf(resp+4,"%d %d\n",&n,&s); /* with skip '+OK ' */
162 if (r == 2)
163 return n;
164 else
165 return -1;
166 }
167
168 DLLIMPORT int stat2bytes(char* resp){
169 /* returns the sumsize in bytes of all stored messages on server */
170 /* should only be called just after a pop3_stat() request */
171 int n,s,r;
172
173 if((!resp)||pop3_error(resp)){
174 return(-1);
175 }
176 r=sscanf(resp+4,"%d %d\n",&n,&s); /* skip '+OK ' */
177 if (r == 2)
178 return(s);
179 else
180 return -1;
181 }
182
183 DLLIMPORT char** uidl2array(char* resp){
184 /* returns an array of unique strings for each message id */
185 /* array[0] gives array's last id */
186 /* should only be called just after a pop3_uidl() request */
187 char** array=NULL;
188 int l,i=0; /* l is array lenth, i is id of msg */
189 char s[POPBUF]; /* temp signature string : sig theorically <=512B */
190 char* cur;
191
192 if((!resp)||pop3_error(resp)){
193 return(NULL); /* any suggestions ? */
194 }
195 if(!dotline(resp)){ /* simple element uidl */
196 /* one should not use this function for simple element */
197 /* one would better use uidli2sig() */
198 /* skip '+OK ': look for first mail int id */
199 for(cur=resp;(*cur<'0')||(*cur>'9');cur++);
200 /* no dot line here */
201 sscanf(cur,"%d %s\n",&i,s);
202 array=(char**)malloc((i+1)*sizeof(char*));
203 memset(array,0,(i+1)*sizeof(char*));
204 array[0]=(char*)malloc(POPBUF); /* up to 512B */
205 snprintf(array[0],POPBUF,"%d",i);
206 array[i]=strdup(s);
207 return(array);
208 }
209 /* else this is a true uid list */
210 /* skip '+OK\r\n : look for first mail integer id */
211 for(cur=resp;(*cur!='.')&&(*cur!='\n'); cur++);
212 cur ++; /* one more time to get behind '\n' */
213 l=1; /* array len */
214 while((*cur)!='.'){
215 sscanf(cur,"%d %s\n",&i,s);
216 while(i > l){ /* pad array while id > len */
217 l++;
218 array=(char**)realloc(array,l*sizeof(char*));
219 #if 0
220 array[l-1]=(char*)malloc(sizeof(char));
221 array[l-1]='\0';
222 #else
223 array[l-1]=NULL; /* for consitency with popchkmsg() */
224 #endif
225
226 }
227 l++;
228 array=(char**)realloc(array,l*sizeof(char*));
229 array[i]=(char*)malloc(POPBUF); /* up to 512B */
230 array[i]=strncpy(array[i],s,POPBUF);
231 cur=nextline(cur);
232 }
233 if(i){ /* i is now the last message id met in this session */
234 array[0]=(char*)malloc(9); /* up to 99999999 msg uids FIXME */
235 snprintf(array[0],9,"%d",i);
236 /* contains the id of the last msg (char*) (also tab length) */
237 }else{ /* zero message */
238 array=(char**)malloc(1*sizeof(char*));
239 array[0]=(char*)malloc(2*sizeof(char)); /* 2 because of '\0' */
240 snprintf(array[0],2,"%d",0);
241 }
242 return(array);
243 }
244
245 DLLIMPORT void freeuidlarray(char** array){
246 /* free the array allocated by uidl2array() */
247 int i,last;
248
249 last= atoi(array[0]);
250 for (i=1;i<=last;i++){
251 free(array[i]);
252 }
253 free(array[0]);
254 free(array);
255 }
256
257 DLLIMPORT char* uidli2sig(char* resp){
258 /* greps signature from server resp */
259 /* should only be called after a pop3_uidl(sock,ID) */
260 char* sig=NULL;
261
262 if(pop3_error(resp)){
263 return(NULL);/* no message ! */
264 }
265 sig=strdup(resp+5); /* skip '+OK ID' should be safer, FIXME */
266 if(sig[1]=='.'){/* special case when no messages on the server */
267 free(sig);
268 return(NULL);
269 }
270 return(sig);
271 }
272

  ViewVC Help
Powered by ViewVC 1.1.26