summaryrefslogtreecommitdiff
path: root/imap4d/copy.c
diff options
context:
space:
mode:
Diffstat (limited to 'imap4d/copy.c')
-rw-r--r--imap4d/copy.c54
1 files changed, 39 insertions, 15 deletions
diff --git a/imap4d/copy.c b/imap4d/copy.c
index 2c688921d..56e9fc90a 100644
--- a/imap4d/copy.c
+++ b/imap4d/copy.c
@@ -21,34 +21,57 @@
* copy messages in argv[2] to mailbox in argv[3]
*/
-/* FIXME if the mailbox is the one selecte we should send notif. */
int
imap4d_copy (struct imap4d_command *command, char *arg)
{
+ int rc;
+ char buffer[64];
+
+ if (! (command->states & state))
+ return util_finish (command, RESP_BAD, "Wrong state");
+
+ rc = imap4d_copy0 (arg, 0, buffer, sizeof buffer);
+ if (rc == RESP_NONE)
+ {
+ /* Reset the state ourself. */
+ int new_state = (rc == RESP_OK) ? command->success : command->failure;
+ if (new_state != STATE_NONE)
+ state = new_state;
+ return util_send ("%s %s\r\n", command->tag, buffer);
+ }
+ return util_finish (command, rc, buffer);
+}
+
+int
+imap4d_copy0 (char *arg, int isuid, char *resp, size_t resplen)
+{
int status;
char *msgset;
char *name;
char *mailbox_name;
const char *delim = "/";
char *sp = NULL;
- int *set = NULL;
+ size_t *set = NULL;
size_t n = 0;
mailbox_t cmbox = NULL;
- if (! (command->states & state))
- return util_finish (command, RESP_BAD, "Wrong state");
-
msgset = util_getword (arg, &sp);
name = util_getword (NULL, &sp);
util_unquote (&name);
if (!msgset || !name || *name == '\0')
- return util_finish (command, RESP_BAD, "Too few args");
+ {
+ snprintf (resp, resplen, "Too few args");
+ return RESP_BAD;
+ }
/* Get the message numbers in set[]. */
- status = util_msgset (msgset, &set, &n, 0);
+ status = util_msgset (msgset, &set, &n, isuid);
if (status != 0)
- return util_finish (command, RESP_BAD, "Bogus number set");
+ {
+ snprintf (resp, resplen, "Bogus number set");
+ return RESP_BAD;
+ }
if (strcasecmp (name, "INBOX") == 0)
{
@@ -71,7 +94,8 @@ imap4d_copy (struct imap4d_command *command, char *arg)
for (i = 0; i < n; i++)
{
message_t msg = NULL;
- mailbox_get_message (mbox, set[i], &msg);
+ size_t msgno = (isuid) ? uid_to_msgno (set[i]) : set[i];
+ mailbox_get_message (mbox, msgno, &msg);
mailbox_append_message (cmbox, msg);
}
mailbox_close (cmbox);
@@ -82,16 +106,16 @@ imap4d_copy (struct imap4d_command *command, char *arg)
free (mailbox_name);
if (status == 0)
- return util_finish (command, RESP_OK, "Completed");
-
- /* Since we do not call util_finish, reset the state ourself. */
- if (command->failure != STATE_NONE)
- state = command->failure;
+ {
+ snprintf (resp, resplen, "Completed");
+ return RESP_OK;
+ }
/* Unless it is certain that the destination mailbix can not be created,
the server MUST send the response code "[TRYCREATE]" as the prefix
of the text of the tagged NO response. This gives a hint to the
client that it can attempt a CREATE command and retry the copy if
the CREATE is successful. */
- return util_send ("%s NO [TRYCREATE] failed\r\n", command->tag);
+ snprintf (resp, resplen, "NO [TRYCREATE] failed");
+ return RESP_NONE;
}

Return to:

Send suggestions and report system problems to the System administrator.