This repository has been archived by the owner on Jan 16, 2021. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 38
/
aparse.h
128 lines (113 loc) · 3.19 KB
/
aparse.h
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
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
// -*-c++-*-
/* $Id$ */
/*
*
* Copyright (C) 2002-2004 Maxwell Krohn (max@okcupid.com)
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2, or (at
* your option) any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
* USA
*
*/
#ifndef _LIBAHTTP_APARSE_H
#define _LIBAHTTP_APARSE_H
#include "abuf.h"
//
// Asynchronous Parser Skeleton Class
//
class async_parser_t {
public:
async_parser_t ()
: abuf (NULL), nwabuf (false), parsing (false), dataready (false) {}
async_parser_t (abuf_src_t *a)
: abuf (New abuf_t (a)), nwabuf (true), parsing (false),
dataready (false) {}
async_parser_t (abuf_t *a)
: abuf (a), nwabuf (false), parsing (false), dataready (false) {}
virtual ~async_parser_t () { if (nwabuf) delete (abuf); }
void parse (cbi::ptr c = NULL);
void can_read_cb ();
void cancel ();
void finish_parse (int r = 0);
void resume ();
void reset ()
{
if (abuf) abuf->reset ();
parsing = dataready = false;
}
// where the real guts of the async parsing is done -- not here
virtual void parse_guts () = 0;
virtual void v_debug () {}
abuf_t *get_abuf () { return abuf; }
protected:
abuf_t *abuf;
private:
cbi::ptr pcb;
bool nwabuf;
bool parsing;
protected:
bool dataready;
};
class async_raw_post_parser_t : public async_parser_t {
public:
explicit async_raw_post_parser_t(abuf_t *a, size_t len) :
async_parser_t(a), m_body(len), m_bp(m_body.cstr()),
m_endp(m_bp + len),
m_ok(false)
{}
str contents() {
if (!m_ok) {
return str(NULL);
} else {
m_body.setlen((m_bp - m_body.cstr()));
// This destroys the underlying m_str and is effectively a move
// constructor.
return str(m_body);
}
}
protected:
void parse_guts(){
// Grab the post body ourselves!
ssize_t rc = 0;
while (m_bp < m_endp) {
rc = abuf->dump(m_bp, m_endp - m_bp);
if (rc < 0) {
assert(rc == ABUF_EOFCHAR || rc == ABUF_WAITCHAR);
break;
}
m_bp += rc;
}
if (m_bp == m_endp || rc == ABUF_EOFCHAR) {
m_ok = true;
finish_parse(HTTP_OK);
}
// otherwise, we're waiting
}
mstr m_body;
char *m_bp, *m_endp;
bool m_ok;
};
class async_dumper_t : public async_parser_t {
public:
async_dumper_t (abuf_t *a) : async_parser_t (a), buf (NULL) {}
~async_dumper_t () { if (buf) delete buf; }
void dump (size_t len, cbs c);
protected:
void parse_guts ();
void parse_done_cb (int dummy);
mstr *buf;
char *bp, *endp;
cbs::ptr dump_cb;
};
#endif