imap-quote.c revision 3d24361e648c120637f6fa250b423a063626bbbb
/* Copyright (c) 2002-2012 Dovecot authors, see the included COPYING file */
#include "lib.h"
#include "str.h"
#include "imap-arg.h"
#include "imap-quote.h"
/* If we have quoted-specials (<">, <\>) in a string, the minimum quoted-string
overhead is 3 bytes ("\") while the minimum literal overhead is 5 bytes
("{n}\r\n"). But the literal overhead also depends on the string size. If
the string length is less than 10, literal catches up to quoted-string after
3 quoted-specials. If the string length is 10..99, it catches up after 4
quoted-specials, and so on. We'll assume that the string lengths are usually
in double digits, so we'll switch to literals after seeing 4
quoted-specials. */
#define QUOTED_MAX_ESCAPE_CHARS 4
{
}
{
unsigned int i;
for (i = 0; src[i] != '\0'; i++) {
if (!IS_ASTRING_CHAR(src[i])) {
return;
}
}
if (i == 0)
else
}
static void
{
}
{
unsigned int i, escape_count = 0;
return;
}
/* first check if we can (or want to) write this as quoted or
as literal.
quoted-specials = DQUOTE / "\"
QUOTED-CHAR = <any TEXT-CHAR except quoted-specials> /
"\" quoted-specials
TEXT-CHAR = <any CHAR except CR and LF>
*/
for (i = 0; src[i] != '\0'; i++) {
switch (src[i]) {
case '"':
case '\\':
if (escape_count++ < QUOTED_MAX_ESCAPE_CHARS)
break;
/* fall through */
case 13:
case 10:
return;
default:
if ((unsigned char)src[i] >= 0x80) {
return;
}
break;
}
}
}
{
switch (*src) {
case 13:
case 10:
/* not allowed */
break;
case '"':
case '\\':
break;
default:
if ((unsigned char)*src >= 0x80) {
/* 8bit input not allowed in dquotes */
break;
}
break;
}
}
}
{
/* first check if there is anything to change */
for (i = 0; i < size; i++) {
switch (src[i]) {
case 0:
/* convert NUL to #0x80 */
break;
case '\t':
/* fall through */
case ' ':
if (last_lwsp) {
remove_count++;
}
break;
case 13:
case 10:
remove_count++;
break;
case '"':
case '\\':
break;
default:
if ((src[i] & 0x80) != 0)
break;
}
}
if (last_lwsp && i > 0) {
remove_count++;
}
if (!modify) {
/* fast path: we can simply write it as quoted string
without any escaping */
return;
}
for (i = 0; i < size; i++) {
switch (src[i]) {
case 0:
break;
case '\t':
case ' ':
if (!last_lwsp)
break;
case 13:
case 10:
break;
default:
break;
}
}
if (last_lwsp)
}