1 /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
3 * Copyright (C) 1999-2008 Novell, Inc. (www.novell.com)
5 * Authors: Matt Brown <matt@mattb.net.nz>
6 * Jeffrey Stedfast <fejj@novell.com>
8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of version 2 of the GNU Lesser General Public
10 * License as published by the Free Software Foundation.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this program; if not, write to the
19 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
20 * Boston, MA 02110-1301, USA.
23 /* Strips PGP message headers from the input stream and also performs
24 * pgp decoding as described in section 7.1 of RFC2440 */
33 #include "camel-mime-filter-pgp.h"
35 #define CAMEL_MIME_FILTER_PGP_GET_PRIVATE(obj) \
36 (G_TYPE_INSTANCE_GET_PRIVATE \
37 ((obj), CAMEL_TYPE_MIME_FILTER_PGP, CamelMimeFilterPgpPrivate))
39 #define BEGIN_PGP_SIGNED_MESSAGE "-----BEGIN PGP SIGNED MESSAGE-----"
40 #define BEGIN_PGP_SIGNATURE "-----BEGIN PGP SIGNATURE-----"
41 #define END_PGP_SIGNATURE "-----END PGP SIGNATURE-----"
43 #define BEGIN_PGP_SIGNED_MESSAGE_LEN (sizeof (BEGIN_PGP_SIGNED_MESSAGE) - 1)
44 #define BEGIN_PGP_SIGNATURE_LEN (sizeof (BEGIN_PGP_SIGNATURE) - 1)
45 #define END_PGP_SIGNATURE_LEN (sizeof (END_PGP_SIGNATURE) - 1)
47 struct _CamelMimeFilterPgpPrivate {
58 G_DEFINE_TYPE (CamelMimeFilterPgp, camel_mime_filter_pgp, CAMEL_TYPE_MIME_FILTER)
61 mime_filter_pgp_run (CamelMimeFilter *mime_filter,
70 CamelMimeFilterPgpPrivate *priv;
71 const gchar *start, *inend = in + inlen;
72 register const gchar *inptr = in;
77 priv = CAMEL_MIME_FILTER_PGP_GET_PRIVATE (mime_filter);
79 /* only need as much space as the input, we're stripping chars */
80 camel_mime_filter_set_size (mime_filter, inlen, FALSE);
82 o = mime_filter->outbuf;
84 while (inptr < inend) {
88 while (inptr < inend && *inptr != '\n') {
89 if (blank && !strchr (" \t\r", *inptr))
96 camel_mime_filter_backup (mime_filter, start, inend - start);
103 if (len > 0 && inptr[-1] == '\r')
108 switch (priv->state) {
110 /* check for the beginning of the pgp block */
111 if (len == BEGIN_PGP_SIGNED_MESSAGE_LEN && !strncmp (start, BEGIN_PGP_SIGNED_MESSAGE, len)) {
116 memcpy (o, start, inptr - start);
117 o += (inptr - start);
120 /* pgp headers (Hash: SHA1, etc) end with a blank (zero-length,
121 * or containing only whitespace) line; see RFC2440 */
126 /* check for beginning of the pgp signature block */
127 if (len == BEGIN_PGP_SIGNATURE_LEN && !strncmp (start, BEGIN_PGP_SIGNATURE, len)) {
132 /* do dash decoding */
133 if (!strncmp (start, "- ", 2)) {
134 /* Dash encoded line found, skip encoding */
138 memcpy (o, start, inptr - start);
139 o += (inptr - start);
142 if (len == END_PGP_SIGNATURE_LEN && !strncmp (start, END_PGP_SIGNATURE, len))
143 priv->state = PGP_PREFACE;
148 *out = mime_filter->outbuf;
149 *outlen = o - mime_filter->outbuf;
150 *outprespace = mime_filter->outpre;
154 mime_filter_pgp_filter (CamelMimeFilter *mime_filter,
162 mime_filter_pgp_run (
163 mime_filter, in, len, prespace,
164 out, outlen, outprespace, FALSE);
168 mime_filter_pgp_complete (CamelMimeFilter *mime_filter,
176 mime_filter_pgp_run (
177 mime_filter, in, len, prespace,
178 out, outlen, outprespace, TRUE);
182 mime_filter_pgp_reset (CamelMimeFilter *mime_filter)
184 CamelMimeFilterPgpPrivate *priv;
186 priv = CAMEL_MIME_FILTER_PGP_GET_PRIVATE (mime_filter);
188 priv->state = PGP_PREFACE;
192 camel_mime_filter_pgp_class_init (CamelMimeFilterPgpClass *class)
194 CamelMimeFilterClass *mime_filter_class;
196 g_type_class_add_private (class, sizeof (CamelMimeFilterPgpPrivate));
198 mime_filter_class = CAMEL_MIME_FILTER_CLASS (class);
199 mime_filter_class->filter = mime_filter_pgp_filter;
200 mime_filter_class->complete = mime_filter_pgp_complete;
201 mime_filter_class->reset = mime_filter_pgp_reset;
205 camel_mime_filter_pgp_init (CamelMimeFilterPgp *filter)
207 filter->priv = CAMEL_MIME_FILTER_PGP_GET_PRIVATE (filter);
211 camel_mime_filter_pgp_new (void)
213 return g_object_new (CAMEL_TYPE_MIME_FILTER_PGP, NULL);