File: qmqp-mainloop.c

package info (click to toggle)
mailfront 0.98-2
  • links: PTS
  • area: main
  • in suites: etch, etch-m68k
  • size: 648 kB
  • ctags: 495
  • sloc: ansic: 3,033; sh: 1,487; makefile: 78
file content (101 lines) | stat: -rw-r--r-- 2,405 bytes parent folder | download
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
98
99
100
101
#include <stdlib.h>
#include <string.h>
#include <unistd.h>

#include <systime.h>
#include <iobuf/iobuf.h>
#include <msg/msg.h>
#include <str/str.h>

#include "mailfront.h"
#include "qmtp.h"

unsigned long maxdatabytes;

static const response* resp;

static char buf[8192];
static str line;

static void get_wrapper(ibuf* in)
{
  unsigned long wraplen;
  switch (get_netstring_len(in, &wraplen)) {
  case -1: exit(0);
  case 0: die1(111, "Invalid wrapper netstring");
  }
}

static void get_body(ibuf* in)
{
  unsigned long bodylen;
  char nl;
  switch (get_netstring_len(in, &bodylen)) {
  case -1: exit(0);
  case 0: die1(111, "Invalid message body netstring");
  }
  if (bodylen == 0) die1(111, "Zero length body");
  if (response_ok(resp)) resp = handle_data_start(0, "QMQP");
  while (bodylen > 0) {
    unsigned long len = sizeof buf;
    if (len > bodylen) len = bodylen;
    if (!ibuf_read(in, buf, len) && in->count == 0)
      die1(111, "EOF while reading body");
    if (response_ok(resp)) handle_data_bytes(buf, in->count);
    bodylen -= in->count;
  }
  if (!ibuf_getc(in, &nl)) die1(111, "EOF while reading comma");
  if (nl != ',') die1(111, "Invalid netstring terminator");
}

static void get_sender(ibuf* in)
{
  switch (get_netstring(in, &line)) {
  case -1: die1(111, "EOF while reading sender address");
  case 0: die1(111, "Invalid sender netstring");
  }
  msg3("sender <", line.s, ">");
  if (response_ok(resp))
    resp = handle_sender(&line);
  if (relayclient == 0) relayclient = "";
}

static void get_recips(ibuf* in)
{
  char ch;
  while (ibuf_peek(in, &ch)) {
    if (ch == ',') return;
    switch (get_netstring(in, &line)) {
    case -1: die1(111, "EOF while reading recipient list");
    case 0: die1(111, "Invalid recipient netstring");
    }
    msg3("recipient <", line.s, ">");
    if (response_ok(resp))
      resp = handle_recipient(&line);
  }
  die1(111, "EOF before end of recipient list");
}

static void get_package(ibuf* in)
{
  resp = handle_reset();
  get_wrapper(in);
  get_body(in);
  get_sender(in);
  get_recips(in);
  if (response_ok(resp)) resp = handle_data_end();
  if (!resp) resp = &resp_accepted;
  if (!respond_resp(resp, 1)) die1(111, "EOF while sending response");
}

int qmqp_mainloop(void)
{
  const response* r;
  if ((r = handle_init()) != 0) {
    respond_resp(r, 1);
    return 1;
  }
  alarm(3600);
  get_package(&inbuf);
  return 0;
}