Skip to content

out_syslog: tls: io: Handle dtls protocol on out syslog - #11728

Merged
edsiper merged 13 commits into
masterfrom
cosmo0920-handle-dtls-protocol-on-out_syslog
Jul 29, 2026
Merged

out_syslog: tls: io: Handle dtls protocol on out syslog#11728
edsiper merged 13 commits into
masterfrom
cosmo0920-handle-dtls-protocol-on-out_syslog

Conversation

@cosmo0920

@cosmo0920 cosmo0920 commented Apr 20, 2026

Copy link
Copy Markdown
Contributor

And implemented dtls transport protocol in core.

RSyslog has DTLS capability to handle DTLS transportation protocol which is described in RFC 6012.

DTLS is handled over UDP and transport layer security(TLS).

Currently, when selecting UDP as a transport protocol, there's no TLS support on out_syslog plugin. So, if users wanted to use this plugin with UDP and TLS combination, there's no luck.
We should add a capability to handle this.

Related to #11703.


Enter [N/A] in the box, if an item is not applicable to your change.

Testing
Before we can approve your change; please submit the following in a comment:

  • Example configuration file for the change
  • Debug log output from testing the change
  • Attached Valgrind output that shows no leaks or memory corruption was found

If this is a change to packaging of containers or native binaries then please confirm it works for all targets.

  • Run local packaging test showing all targets (including any new ones) build.
  • Set ok-package-test label to test for all targets (requires maintainer to do).

Documentation

  • Documentation required for this feature

Backporting

  • Backport to latest stable release.

Fluent Bit is licensed under Apache 2.0, by submitting this pull request I understand that this code will be released under the terms of that license.

Summary by CodeRabbit

  • New Features

    • Added UDP and DTLS transport support; syslog output now accepts mode=udp, tcp, tls, dtls. DTLS requires TLS enabled and certificate options apply.
  • Documentation

    • Help text and connection display updated to list dtls:// and include dtls in supported modes; proxy and TCP keepalive now only apply to TCP transports.
  • Behavior

    • Streams are considered secure when TLS or DTLS is used.
  • Tests

    • Added integration tests covering syslog over UDP, TCP, and DTLS.

@coderabbitai

coderabbitai Bot commented Apr 20, 2026

Copy link
Copy Markdown

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Added DTLS-over-UDP transport support across IO, upstream, TLS, and out_syslog: new I/O flags and TLS datagram modes, transport-aware connection/handshake logic, syslog plugin DTLS handling and config/validation, and integration tests for UDP/TCP/DTLS flows. Several related code paths were adjusted for UDP/DTLS.

Changes

Cohort / File(s) Summary
I/O flags & public headers
include/fluent-bit/flb_io.h, include/fluent-bit/flb_upstream.h, include/fluent-bit/tls/flb_tls.h
Added FLB_IO_UDP, FLB_IO_DTLS flags; moved FLB_IO_IPV6 value; added DTLS TLS mode constants (FLB_TLS_*_MODE_DGRAM).
Stream/upstream plumbing
include/fluent-bit/flb_stream.h, src/flb_upstream.c, src/flb_io.c, src/flb_connection.c
Stream security check recognizes DTLS; upstream derives transport (UDP vs TCP) from flags; IO connect/read/write/selects UDP/TCP paths and handles TLS vs DTLS TLS sessions; user-friendly host formatting differentiates dtls://.
OpenSSL DTLS support
src/tls/openssl.c
Create DTLS SSL_CTX for datagram client/server modes; handshake paths adjusted for datagram modes; fail early if OpenSSL lacks DTLS.
out_syslog plugin
plugins/out_syslog/syslog.c, plugins/out_syslog/syslog_conf.c, plugins/out_syslog/syslog_conf.h
Added FLB_SYSLOG_DTLS mode; parse/validate mode=dtls and require tls=on; initialize/destroy DTLS client TLS context and choose IO flags (UDP/DTLS/TLS/TCP); moved context registration and adjusted help text.
Tests (integration)
tests/integration/scenarios/out_syslog/config/...yaml, tests/integration/scenarios/out_syslog/tests/test_out_syslog_001.py
Added UDP/TCP/DTLS integration test configs and a test module with UDP/TCP receivers and an openssl-based DtlsReceiver exercising DTLS end-to-end.
Misc
include/fluent-bit/flb_stream.h (newline), src/flb_connection.c (newline fixes)
Minor file-end newline fixes and small formatting edits.

Sequence Diagram(s)

sequenceDiagram
    autonumber
    participant App as Fluent Bit Plugin (out_syslog)
    participant Up as Upstream Manager
    participant IO as flb_io / Socket Layer
    participant TLS as OpenSSL TLS/DTLS
    participant Receiver as Syslog Server

    App->>Up: create upstream with flags (FLB_IO_UDP / FLB_IO_DTLS / FLB_IO_TLS / FLB_IO_TCP)
    Up->>IO: flb_stream_setup(transport derived from flags)
    App->>IO: connect() (UDP/TCP path selected)
    alt transport == UDP/DTLS
        IO->>IO: use UDP socket (non-blocking / recv timeout)
    else
        IO->>IO: use TCP connect (+proxy if TCP)
    end
    alt TLS or DTLS requested
        IO->>TLS: establish TLS/DTLS session (client mode datagram/tcp as selected)
        TLS-->>IO: handshake complete
    end
    IO->>Receiver: send datagram/stream (DTLS wraps datagram if used)
    Receiver-->>App: response/ACK (captured by test receiver)
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

Suggested reviewers

  • edsiper
  • koleini
  • fujimotos

Poem

"I hopped through sockets, soft and spry,
DTLS seeds in paw and eye.
From udp burrows up I leap,
secure the datagrams while others sleep.
A tiny rabbit's patchwork net—hello, safe packets yet! 🐇"

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 4.88% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title directly addresses the main objective of adding DTLS protocol support to the out_syslog plugin, which is the primary focus of this changeset across core I/O, TLS, and plugin layers.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch cosmo0920-handle-dtls-protocol-on-out_syslog

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
@cosmo0920
cosmo0920 force-pushed the cosmo0920-handle-dtls-protocol-on-out_syslog branch from 4c265e7 to 719fef2 Compare April 20, 2026 08:16
@cosmo0920
cosmo0920 marked this pull request as ready for review April 20, 2026 08:17
@cosmo0920
cosmo0920 requested a review from edsiper as a code owner April 20, 2026 08:17
@cosmo0920 cosmo0920 added this to the Fluent Bit v5.1 milestone Apr 20, 2026
@edsiper

edsiper commented Apr 21, 2026

Copy link
Copy Markdown
Member

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 504b4b2c40

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/flb_io.c
Comment thread plugins/out_syslog/syslog.c Outdated
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
plugins/out_syslog/syslog.c (1)

863-870: ⚠️ Potential issue | 🟠 Major

Treat DTLS as datagram mode when formatting syslog payloads.

FLB_SYSLOG_DTLS now uses datagram transport, but Line 863 still appends a TCP/TLS newline for every non-UDP mode. That changes DTLS wire payloads and can exceed ctx->maxsize by one byte because truncation happens before the newline append.

🐛 Proposed fix
-        if (ctx->parsed_mode != FLB_SYSLOG_UDP) {
+        if (ctx->parsed_mode != FLB_SYSLOG_UDP &&
+            ctx->parsed_mode != FLB_SYSLOG_DTLS) {
             tmp = flb_sds_cat(*s, "\n", 1);
             if (!tmp) {
                 ret_sds = NULL;

Also applies to: 1035-1036

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@plugins/out_syslog/syslog.c` around lines 863 - 870, The code unconditionally
treats non-UDP modes as stream-based when appending a trailing newline to the
syslog payload; update the conditional that checks ctx->parsed_mode (used where
*s is appended with "\n") to treat FLB_SYSLOG_DTLS as a datagram mode (i.e.,
only append the newline when parsed_mode is neither FLB_SYSLOG_UDP nor
FLB_SYSLOG_DTLS). Apply the same change at the other occurrence that appends a
newline (the second block referencing ctx->parsed_mode and appending "\n") so
DTLS payloads are not altered or over-sized.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Outside diff comments:
In `@plugins/out_syslog/syslog.c`:
- Around line 863-870: The code unconditionally treats non-UDP modes as
stream-based when appending a trailing newline to the syslog payload; update the
conditional that checks ctx->parsed_mode (used where *s is appended with "\n")
to treat FLB_SYSLOG_DTLS as a datagram mode (i.e., only append the newline when
parsed_mode is neither FLB_SYSLOG_UDP nor FLB_SYSLOG_DTLS). Apply the same
change at the other occurrence that appends a newline (the second block
referencing ctx->parsed_mode and appending "\n") so DTLS payloads are not
altered or over-sized.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: ff0cf485-40f8-4709-9fd2-dff4d889c32d

📥 Commits

Reviewing files that changed from the base of the PR and between 504b4b2 and 18dc607.

📒 Files selected for processing (2)
  • plugins/out_syslog/syslog.c
  • src/flb_io.c

@cosmo0920

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 18dc607fed

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/tls/openssl.c Outdated
Comment thread tests/integration/scenarios/out_syslog/tests/test_out_syslog_001.py
Signed-off-by: Hiroshi Hatake <hiroshi@chronosphere.io>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/tls/openssl.c (1)

845-858: ⚠️ Potential issue | 🟠 Major

Mirror the OPENSSL_NO_DTLS guard in the OpenSSL ≥ 1.1.0 branch.

The legacy branch at lines 823–837 correctly guards DTLS method calls with #ifndef OPENSSL_NO_DTLS and fails gracefully with an error message when unsupported. The #else branch for OpenSSL ≥ 1.1.0 (lines 845–858) lacks this guard and unconditionally references DTLS_server_method() and DTLS_client_method(). When OpenSSL ≥ 1.1.0 is built with OPENSSL_NO_DTLS, these function symbols are declared but not implemented, causing a linker failure. Apply the same guard here for consistency and build robustness.

🔧 Proposed fix
 `#else`
     if (mode == FLB_TLS_SERVER_MODE) {
         ssl_ctx = SSL_CTX_new(TLS_server_method());
     }
-    else if (mode == FLB_TLS_SERVER_MODE_DGRAM) {
-        ssl_ctx = SSL_CTX_new(DTLS_server_method());
-    }
-    else if (mode == FLB_TLS_CLIENT_MODE_DGRAM) {
-        ssl_ctx = SSL_CTX_new(DTLS_client_method());
-    }
+    else if (mode == FLB_TLS_SERVER_MODE_DGRAM ||
+             mode == FLB_TLS_CLIENT_MODE_DGRAM) {
+#ifndef OPENSSL_NO_DTLS
+        if (mode == FLB_TLS_SERVER_MODE_DGRAM) {
+            ssl_ctx = SSL_CTX_new(DTLS_server_method());
+        }
+        else {
+            ssl_ctx = SSL_CTX_new(DTLS_client_method());
+        }
+#else
+        flb_error("[openssl] DTLS mode requested but this OpenSSL build "
+                  "does not provide DTLS support");
+        return NULL;
+#endif
+    }
     else {
         ssl_ctx = SSL_CTX_new(TLS_client_method());
     }
 `#endif`
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/tls/openssl.c` around lines 845 - 858, The OpenSSL ≥1.1.0 branch
unconditionally calls DTLS_server_method() and DTLS_client_method(), which can
cause linker failures when built with OPENSSL_NO_DTLS; wrap the DTLS-specific
branches (those comparing mode to FLB_TLS_SERVER_MODE_DGRAM and
FLB_TLS_CLIENT_MODE_DGRAM) with the same `#ifndef` OPENSSL_NO_DTLS guard used in
the legacy branch, and in the guarded-else provide the existing graceful
fallback that logs an error and returns when DTLS is unavailable; keep
TLS_server_method()/TLS_client_method() paths unchanged and ensure symbols
SSL_CTX_new, DTLS_server_method, DTLS_client_method, TLS_server_method,
TLS_client_method and the mode constants are referenced exactly as in the diff.
🧹 Nitpick comments (1)
src/tls/openssl.c (1)

823-843: Consider version-negotiating DTLS method for the pre-1.1.0 branch.

DTLSv1_server_method() / DTLSv1_client_method() pin the context to DTLS 1.0 only, while the >=1.1.0 branch uses the version-negotiating DTLS_*_method(). Since DTLS_*_method() is available starting in OpenSSL 1.0.2, you could use it here (with an additional OPENSSL_VERSION_NUMBER check for 1.0.2+) to allow DTLS 1.2. This branch only targets very old OpenSSL releases, so this is optional.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/tls/openssl.c` around lines 823 - 843, The DTLS branch currently uses
DTLSv1_server_method()/DTLSv1_client_method() which pins to DTLS 1.0; change it
to prefer the version‑negotiating DTLS_server_method()/DTLS_client_method() when
building against OpenSSL 1.0.2+ by checking OPENSSL_VERSION_NUMBER (>=
0x10002000L) and calling DTLS_server_method()/DTLS_client_method() to create
ssl_ctx for FLB_TLS_SERVER_MODE_DGRAM/FLB_TLS_CLIENT_MODE_DGRAM, and fall back
to DTLSv1_server_method()/DTLSv1_client_method() when the version check fails or
the symbols are unavailable; keep existing error handling (flb_error and return
NULL) when OPENSSL_NO_DTLS is defined.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Outside diff comments:
In `@src/tls/openssl.c`:
- Around line 845-858: The OpenSSL ≥1.1.0 branch unconditionally calls
DTLS_server_method() and DTLS_client_method(), which can cause linker failures
when built with OPENSSL_NO_DTLS; wrap the DTLS-specific branches (those
comparing mode to FLB_TLS_SERVER_MODE_DGRAM and FLB_TLS_CLIENT_MODE_DGRAM) with
the same `#ifndef` OPENSSL_NO_DTLS guard used in the legacy branch, and in the
guarded-else provide the existing graceful fallback that logs an error and
returns when DTLS is unavailable; keep TLS_server_method()/TLS_client_method()
paths unchanged and ensure symbols SSL_CTX_new, DTLS_server_method,
DTLS_client_method, TLS_server_method, TLS_client_method and the mode constants
are referenced exactly as in the diff.

---

Nitpick comments:
In `@src/tls/openssl.c`:
- Around line 823-843: The DTLS branch currently uses
DTLSv1_server_method()/DTLSv1_client_method() which pins to DTLS 1.0; change it
to prefer the version‑negotiating DTLS_server_method()/DTLS_client_method() when
building against OpenSSL 1.0.2+ by checking OPENSSL_VERSION_NUMBER (>=
0x10002000L) and calling DTLS_server_method()/DTLS_client_method() to create
ssl_ctx for FLB_TLS_SERVER_MODE_DGRAM/FLB_TLS_CLIENT_MODE_DGRAM, and fall back
to DTLSv1_server_method()/DTLSv1_client_method() when the version check fails or
the symbols are unavailable; keep existing error handling (flb_error and return
NULL) when OPENSSL_NO_DTLS is defined.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: e609e643-ded6-406e-936c-cdeb8826f3bd

📥 Commits

Reviewing files that changed from the base of the PR and between 18dc607 and 732e4e5.

📒 Files selected for processing (1)
  • src/tls/openssl.c

@edsiper
edsiper merged commit 2de126c into master Jul 29, 2026
53 checks passed
@edsiper
edsiper deleted the cosmo0920-handle-dtls-protocol-on-out_syslog branch July 29, 2026 15:50
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants