1 /* GNU Mailutils -- a suite of utilities for electronic mail
2    Copyright (C) 2011-2021 Free Software Foundation, Inc.
3 
4    This library is free software; you can redistribute it and/or
5    modify it under the terms of the GNU Lesser General Public
6    License as published by the Free Software Foundation; either
7    version 3 of the License, or (at your option) any later version.
8 
9    This library is distributed in the hope that it will be useful,
10    but WITHOUT ANY WARRANTY; without even the implied warranty of
11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12    Lesser General Public License for more details.
13 
14    You should have received a copy of the GNU Lesser General
15    Public License along with this library.  If not, see
16    <http://www.gnu.org/licenses/>. */
17 
18 #ifdef HAVE_CONFIG_H
19 # include <config.h>
20 #endif
21 
22 #include <stdlib.h>
23 #include <mailutils/errno.h>
24 #include <mailutils/imap.h>
25 #include <mailutils/sys/imap.h>
26 
27 int
mu_imap_gencom(mu_imap_t imap,struct imap_command * cmd)28 mu_imap_gencom (mu_imap_t imap, struct imap_command *cmd)
29 {
30   int status;
31 
32   if (imap == NULL || !cmd || cmd->argc < 1)
33     return EINVAL;
34   if (!imap->io)
35     return MU_ERR_NO_TRANSPORT;
36   if (imap->session_state < cmd->session_state)
37     return MU_ERR_SEQ;
38 
39   if (cmd->capa)
40     {
41       status = mu_imap_capability_test (imap, cmd->capa, NULL);
42       switch (status)
43 	{
44 	case 0:
45 	  break;
46 
47 	case MU_ERR_NOENT:
48 	  return ENOSYS;
49 
50 	default:
51 	  return status;
52 	}
53     }
54 
55   if (imap->client_state == MU_IMAP_CLIENT_READY)
56     {
57       status = _mu_imap_tag_next (imap);
58       MU_IMAP_CHECK_EAGAIN (imap, status);
59       status = mu_imapio_send_command_v (imap->io, imap->tag_str,
60 					 cmd->msgset,
61 					 cmd->argc, cmd->argv, cmd->extra);
62       MU_IMAP_CHECK_ERROR (imap, status);
63       MU_IMAP_FCLR (imap, MU_IMAP_RESP);
64       imap->client_state = cmd->rx_state;
65     }
66 
67   if (imap->client_state == cmd->rx_state)
68     {
69       status = _mu_imap_response (imap, cmd->untagged_handler,
70 				  cmd->untagged_handler_data);
71       MU_IMAP_CHECK_EAGAIN (imap, status);
72       if (cmd->tagged_handler)
73 	  cmd->tagged_handler (imap);
74       switch (imap->response)
75 	{
76 	case MU_IMAP_OK:
77 	  status = 0;
78 	  break;
79 
80 	case MU_IMAP_NO:
81 	  status = MU_ERR_FAILURE;
82 	  break;
83 
84 	case MU_IMAP_BAD:
85 	  status = MU_ERR_BADREPLY;
86 	  break;
87 	}
88       imap->client_state = MU_IMAP_CLIENT_READY;
89     }
90   else
91     status = EINPROGRESS;
92 
93   return status;
94 }
95 
96