/[imapfilter]/imapfilter/connect.c
ViewVC logotype

Annotation of /imapfilter/connect.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1.10 - (hide annotations)
Tue Aug 28 22:42:06 2001 UTC (22 years, 7 months ago) by lefcha
Branch: MAIN
Changes since 1.9: +38 -0 lines
File MIME type: text/plain
Info message about deleted mails.

1 lefcha 1.1 #include <stdio.h>
2     #include <errno.h>
3     #include <unistd.h>
4     #include <sys/types.h>
5     #include <sys/time.h>
6     #include <sys/socket.h>
7     #include <fcntl.h>
8     #include <netdb.h>
9     #include <netinet/in.h>
10     #include <string.h>
11     #include <regex.h>
12    
13     #include "config.h"
14     #include "imapfilter.h"
15     #include "connect.h"
16     #include "log.h"
17     #include "imap.h"
18    
19    
20 lefcha 1.6 extern account_t *accounts;
21 lefcha 1.9 extern unsigned int options;
22 lefcha 1.6
23 lefcha 1.1 int sock;
24    
25    
26     /*
27     * Connects to mailserver.
28     */
29 lefcha 1.6 int init_connection(account_t * ca)
30 lefcha 1.1 {
31     struct sockaddr_in name;
32     struct hostent *hostinfo;
33    
34     memset((char *) &name, 0, sizeof(struct sockaddr_in));
35    
36     sock = socket(PF_INET, SOCK_STREAM, 0);
37     if (sock < 0) {
38     error("imapfilter: create socket; %s\n", strerror(errno));
39 lefcha 1.6 return 1;
40 lefcha 1.1 }
41    
42 lefcha 1.6 if (!(hostinfo = gethostbyname(ca->server))) {
43 lefcha 1.1 error("imapfilter: get network host entry; %s\n", strerror(errno));
44     close_connection();
45 lefcha 1.6 return 1;
46 lefcha 1.1 }
47    
48     name.sin_family = AF_INET;
49 lefcha 1.6 name.sin_port = htons(ca->port);
50 lefcha 1.1 name.sin_addr = *(struct in_addr *) hostinfo->h_addr;
51    
52     if (connect(sock, (struct sockaddr *) &name, sizeof(struct sockaddr))) {
53     error("imapfilter: initiating connection; %s\n", strerror(errno));
54     close_connection();
55 lefcha 1.6 return 1;
56 lefcha 1.1 }
57    
58 lefcha 1.7 info("Connected to %s as %s.\n", hostinfo->h_name, ca->userid);
59 lefcha 1.1
60 lefcha 1.6 return 0;
61 lefcha 1.1 }
62    
63    
64     /*
65     * Disconnects from mailserver.
66     */
67     int close_connection(void)
68     {
69     if (close(sock)) {
70     error("imapfilter: closing socket; %s\n", strerror(errno));
71 lefcha 1.6 return 1;
72     } else
73     return 0;
74 lefcha 1.1 }
75    
76    
77     /*
78 lefcha 1.9 * Reads data the server sent.
79 lefcha 1.1 */
80 lefcha 1.9 int recv_response(char *buf)
81 lefcha 1.1 {
82     int flags;
83     fd_set rfds;
84     struct timeval tv;
85    
86 lefcha 1.6 memset(buf, 0, RESPONSE_BUF);
87 lefcha 1.1
88     tv.tv_sec = 10;
89     tv.tv_usec = 0;
90    
91     flags = fcntl(sock, F_GETFL, 0);
92     fcntl(sock, F_SETFL, flags | O_NONBLOCK);
93    
94     FD_ZERO(&rfds);
95     FD_SET(sock, &rfds);
96    
97     if ((select(sock + 1, &rfds, NULL, NULL, &tv) > 0)
98     && FD_ISSET(sock, &rfds)) {
99 lefcha 1.6 if (read(sock, buf, RESPONSE_BUF - 1) != -1) {
100 lefcha 1.1 #ifdef DEBUG
101     printf("\n%s\n", buf);
102     #endif
103 lefcha 1.6 if (options & OPT_DETAILS_VERBOSE)
104 lefcha 1.1 analyze_response(buf);
105    
106     fcntl(sock, F_SETFL, flags);
107 lefcha 1.6 return 0;
108 lefcha 1.1 }
109     }
110    
111     fcntl(sock, F_SETFL, flags);
112    
113 lefcha 1.6 return 1;
114 lefcha 1.1 }
115    
116    
117     /*
118 lefcha 1.9 * Clears stream from any data server sent.
119 lefcha 1.1 */
120     int clear_stream(void)
121     {
122 lefcha 1.6 char buf[RESPONSE_BUF];
123 lefcha 1.1
124 lefcha 1.9 return recv_response(buf);
125 lefcha 1.1 }
126    
127    
128     /*
129 lefcha 1.9 * Processes the data that server sent due to IMAP STATUS client request.
130 lefcha 1.5 */
131 lefcha 1.8 int status_response(void)
132 lefcha 1.5 {
133 lefcha 1.8 int r, s;
134 lefcha 1.6 char buf[RESPONSE_BUF];
135 lefcha 1.9 char exist[STATUS_BUF], recent[STATUS_BUF], unseen[STATUS_BUF];
136 lefcha 1.8 regex_t creg;
137     regmatch_t match[4];
138     const char *reg =
139     "\\* STATUS INBOX \\(MESSAGES ([[:digit:]]+) RECENT ([[:digit:]]+) UNSEEN ([[:digit:]]+)\\)";
140 lefcha 1.6
141 lefcha 1.9 exist[0] = recent[0] = unseen[0] = 0;
142 lefcha 1.6
143 lefcha 1.9 r = recv_response(buf);
144 lefcha 1.5
145 lefcha 1.8 regcomp(&creg, reg, REG_EXTENDED);
146 lefcha 1.5
147 lefcha 1.8 if (!regexec(&creg, buf, 4, match, 0)) {
148     s = min(match[1].rm_eo - match[1].rm_so, STATUS_BUF - 1);
149 lefcha 1.9 strncpy(exist, buf + match[1].rm_so, s);
150     exist[s] = 0;
151 lefcha 1.6
152 lefcha 1.8 s = min(match[2].rm_eo - match[2].rm_so, STATUS_BUF - 1);
153     strncpy(recent, buf + match[2].rm_so, s);
154 lefcha 1.5 recent[s] = 0;
155 lefcha 1.8
156     s = min(match[3].rm_eo - match[3].rm_so, STATUS_BUF - 1);
157     strncpy(unseen, buf + match[3].rm_so, s);
158     unseen[s] = 0;
159    
160 lefcha 1.9 info("%s messages exist, %s recent, %s unseen.\n", exist, recent,
161 lefcha 1.8 unseen);
162 lefcha 1.6 }
163 lefcha 1.5
164 lefcha 1.10 regfree(&creg);
165    
166 lefcha 1.5 return r;
167     }
168    
169    
170     /*
171 lefcha 1.2 * Processes the data that server sent due to IMAP SEARCH client request.
172 lefcha 1.1 */
173 lefcha 1.6 int search_response(char *res)
174 lefcha 1.1 {
175 lefcha 1.5 int r, s, len;
176 lefcha 1.6 char buf[RESPONSE_BUF];
177     regex_t creg;
178 lefcha 1.1 regmatch_t match[2];
179 lefcha 1.3 const char *reg = "\\* SEARCH([[:digit:] ]*)";
180    
181 lefcha 1.6 len = strlen(res);
182 lefcha 1.1
183 lefcha 1.9 r = recv_response(buf);
184 lefcha 1.1
185 lefcha 1.6 regcomp(&creg, reg, REG_EXTENDED);
186 lefcha 1.1
187 lefcha 1.6 if (!regexec(&creg, buf, 2, match, 0)) {
188     s = min(match[1].rm_eo - match[1].rm_so, SEARCH_BUF - 1);
189     strncpy(res + len, buf + match[1].rm_so, s);
190     res[s + len] = 0;
191 lefcha 1.5 }
192 lefcha 1.10
193     regfree(&creg);
194    
195 lefcha 1.5 return r;
196 lefcha 1.1 }
197    
198    
199     /*
200 lefcha 1.2 * Processes the data that server sent due to IMAP FETCH client request.
201 lefcha 1.1 */
202 lefcha 1.6 int fetch_response(char *res)
203 lefcha 1.1 {
204 lefcha 1.5 int r, i, s, len = 0;
205 lefcha 1.6 char buf[RESPONSE_BUF];
206     regex_t creg[3];
207 lefcha 1.1 regmatch_t match[1];
208     const char *reg[3] = {
209     "Date: [[:print:]]*",
210     "From: [[:print:]]*",
211     "Subject: [[:print:]]*"
212     };
213    
214 lefcha 1.9 r = recv_response(buf);
215 lefcha 1.1
216     for (i = 0; i < 3; i++) {
217 lefcha 1.6 regcomp(&creg[i], reg[i], REG_EXTENDED);
218 lefcha 1.1
219 lefcha 1.6 if (!regexec(&creg[i], buf, 1, match, 0)) {
220 lefcha 1.1 s = min(match[0].rm_eo - match[0].rm_so,
221     HEADERS_MAX - len - 1);
222 lefcha 1.6 strncpy(res + len, buf + match[0].rm_so, s);
223     res[s + len] = '\n';
224     res[s + len + 1] = 0;
225     len = strlen(res);
226 lefcha 1.1 }
227     }
228 lefcha 1.5
229 lefcha 1.10 for (i = 0; i < 3; i++)
230     regfree(&creg[i]);
231    
232     return r;
233     }
234    
235    
236     /*
237     * Proccesses data that server sent due to IMAP EXPUNGE client request.
238     */
239     int expunge_response(void)
240     {
241     int r, i = 0, e = 0;
242     char buf[RESPONSE_BUF];
243     regex_t creg;
244     regmatch_t match[1];
245     const char *reg = "\\* [[:digit:]]+ EXPUNGE";
246    
247     r = recv_response(buf);
248    
249     regcomp(&creg, reg, REG_EXTENDED);
250    
251     while (!regexec(&creg, buf + e, 1, match, 0)) {
252     e += match[0].rm_eo;
253     i++;
254     }
255    
256     info("%d messages expunged.\n", i);
257    
258     regfree(&creg);
259    
260 lefcha 1.5 return r;
261 lefcha 1.1 }
262    
263    
264     /*
265     * Checks if response of server to client's request was succesfully
266     * delivered or there was some kind of error.
267     */
268     void analyze_response(char *buf)
269     {
270     int s;
271 lefcha 1.6 regex_t creg;
272 lefcha 1.1 regmatch_t match[2];
273 lefcha 1.9 const char *reg = "[[:xdigit:]]{4,4} ((OK|NO|BAD) [[:print:]]*)";
274 lefcha 1.6 char res[RESULTS_BUF];
275 lefcha 1.1
276 lefcha 1.6 regcomp(&creg, reg, REG_EXTENDED);
277 lefcha 1.1
278 lefcha 1.6 if (!regexec(&creg, buf, 2, match, 0)) {
279     s = min(match[1].rm_eo - match[1].rm_so, RESULTS_BUF - 1);
280     strncpy(res, buf + match[1].rm_so, s);
281     res[s] = 0;
282     printf("Server response: %s\n", res);
283 lefcha 1.1 }
284 lefcha 1.10
285     regfree(&creg);
286 lefcha 1.1 }

webmaster@linux.gr
ViewVC Help
Powered by ViewVC 1.1.26