1 /*
2 ** Copyright 2011 Double Precision, Inc.
3 ** See COPYING for distribution information.
4 **
5 */
6 
7 #include	"rfc3676parser.h"
8 
9 extern "C" {
10 
tpp_trampoline_line_begin(size_t quote_level,void * arg)11 	int mail::tpp_trampoline_line_begin(size_t quote_level, void *arg)
12 	{
13 		reinterpret_cast<mail::textplainparser *>(arg)
14 			->line_begin(quote_level);
15 
16 		return 0;
17 	}
18 
tpp_trampoline_line_contents(const char32_t * ptr,size_t cnt,void * arg)19 	int mail::tpp_trampoline_line_contents(const char32_t *ptr,
20 					       size_t cnt, void *arg)
21 	{
22 		reinterpret_cast<mail::textplainparser *>(arg)
23 			->line_contents(ptr, cnt);
24 		return 0;
25 	}
26 
tpp_trampoline_line_flowed_notify(void * arg)27 	int mail::tpp_trampoline_line_flowed_notify(void *arg)
28 	{
29 		reinterpret_cast<mail::textplainparser *>(arg)
30 			->line_flowed_notify();
31 
32 		return 0;
33 	}
34 
tpp_trampoline_line_end(void * arg)35 	int mail::tpp_trampoline_line_end(void *arg)
36 	{
37 		reinterpret_cast<mail::textplainparser *>(arg)
38 			->line_end();
39 		return 0;
40 	}
41 }
42 
textplainparser()43 mail::textplainparser::textplainparser() : handle(NULL)
44 {
45 }
46 
~textplainparser()47 mail::textplainparser::~textplainparser()
48 {
49 	end();
50 }
51 
begin(const std::string & charset,bool flowed,bool delsp)52 bool mail::textplainparser::begin(const std::string &charset,
53 				  bool flowed,
54 				  bool delsp)
55 {
56 	end();
57 
58 	struct rfc3676_parser_info info=rfc3676_parser_info();
59 
60 	info.charset=charset.c_str();
61 	info.isflowed=flowed == true;
62 	info.isdelsp=delsp == true;
63 
64 	info.line_begin=&tpp_trampoline_line_begin;
65 	info.line_contents=&tpp_trampoline_line_contents;
66 	info.line_flowed_notify=&tpp_trampoline_line_flowed_notify;
67 	info.line_end=&tpp_trampoline_line_end;
68 
69 	info.arg=reinterpret_cast<void *>(this);
70 
71 	if ((handle=rfc3676parser_init(&info)) == NULL)
72 		return false;
73 
74 	return true;
75 }
76 
end(bool & unicode_errflag)77 void mail::textplainparser::end(bool &unicode_errflag)
78 {
79 	int rc=0;
80 
81 	if (handle)
82 	{
83 		rfc3676parser_deinit(handle, &rc);
84 		handle=NULL;
85 	}
86 
87 	unicode_errflag=rc != 0;
88 }
89 
line_begin(size_t quote_level)90 void mail::textplainparser::line_begin(size_t quote_level)
91 {
92 	if (quote_level)
93 	{
94 		std::vector<char32_t> vec;
95 
96 		vec.reserve(quote_level+1);
97 		vec.insert(vec.end(), quote_level, '>');
98 		vec.push_back(' ');
99 		line_contents(&vec[0], vec.size());
100 	}
101 }
102 
line_contents(const char32_t * data,size_t cnt)103 void mail::textplainparser::line_contents(const char32_t *data,
104 					  size_t cnt)
105 {
106 }
107 
line_flowed_notify()108 void mail::textplainparser::line_flowed_notify()
109 {
110 }
111 
line_end()112 void mail::textplainparser::line_end()
113 {
114 	char32_t nl='\n';
115 
116 	line_contents(&nl, 1);
117 }
118