Commit f8c8c76d authored by Jiri Hruska's avatar Jiri Hruska Committed by Steve Holme
Browse files

imap: Implemented APPEND final processing

The APPEND operation needs to be performed in several steps:
  1) We send "<tag> APPEND <mailbox> <flags> {<size>}\r\n"
  2) Server responds with continuation respose "+ ...\r\n"
  3) We start the transfer and send <size> bytes of data
  4) Only now we end the request command line by sending "\r\n"
  5) Server responds with "<tag> OK ...\r\n"

This commit performs steps 4 and 5, in the DONE phase, as more
processing is required after the transfer.
parent 90b7d0ea
Loading
Loading
Loading
Loading
+35 −2
Original line number Diff line number Diff line
@@ -1410,6 +1410,26 @@ static CURLcode imap_state_append_resp(struct connectdata *conn,
  }
}

/* For final APPEND responses performed after the upload */
static CURLcode imap_state_append_final_resp(struct connectdata *conn,
                                             int imapcode,
                                             imapstate instate)
{
  CURLcode result = CURLE_OK;

  (void)instate; /* No use for this yet */

  /* Final response, stop and return the final status */
  if(imapcode == 'O')
    result = CURLE_OK;
  else
    result = CURLE_UPLOAD_FAILED;

  state(conn, IMAP_STOP);

  return result;
}

static CURLcode imap_statemach_act(struct connectdata *conn)
{
  CURLcode result = CURLE_OK;
@@ -1516,6 +1536,10 @@ static CURLcode imap_statemach_act(struct connectdata *conn)
      result = imap_state_append_resp(conn, imapcode, imapc->state);
      break;

    case IMAP_APPEND_FINAL:
      result = imap_state_append_final_resp(conn, imapcode, imapc->state);
      break;

    case IMAP_LOGOUT:
      /* fallthrough, just stop! */
    default:
@@ -1660,7 +1684,15 @@ static CURLcode imap_done(struct connectdata *conn, CURLcode status,
    result = status;         /* use the already set error code */
  }
  else if(!data->set.connect_only) {
    /* Handle responses after FETCH or APPEND transfer has finished */
    if(!data->set.upload)
      state(conn, IMAP_FETCH_FINAL);
    else {
      /* End the APPEND command first by sending an empty line */
      result = Curl_pp_sendf(&conn->proto.imapc.pp, "");
      if(!result)
        state(conn, IMAP_APPEND_FINAL);
    }

    /* Run the state-machine

@@ -1669,6 +1701,7 @@ static CURLcode imap_done(struct connectdata *conn, CURLcode status,
       non-blocking DONE operations, not in the multi state machine and with
       Curl_done() invokes on several places in the code!
    */
    if(!result)
      result = imap_block_statemach(conn);
  }