NeoMutt  2024-12-12-14-g7b49f7
Teaching an old dog new tricks
DOXYGEN
Loading...
Searching...
No Matches
SMTP Authentication API

Authenticate an SMTP connection. More...

Functions

static int smtp_auth_oauth (struct SmtpAccountData *adata, const char *method)
 Authenticate an SMTP connection using OAUTHBEARER - Implements SmtpAuth::authenticate() -.
 
static int smtp_auth_xoauth2 (struct SmtpAccountData *adata, const char *method)
 Authenticate an SMTP connection using XOAUTH2 - Implements SmtpAuth::authenticate() -.
 
static int smtp_auth_plain (struct SmtpAccountData *adata, const char *method)
 Authenticate using plain text - Implements SmtpAuth::authenticate() -.
 
static int smtp_auth_login (struct SmtpAccountData *adata, const char *method)
 Authenticate using plain text - Implements SmtpAuth::authenticate() -.
 

Detailed Description

Authenticate an SMTP connection.

Parameters
adataSmtp Account data
methodUse this named method, or any available method if NULL
Return values
numResult, e.g. SMTP_AUTH_SUCCESS

Function Documentation

◆ smtp_auth_oauth()

static int smtp_auth_oauth ( struct SmtpAccountData adata,
const char *  method 
)
static

Authenticate an SMTP connection using OAUTHBEARER - Implements SmtpAuth::authenticate() -.

Parameters
adataSMTP Account data
methodAuthentication method (not used)
Return values
numResult, e.g. SMTP_AUTH_SUCCESS

Definition at line 770 of file smtp.c.

771{
772 return smtp_auth_oauth_xoauth2(adata, method, false);
773}
static int smtp_auth_oauth_xoauth2(struct SmtpAccountData *adata, const char *method, bool xoauth2)
Authenticate an SMTP connection using OAUTHBEARER/XOAUTH2.
Definition: smtp.c:732
+ Here is the call graph for this function:

◆ smtp_auth_xoauth2()

static int smtp_auth_xoauth2 ( struct SmtpAccountData adata,
const char *  method 
)
static

Authenticate an SMTP connection using XOAUTH2 - Implements SmtpAuth::authenticate() -.

Parameters
adataSMTP Account data
methodAuthentication method (not used)
Return values
numResult, e.g. SMTP_AUTH_SUCCESS

Definition at line 781 of file smtp.c.

782{
783 return smtp_auth_oauth_xoauth2(adata, method, true);
784}
+ Here is the call graph for this function:

◆ smtp_auth_plain()

static int smtp_auth_plain ( struct SmtpAccountData adata,
const char *  method 
)
static

Authenticate using plain text - Implements SmtpAuth::authenticate() -.

Parameters
adataSMTP Account data
methodAuthentication method (not used)
Return values
0Success
<0Error, e.g. SMTP_AUTH_FAIL
Note
method is "PLAIN"

Definition at line 795 of file smtp.c.

796{
797 struct Buffer *buf = NULL;
798 struct ConnAccount *cac = &adata->conn->account;
799 int rc = -1;
800
801 /* Get username and password. Bail out of any can't be retrieved. */
802 if ((mutt_account_getuser(cac) < 0) || (mutt_account_getpass(cac) < 0))
803 goto error;
804
805 /* Build the initial client response. */
806 buf = buf_pool_get();
807 mutt_sasl_plain_msg(buf, "AUTH PLAIN", cac->user, cac->user, cac->pass);
808 buf_add_printf(buf, "\r\n");
809
810 /* Send request, receive response (with a check for OK code). */
811 if ((mutt_socket_send(adata->conn, buf_string(buf)) < 0) || smtp_get_resp(adata))
812 goto error;
813
814 rc = 0; // Auth was successful
815
816error:
817 if (rc != 0)
818 {
819 // L10N: %s is the method name, e.g. Anonymous, CRAM-MD5, GSSAPI, SASL
820 mutt_error(_("%s authentication failed"), "SASL");
821 }
822 buf_pool_release(&buf);
823 return rc;
824}
int buf_add_printf(struct Buffer *buf, const char *fmt,...)
Format a string appending a Buffer.
Definition: buffer.c:204
static const char * buf_string(const struct Buffer *buf)
Convert a buffer to a const char * "string".
Definition: buffer.h:96
int mutt_account_getpass(struct ConnAccount *cac)
Fetch password into ConnAccount, if necessary.
Definition: connaccount.c:130
int mutt_account_getuser(struct ConnAccount *cac)
Retrieve username into ConnAccount, if necessary.
Definition: connaccount.c:51
#define mutt_error(...)
Definition: logging2.h:92
#define _(a)
Definition: message.h:28
struct Buffer * buf_pool_get(void)
Get a Buffer from the pool.
Definition: pool.c:82
void buf_pool_release(struct Buffer **ptr)
Return a Buffer to the pool.
Definition: pool.c:96
size_t mutt_sasl_plain_msg(struct Buffer *buf, const char *cmd, const char *authz, const char *user, const char *pass)
Construct a base64 encoded SASL PLAIN message.
Definition: sasl_plain.c:50
static int smtp_get_resp(struct SmtpAccountData *adata)
Read a command response from the SMTP server.
Definition: smtp.c:140
#define mutt_socket_send(conn, buf)
Definition: socket.h:57
String manipulation buffer.
Definition: buffer.h:36
Login details for a remote server.
Definition: connaccount.h:53
char user[128]
Username.
Definition: connaccount.h:56
char pass[256]
Password.
Definition: connaccount.h:57
struct ConnAccount account
Account details: username, password, etc.
Definition: connection.h:49
struct Connection * conn
Server Connection.
Definition: smtp.c:99
+ Here is the call graph for this function:

◆ smtp_auth_login()

static int smtp_auth_login ( struct SmtpAccountData adata,
const char *  method 
)
static

Authenticate using plain text - Implements SmtpAuth::authenticate() -.

Parameters
adataSMTP Account data
methodAuthentication method (not used)
Return values
0Success
<0Error, e.g. SMTP_AUTH_FAIL
Note
method is "LOGIN"

Definition at line 835 of file smtp.c.

836{
837 char b64[1024] = { 0 };
838 char buf[1026] = { 0 };
839
840 /* Get username and password. Bail out of any can't be retrieved. */
841 if ((mutt_account_getuser(&adata->conn->account) < 0) ||
842 (mutt_account_getpass(&adata->conn->account) < 0))
843 {
844 goto error;
845 }
846
847 /* Send the AUTH LOGIN request. */
848 if (mutt_socket_send(adata->conn, "AUTH LOGIN\r\n") < 0)
849 {
850 goto error;
851 }
852
853 /* Read the 334 VXNlcm5hbWU6 challenge ("Username:" base64-encoded) */
854 int rc = mutt_socket_readln_d(buf, sizeof(buf), adata->conn, MUTT_SOCK_LOG_FULL);
855 if ((rc < 0) || !mutt_str_equal(buf, "334 VXNlcm5hbWU6"))
856 {
857 goto error;
858 }
859
860 /* Send the username */
861 size_t len = snprintf(buf, sizeof(buf), "%s", adata->conn->account.user);
862 mutt_b64_encode(buf, len, b64, sizeof(b64));
863 snprintf(buf, sizeof(buf), "%s\r\n", b64);
864 if (mutt_socket_send(adata->conn, buf) < 0)
865 {
866 goto error;
867 }
868
869 /* Read the 334 UGFzc3dvcmQ6 challenge ("Password:" base64-encoded) */
870 rc = mutt_socket_readln_d(buf, sizeof(buf), adata->conn, MUTT_SOCK_LOG_FULL);
871 if ((rc < 0) || !mutt_str_equal(buf, "334 UGFzc3dvcmQ6"))
872 {
873 goto error;
874 }
875
876 /* Send the password */
877 len = snprintf(buf, sizeof(buf), "%s", adata->conn->account.pass);
878 mutt_b64_encode(buf, len, b64, sizeof(b64));
879 snprintf(buf, sizeof(buf), "%s\r\n", b64);
880 if (mutt_socket_send(adata->conn, buf) < 0)
881 {
882 goto error;
883 }
884
885 /* Check the final response */
886 if (smtp_get_resp(adata) < 0)
887 {
888 goto error;
889 }
890
891 /* If we got here, auth was successful. */
892 return 0;
893
894error:
895 // L10N: %s is the method name, e.g. Anonymous, CRAM-MD5, GSSAPI, SASL
896 mutt_error(_("%s authentication failed"), "LOGIN");
897 return -1;
898}
size_t mutt_b64_encode(const char *in, size_t inlen, char *out, size_t outlen)
Convert raw bytes to null-terminated base64 string.
Definition: base64.c:87
bool mutt_str_equal(const char *a, const char *b)
Compare two strings.
Definition: string.c:660
int mutt_socket_readln_d(char *buf, size_t buflen, struct Connection *conn, int dbg)
Read a line from a socket.
Definition: socket.c:238
#define MUTT_SOCK_LOG_FULL
Definition: socket.h:54
+ Here is the call graph for this function: