This adds support for RFC6855 to imap/*.c.
Thanks to Arnt Gulbrandsen for the original patch.
char *ptr;
imap_fix_path (idata, mx.mbox, mbox, sizeof (mbox));
ptr = safe_strdup (mbox);
- imap_utf7_encode (&ptr);
+ imap_utf_encode (idata, &ptr);
mbox[sizeof (mbox) - 1] = '\0';
strncpy (mbox, ptr, sizeof (mbox) - 1);
FREE (&ptr);
char tmp[LONG_STRING];
char relpath[LONG_STRING];
IMAP_MBOX mx;
+ IMAP_DATA* idata;
if (imap_parse_path (state->folder, &mx))
return;
+ if (!(idata = imap_conn_find (&(mx.account), 0)))
+ return;
- imap_unmunge_mbox_name (folder);
+ imap_unmunge_mbox_name (idata, folder);
if (state->entrylen + 1 == state->entrymax)
{
static void cmd_parse_myrights (IMAP_DATA* idata, const char* s);
static void cmd_parse_search (IMAP_DATA* idata, const char* s);
static void cmd_parse_status (IMAP_DATA* idata, char* s);
+static void cmd_parse_enabled (IMAP_DATA* idata, const char* s);
static const char * const Capabilities[] = {
"IMAP4",
"LOGINDISABLED",
"IDLE",
"SASL-IR",
+ "ENABLE",
NULL
};
cmd_parse_search (idata, s);
else if (ascii_strncasecmp ("STATUS", s, 6) == 0)
cmd_parse_status (idata, s);
+ else if (ascii_strncasecmp ("ENABLED", s, 7) == 0)
+ cmd_parse_enabled (idata, s);
else if (ascii_strncasecmp ("BYE", s, 3) == 0)
{
dprint (2, (debugfile, "Handling BYE\n"));
}
else
{
- imap_unmunge_mbox_name (s);
+ imap_unmunge_mbox_name (idata, s);
list->name = s;
}
{
s = imap_next_word (mailbox);
*(s - 1) = '\0';
- imap_unmunge_mbox_name (mailbox);
+ imap_unmunge_mbox_name (idata, mailbox);
}
status = imap_mboxcache_get (idata, mailbox, 1);
FREE (&mx.mbox);
}
}
+
+/* cmd_parse_enabled: record what the server has enabled */
+static void cmd_parse_enabled (IMAP_DATA* idata, const char* s)
+{
+ dprint (2, (debugfile, "Handling ENABLED\n"));
+
+ while ((s = imap_next_word ((char*)s)) && *s != '\0')
+ {
+ if (ascii_strncasecmp(s, "UTF8=ACCEPT", 11) == 0 ||
+ ascii_strncasecmp(s, "UTF8=ONLY", 9) == 0)
+ idata->unicode = 1;
+ }
+}
return 0;
}
- imap_munge_mbox_name (mbox, sizeof (mbox), mailbox);
+ imap_munge_mbox_name (idata, mbox, sizeof (mbox), mailbox);
if (mutt_bit_isset (idata->capabilities, IMAP4REV1))
snprintf (buf, sizeof (buf), "STATUS %s (UIDVALIDITY)", mbox);
{
char buf[LONG_STRING], mbox[LONG_STRING];
- imap_munge_mbox_name (mbox, sizeof (mbox), mailbox);
+ imap_munge_mbox_name (idata, mbox, sizeof (mbox), mailbox);
snprintf (buf, sizeof (buf), "CREATE %s", mbox);
if (imap_exec (idata, buf, 0) != 0)
char newmbox[LONG_STRING];
char buf[LONG_STRING];
- imap_munge_mbox_name (oldmbox, sizeof (oldmbox), mx->mbox);
- imap_munge_mbox_name (newmbox, sizeof (newmbox), newname);
+ imap_munge_mbox_name (idata, oldmbox, sizeof (oldmbox), mx->mbox);
+ imap_munge_mbox_name (idata, newmbox, sizeof (newmbox), newname);
snprintf (buf, sizeof (buf), "RENAME %s %s", oldmbox, newmbox);
idata = ctx->data;
}
- imap_munge_mbox_name (mbox, sizeof (mbox), mx.mbox);
+ imap_munge_mbox_name (idata, mbox, sizeof (mbox), mx.mbox);
snprintf (buf, sizeof (buf), "DELETE %s", mbox);
if (imap_exec ((IMAP_DATA*) idata, buf, 0) != 0)
{
/* capabilities may have changed */
imap_exec (idata, "CAPABILITY", IMAP_CMD_QUEUE);
+ /* enable RFC6855, if the server supports that */
+ if (mutt_bit_isset (idata->capabilities, ENABLE))
+ imap_exec (idata, "ENABLE UTF8=ACCEPT", IMAP_CMD_QUEUE);
/* get root delimiter, '/' as default */
idata->delim = '/';
imap_exec (idata, "LIST \"\" \"\"", IMAP_CMD_QUEUE);
idata->newMailCount = 0;
mutt_message (_("Selecting %s..."), idata->mailbox);
- imap_munge_mbox_name (buf, sizeof(buf), idata->mailbox);
+ imap_munge_mbox_name (idata, buf, sizeof(buf), idata->mailbox);
/* pipeline ACL test */
if (mutt_bit_isset (idata->capabilities, ACL))
if (!lastdata)
lastdata = idata;
- imap_munge_mbox_name (munged, sizeof (munged), name);
+ imap_munge_mbox_name (idata, munged, sizeof (munged), name);
snprintf (command, sizeof (command),
"STATUS %s (UIDNEXT UIDVALIDITY UNSEEN RECENT)", munged);
else if (mutt_bit_isset(idata->capabilities,IMAP4REV1) ||
mutt_bit_isset(idata->capabilities,STATUS))
{
- imap_munge_mbox_name (mbox, sizeof(mbox), buf);
+ imap_munge_mbox_name (idata, mbox, sizeof(mbox), buf);
snprintf (buf, sizeof (buf), "STATUS %s (%s)", mbox, "MESSAGES");
- imap_unmunge_mbox_name (mbox);
+ imap_unmunge_mbox_name (idata, mbox);
}
else
/* Server does not support STATUS, and this is not the current mailbox.
mutt_message (_("Subscribing to %s..."), buf);
else
mutt_message (_("Unsubscribing from %s..."), buf);
- imap_munge_mbox_name (mbox, sizeof(mbox), buf);
+ imap_munge_mbox_name (idata, mbox, sizeof(mbox), buf);
snprintf (buf, sizeof (buf), "%sSUBSCRIBE %s", subscribe ? "" : "UN", mbox);
if (imap_exec (idata, buf, 0) < 0)
goto fail;
- imap_unmunge_mbox_name(mx.mbox);
+ imap_unmunge_mbox_name(idata, mx.mbox);
if (subscribe)
mutt_message (_("Subscribed to %s"), mx.mbox);
else
LOGINDISABLED, /* LOGINDISABLED */
IDLE, /* RFC 2177: IDLE */
SASL_IR, /* SASL initial response draft */
+ ENABLE, /* RFC 5161 */
CAPMAX
};
typedef struct
{
char* name;
-
+
char delim;
/* if we end up storing a lot of these we could turn this into a bitfield */
unsigned char noselect;
char* buf;
unsigned int blen;
+ /* If nonzero, we can send UTF-8, and the server will use UTF8 rather
+ * than mUTF7 */
+ int unicode;
+
/* if set, the response parser will store results for complicated commands
* here. */
IMAP_COMMAND_TYPE cmdtype;
void imap_qualify_path (char *dest, size_t len, IMAP_MBOX *mx, char* path);
void imap_quote_string (char* dest, size_t slen, const char* src);
void imap_unquote_string (char* s);
-void imap_munge_mbox_name (char *dest, size_t dlen, const char *src);
-void imap_unmunge_mbox_name (char *s);
+void imap_munge_mbox_name (IMAP_DATA *idata, char *dest, size_t dlen, const char *src);
+void imap_unmunge_mbox_name (IMAP_DATA *idata, char *s);
int imap_wordcasecmp(const char *a, const char *b);
/* utf7.c */
-void imap_utf7_encode (char **s);
-void imap_utf7_decode (char **s);
+void imap_utf_encode (IMAP_DATA *idata, char **s);
+void imap_utf_decode (IMAP_DATA *idata, char **s);
#if USE_HCACHE
/* typedef size_t (*hcache_keylen_t)(const char* fn); */
mutt_progress_init (&progressbar, _("Uploading message..."),
M_PROGRESS_SIZE, NetInc, len);
- imap_munge_mbox_name (mbox, sizeof (mbox), mailbox);
+ imap_munge_mbox_name (idata, mbox, sizeof (mbox), mailbox);
imap_make_date (internaldate, msg->received);
imap_flags[0] = imap_flags[1] = 0;
imap_fix_path (idata, mx.mbox, mbox, sizeof (mbox));
if (!*mbox)
strfcpy (mbox, "INBOX", sizeof (mbox));
- imap_munge_mbox_name (mmbox, sizeof (mmbox), mbox);
+ imap_munge_mbox_name (idata, mmbox, sizeof (mmbox), mbox);
/* loop in case of TRYCREATE */
do
return 0;
}
-void imap_utf7_encode (char **s)
+void imap_utf_encode (IMAP_DATA *idata, char **s)
{
if (Charset)
{
char *t = safe_strdup (*s);
- if (!mutt_convert_string (&t, Charset, "utf-8", 0))
+ if (t && !mutt_convert_string (&t, Charset, "utf-8", 0))
{
- char *u7 = utf8_to_utf7 (t, strlen (t), NULL, 0);
FREE (s); /* __FREE_CHECKED__ */
- *s = u7;
+ if (idata->unicode)
+ *s = safe_strdup (t);
+ else
+ *s = utf8_to_utf7 (t, strlen (t), NULL, 0);
}
FREE (&t);
}
}
-void imap_utf7_decode (char **s)
+void imap_utf_decode (IMAP_DATA *idata, char **s)
{
+ char *t;
+
if (Charset)
{
- char *t = utf7_to_utf8 (*s, strlen (*s), 0, 0);
+ if (idata->unicode)
+ t = safe_strdup (*s);
+ else
+ t = utf7_to_utf8 (*s, strlen (*s), 0, 0);
+
if (t && !mutt_convert_string (&t, "utf-8", Charset, 0))
{
FREE (s); /* __FREE_CHECKED__ */
*s = t;
}
+ else
+ FREE (&t);
}
}
*d = '\0';
}
+
/*
* Quoting and UTF-7 conversion
*/
-void imap_munge_mbox_name (char *dest, size_t dlen, const char *src)
+void imap_munge_mbox_name (IMAP_DATA *idata, char *dest, size_t dlen, const char *src)
{
char *buf;
buf = safe_strdup (src);
- imap_utf7_encode (&buf);
+ imap_utf_encode (idata, &buf);
imap_quote_string (dest, dlen, buf);
FREE (&buf);
}
-void imap_unmunge_mbox_name (char *s)
+void imap_unmunge_mbox_name (IMAP_DATA *idata, char *s)
{
char *buf;
buf = safe_strdup (s);
if (buf)
{
- imap_utf7_decode (&buf);
+ imap_utf_decode (idata, &buf);
strncpy (s, buf, strlen (s));
}