smtp-client icon indicating copy to clipboard operation
smtp-client copied to clipboard

Incorrect SMTPUTF8 support

Open kingsamchen opened this issue 1 year ago • 0 comments

The behavior of SMTPUTF8 support of the library isn't compliant with RFC 6531.

If one of recipients uses i18n email address, the smtp connection will fail.

sample code (based on example_sample.c):

#include <stdio.h>
#include "smtp.h"
#define MAIL_SERVER              "localhost"
#define MAIL_PORT                "25"
#define MAIL_CONNECTION_SECURITY SMTP_SECURITY_NONE
#define MAIL_FLAGS               (SMTP_DEBUG         | \
                                  SMTP_NO_CERT_VERIFY) /* Do not verify cert. */
#define MAIL_CAFILE              NULL
#define MAIL_AUTH                SMTP_AUTH_PLAIN
#define MAIL_USER                "[email protected]"
#define MAIL_PASS                "password"
#define MAIL_FROM                "[email protected]"
#define MAIL_FROM_NAME           "Kingsley"
#define MAIL_SUBJECT             "Test for SMTPUTF8"
#define MAIL_BODY                "This is a test text."
#define MAIL_TO                  "绲斤铐@example.com"
#define MAIL_TO_NAME             "Admin"
int main(void)
{
  struct smtp *smtp;
  int rc;
  rc = smtp_open(MAIL_SERVER,
                 MAIL_PORT,
                 MAIL_CONNECTION_SECURITY,
                 MAIL_FLAGS,
                 MAIL_CAFILE,
                 &smtp);
  rc = smtp_address_add(smtp,
                        SMTP_ADDRESS_FROM,
                        MAIL_FROM,
                        MAIL_FROM_NAME);
  rc = smtp_address_add(smtp,
                        SMTP_ADDRESS_TO,
                        MAIL_TO,
                        MAIL_TO_NAME);
  rc = smtp_header_add(smtp,
                       "Subject",
                       MAIL_SUBJECT);
  rc = smtp_mail(smtp,
                 MAIL_BODY);
  rc = smtp_close(smtp);
  if(rc != SMTP_STATUS_OK){
    fprintf(stderr, "smtp failed: %s\n", smtp_status_code_errstr(rc));
    return 1;
  }
  return 0;
}

Postfix v3.6 is running background and if we ran the test, we have following smtp logs

[smtp Server]: 220 temporary.example.com ESMTP Postfix
[smtp Client]: EHLO smtp
[smtp Server]: 250-temporary.example.com
[smtp Server]: 250-PIPELINING
[smtp Server]: 250-SIZE 10240000
[smtp Server]: 250-VRFY
[smtp Server]: 250-ETRN
[smtp Server]: 250-STARTTLS
[smtp Server]: 250-ENHANCEDSTATUSCODES
[smtp Server]: 250-8BITMIME
[smtp Server]: 250-DSN
[smtp Server]: 250-SMTPUTF8
[smtp Server]: 250 CHUNKING
[smtp Client]: MAIL FROM:<[email protected]>
[smtp Server]: 250 2.1.0 Ok
[smtp Client]: RCPT TO:<绲斤铐@example.com> SMTPUTF8            <== (1)
[smtp Server]: 555 5.5.4 Unsupported option: SMTPUTF8          <== (2)
[smtp Client]: DATA
[smtp Server]: 554 5.5.1 Error: no valid recipients
[smtp Client]: QUIT
smtp failed: SMTP server sent back an unexpected status code
  1. RFC 6531 allows SMTPUTF8 option only in command MAIL, VRFY and EXPN, see https://datatracker.ietf.org/doc/html/rfc6531#section-3.1
  2. Postfix supports SMTPUTF8 option in MAIL and VRFY commands https://www.postfix.org/SMTPUTF8_README.html

Neither of them allows using the option in RCPT TO; thats why the Postfix would complain the unsupported option in response.


I checked the implementation and found the root cause of this issue is in the function smtp_mail_envelope_header(): the lib should append SMTPUTF8 only in MAIL FROM.

Maybe we need to maintain a boolean to indicate if there is a need to use UTF-8 support because any non-ascii address used in sender or recipients would require UTF-8 support.

kingsamchen avatar Oct 30 '22 09:10 kingsamchen