Add SMTP TLS and Authentication using libcurl#2195
Conversation
Enable authenticated and TLS SMTP for ossec-maild when built with USE_CURL=yes (off by default). Uses libcurl for SMTP AUTH (PLAIN/LOGIN) and TLS/STARTTLS; credentials and TLS are validated and sanitized. Security hardening: header/envelope CR/LF sanitization, hostname validation for smtp_server, timeouts, mandatory TLS when AUTH is on, post-parse credential validation, and secure clearing of password in config and at exit. CA bundle and chroot ossec-maild runs inside a chroot (e.g. /var/ossec). libcurl uses CURLOPT_SSL_VERIFYPEER=1 and by default looks for the system CA bundle (e.g. /etc/ssl/certs/ca-certificates.crt). After chroot, that path is not visible, so TLS verification fails (CURLE_PEER_FAILED_VERIFICATION) and mail is dropped unless the CA bundle is available inside the chroot. Installation (or the admin) must copy or symlink the system CA bundle into the chroot (e.g. <chroot>/etc/ssl/certs/ca-certificates.crt) and either set CURLOPT_CAINFO to that path in code or ensure the default path resolves inside the chroot. Do not disable VERIFYPEER. Original idea and initial implementation from alexbartlow via Allow TLS Email sends as a compile-time option ossec#1360 Credit: alexbartlow (PR ossec#1360) Signed-off-by: Scott R. Shinn <scott@atomicorp.com>
There was a problem hiding this comment.
Pull request overview
Adds an optional libcurl-based SMTP delivery path to ossec-maild (enabled only when building with USE_CURL=yes) to support SMTP AUTH and TLS/STARTTLS while running inside the project’s chrooted environment.
Changes:
- Introduces
USE_CURLbuild flag (USE_SMTP_CURL) and a new libcurl-based SMTP sender implementation. - Extends mail/global config parsing with
auth_smtp,secure_smtp,smtp_user,smtp_password, andsmtp_port, plus pre-resolution support for chroot. - Adds a new GitHub Actions multi-platform Make build workflow (Rocky + Windows cross-compile).
Reviewed changes
Copilot reviewed 11 out of 11 changed files in this pull request and generated 7 comments.
Show a summary per file
| File | Description |
|---|---|
| src/os_maild/sendmail.c | Compiles out legacy SMTP/local sendmail implementation when USE_SMTP_CURL is set. |
| src/os_maild/maild.c | Adds SMTP secret clearing and pre-chroot hostname resolution for curl mode. |
| src/os_maild/curlmail.c | New libcurl-based SMTP sender (TLS + AUTH) behind USE_SMTP_CURL. |
| src/os_maild/config.c | Initializes new mail config fields and adds curl-gated validation for AUTH. |
| src/monitord/main.c | Adjusts how monitord reads/validates smtp_server when USE_SMTP_CURL is defined. |
| src/config/mail-config.h | Adds SMTP TLS/AUTH-related fields to MailConfig. |
| src/config/global-config.h | Adds authsmtp/securesmtp flags to global config struct. |
| src/config/global-config.c | Parses new SMTP TLS/AUTH-related XML elements and pre-resolves SMTP host in curl mode. |
| src/Makefile | Adds USE_CURL toggle to enable USE_SMTP_CURL and link with -lcurl. |
| .github/workflows/make-multi-platform.yml | New CI workflow for Rocky Linux container builds + Windows cross-compile. |
| .github/workflows/README.md | Documents the workflows. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
You can also share your feedback on Copilot code review. Take the survey.
Signed-off-by: Scott R. Shinn <scott@atomicorp.com>
There was a problem hiding this comment.
Pull request overview
Adds an optional (compile-time) libcurl-based SMTP delivery path for ossec-maild, enabling SMTP AUTH and TLS/STARTTLS when built with USE_CURL=yes, along with related config parsing and build/CI wiring.
Changes:
- Add new libcurl SMTP sender (
OS_Sendmail) supporting AUTH + TLS/STARTTLS and hostname/IP pre-resolution for chrooted operation. - Extend global/mail config parsing with
auth_smtp,secure_smtp,smtp_user,smtp_password, andsmtp_port. - Add
USE_CURLbuild switch (definesUSE_SMTP_CURL, links-lcurl) and introduce a multi-platform GitHub Actions build workflow.
Reviewed changes
Copilot reviewed 11 out of 11 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| src/os_maild/sendmail.c | Excludes the legacy sendmail/plain SMTP implementation when USE_SMTP_CURL is enabled. |
| src/os_maild/maild.c | Initializes/cleans up libcurl and pre-resolves SMTP hostnames before chroot; clears credentials in child. |
| src/os_maild/curlmail.c | New libcurl-based SMTP implementation (TLS/AUTH, CRLF sanitization, timeouts, CURLOPT_RESOLVE). |
| src/os_maild/config.c | Initializes new MailConfig fields and enforces option validity depending on USE_SMTP_CURL. |
| src/monitord/main.c | Adjusts SMTP server validation/storage to preserve hostname for libcurl builds. |
| src/config/mail-config.h | Extends MailConfig with curl/TLS/auth fields and pre-resolved SMTP IP. |
| src/config/global-config.h | Extends global _Config with auth/TLS flags. |
| src/config/global-config.c | Parses new SMTP auth/TLS options; pre-resolves SMTP host for chroot when curl is enabled. |
| src/Makefile | Adds USE_CURL switch to enable USE_SMTP_CURL and link -lcurl. |
| .github/workflows/make-multi-platform.yml | New CI workflow to build on Rocky Linux container + cross-compile Windows agent. |
| .github/workflows/README.md | Documents the workflows. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
You can also share your feedback on Copilot code review. Take the survey.
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Signed-off-by: Scott R. Shinn <scott@atomicorp.com>
There was a problem hiding this comment.
Pull request overview
Adds an optional libcurl-backed SMTP implementation for ossec-maild (enabled with USE_CURL=yes) to support SMTP AUTH and TLS/STARTTLS, plus related config wiring and build/CI updates.
Changes:
- Introduces
src/os_maild/curlmail.c(libcurl SMTP sender) and gates the legacysendmail.cimplementation behind#ifndef USE_SMTP_CURL. - Extends global/mail configuration parsing and structs for
auth_smtp,secure_smtp,smtp_user,smtp_password, andsmtp_port, including pre-resolution storage for chrooted operation. - Adds
USE_CURLbuild flag support and a new multi-platform GitHub Actions build workflow.
Reviewed changes
Copilot reviewed 12 out of 12 changed files in this pull request and generated 4 comments.
Show a summary per file
| File | Description |
|---|---|
| src/os_maild/sendmail.c | Wraps legacy SMTP/sendmail implementation behind !USE_SMTP_CURL. |
| src/os_maild/maild.c | Initializes libcurl globally (curl build) and pre-resolves SMTP hostname before chroot. |
| src/os_maild/curlmail.c | New libcurl SMTP sender with TLS/AUTH support and sanitization/error logging. |
| src/os_maild/config.c | Initializes new MailConfig fields; enforces curl-build requirement for AUTH/TLS options. |
| src/monitord/main.c | Adjusts how smtp_server is validated/stored when USE_SMTP_CURL is enabled. |
| src/config/mail-config.h | Adds new SMTP AUTH/TLS fields and smtpserver_resolved to MailConfig. |
| src/config/global-config.h | Adds global authsmtp/securesmtp flags to the global config struct. |
| src/config/global-config.c | Parses new SMTP AUTH/TLS XML fields and pre-resolves SMTP host when curl is enabled. |
| src/Makefile | Adds USE_CURL option to define USE_SMTP_CURL and link -lcurl. |
| README.md | Documents libcurl SMTP error logging behavior at a high level. |
| .github/workflows/make-multi-platform.yml | Adds a new multi-platform build workflow (Rocky + Windows cross-compile). |
| .github/workflows/README.md | Documents the repository’s GitHub Actions workflows. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Monitord has a configurable email report that operates independently of ossec-maild in OS_SendCustomEmail2 - Implement libcurl-based SMTP send path in sendcustomemail.c with support for SMTP AUTH and TLS/SSL (CURLUSESSL_ALL). - Add auth_smtp, secure_smtp, smtp_port, smtp_user, and smtp_pass configuration options to monitord. Signed-off-by: Scott R. Shinn <scott@atomicorp.com>
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 16 out of 16 changed files in this pull request and generated 5 comments.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Signed-off-by: Scott R. Shinn <scott@atomicorp.com>
- monitord main/sendcustomemail and os_maild config updates - Rocky 9 workflow: keep upstream CRB/deps; add USE_CURL matrix + libcurl-devel
Signed-off-by: Scott R. Shinn <scott@atomicorp.com>
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 15 out of 15 changed files in this pull request and generated 7 comments.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| if (!is_valid_smtp_host(smtpserver)) { | ||
| merror("%s: ERROR: Invalid SMTP server '%s' (contains invalid characters).", ARGV0, smtpserver); | ||
| return (0); | ||
| } |
There was a problem hiding this comment.
In the libcurl path, invalid smtpserver currently logs an error but then returns 0 (success) and also skips the cleanup_curl path, leaking curl, body_fp, and header_buf. This should return an error (e.g., OS_INVALID) and go through the normal cleanup path (e.g., set res and goto cleanup_curl).
| if (n2 < 0 || (size_t)n2 >= sizeof(mail_url)) { | ||
| merror("%s: ERROR: SMTP server or URL too long (truncation).", ARGV0); | ||
| return (0); | ||
| } |
There was a problem hiding this comment.
On URL truncation, this path also returns 0 (success) and bypasses cleanup, leaking the libcurl handle / open file / header buffer. Please return an error and route through cleanup_curl (or otherwise free resources) before returning.
| if (mond.reports) { | ||
| mond.smtp_user = OS_GetOneContentforElement(&xml, xml_smtp_user); | ||
| mond.smtp_pass = OS_GetOneContentforElement(&xml, xml_smtp_pass); | ||
|
|
||
| if (mond.authsmtp && (!mond.smtp_user || !mond.smtp_pass)) { | ||
| merror("%s: ERROR: SMTP auth enabled but user/pass missing. Disabling email reports.", ARGV0); | ||
| if (mond.emailfrom) { |
There was a problem hiding this comment.
Even in non-USE_SMTP_CURL builds, this reads and stores smtp_user/smtp_password into mond.*, but the secret-clearing atexit handler is only installed under USE_SMTP_CURL. This can leave credentials resident in memory unnecessarily. Please avoid reading these secrets when curl support is not compiled in (or ensure they are securely cleared regardless).
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Enable authenticated and TLS SMTP for ossec-maild when built with
USE_CURL=yes (off by default). Uses libcurl for SMTP AUTH (PLAIN/LOGIN)
and TLS/STARTTLS; credentials and TLS are validated and sanitized.
Security hardening: header/envelope CR/LF sanitization, hostname
validation for smtp_server, timeouts, mandatory TLS when AUTH is on,
post-parse credential validation, and secure clearing of password
in config and at exit.
CA bundle and chroot
ossec-maild runs inside a chroot (e.g. /var/ossec). libcurl uses
CURLOPT_SSL_VERIFYPEER=1 and by default looks for the system CA bundle
(e.g. /etc/ssl/certs/ca-certificates.crt). After chroot, that path
is not visible, so TLS verification fails (CURLE_PEER_FAILED_VERIFICATION)
and mail is dropped unless the CA bundle is available inside the chroot.
Installation (or the admin) must copy or symlink the system CA bundle
into the chroot (e.g. /etc/ssl/certs/ca-certificates.crt) and
either set CURLOPT_CAINFO to that path in code or ensure the default
path resolves inside the chroot. Do not disable VERIFYPEER.
Original idea and initial implementation from alexbartlow via
Allow TLS Email sends as a compile-time option
#1360
Credit: alexbartlow (PR #1360)