Bug 15918 - Buffer overflow in CTDB Infiniband support
Summary: Buffer overflow in CTDB Infiniband support
Status: RESOLVED WONTFIX
Alias: None
Product: Samba 4.1 and newer
Classification: Unclassified
Component: CTDB (show other bugs)
Version: 4.11.0
Hardware: All All
: P5 normal (vote)
Target Milestone: ---
Assignee: Martin Schwenke
QA Contact: Samba QA Contact
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2025-09-18 05:15 UTC by Martin Schwenke
Modified: 2025-09-25 07:54 UTC (History)
2 users (show)

See Also:


Attachments
Initial patch (17.39 KB, patch)
2025-09-18 05:41 UTC, Martin Schwenke
no flags Details
Patch v2 (18.27 KB, patch)
2025-09-19 05:30 UTC, Martin Schwenke
no flags Details

Note You need to log in before you can comment on or make changes to this bug.
Description Martin Schwenke 2025-09-18 05:15:10 UTC
There is a buffer overflow in the InfiniBand wrapper (ctdb/ib/ibwrapper.c) via an unbounded sprintf() into ibw_lasterr (a 512-byte buffer). An attacker can send crafted data causing strings longer than 512 bytes to be logged into ibw_lasterr, potentially triggering data corruption and a crash.  Remote code execution seems less likely because the bug is not stack based.
Comment 1 Martin Schwenke 2025-09-18 05:41:45 UTC
Created attachment 18729 [details]
Initial patch
Comment 2 Martin Schwenke 2025-09-18 07:34:35 UTC
Reasons why this might not be incredibly serious:

1. The IB code isn't built by default - I assume there are very few
   users.

2. The code is for the transport that connects ctdbd's on different
   nodes together.  This should use a private network.

   The wiki says:

     This should be a private non-routeable subnet which is only used
     for internal cluster traffic. 

   ctdb(7) says:

     It is strongly recommended that the private addresses are
     configured on a private network that is separate from client
     networks. This is because the CTDB protocol is both unauthenticated
     and unencrypted. If clients share the private network then steps
     need to be taken to stop injection of packets to relevant ports on
     the private addresses. It is also likely that CTDB protocol traffic
     between nodes could leak sensitive information if it can be
     intercepted.

  So, random clients should not be able to inject packets.  This
  network is meant to be separate from the one with SMB (and
  other) clients.
Comment 3 Martin Schwenke 2025-09-18 07:36:03 UTC
(In reply to Martin Schwenke from comment #0)

On reflection, the compiler is unlikely to provide much/any protection for BSS data declared in one files if a buffer overflows BSS data declared in another file.  Not being stack-based probably doesn't buy us much.
Comment 4 Martin Schwenke 2025-09-19 05:30:42 UTC
Created attachment 18730 [details]
Patch v2

Patch is for master but applies and builds at least as far back as v4-20-test.
Comment 5 Martin Schwenke 2025-09-19 05:31:20 UTC
Marcos: Are you happy with your attribution in the commit?
Comment 6 Marcos Tolosa 2025-09-22 11:44:53 UTC
Martin: Yes, thanks for checking!
Comment 7 Martin Schwenke 2025-09-25 07:48:54 UTC
Fixing this via:

  https://gitlab.com/samba-team/samba/-/merge_requests/4240

The code that could overflow the buffer is never executed in ctdbd.  Here is the commit message:

ctdb-ib: Replace uses of sprintf()

An unbounded sprintf() into ibw_lasterr (a 512-byte static data
buffer) can potentially cause overflow into other BSS data.

However, the risk is effectively minimised to zero due to:

* This code not being executed at all in ctdbd.  It is only executed
  in the accompanying test code:

  - The function ibw_process_init_attrs() can cause a buffer overflow
    if its 2nd argument, nattr, is non-zero and one of the structs in
    the array pointed to by its 1st argument, attr, contains a name
    member that is too long.

  - ibw_process_init_attrs() is only called by ibw_init(), which also
    has attr and nattr as its 1st and 2nd args, and it just passes them
    straight through.

  - ibw_init() is called in 2 places:

    1. In ibwrapper_test.c, which is targeted test code.

    2. In ibw_ctdb_init.c:ctdb_ibw_init(), which is the initialisation
       function use to initialise the IB transport in ctdbd.  Here, NULL
       and 0 are passed as the relevant arguments to ibw_init().  Both
       arguments are flagged with TODO comments.  :-)

* This code is not built by default (--enable-infiniband is
  required).

  It appears that Debian and Red Hat family Linux distributions have
  never distributed binaries with this enabled.

* Documentation (ctdb(7) and the wiki) recommends that private
  addresses are configured on a private network that is separate from
  client networks.  So, even if the TODOs were done and the relevant
  arguments could come off the wire, the attack surface should be very
  small.

Only the instance with %s in the format is potentially problematic.
The others can not overflow the current 512 byte buffer.  However, it
makes sense to change them all in case someone foolishly reduces the
size of the buffer and makes other changes so that the buffer can be
overflowed in ctdbd.

Now, will static analysers complain that the result of snprintf() is
not checked even though snprintf() always NUL-terminates?
Comment 8 Martin Schwenke 2025-09-25 07:54:44 UTC
Because this bug does not occur, I have un-embargoed it.  It will be fixed in master.

However, backporting it to stable releases would be pointless, so I am closing this bug with reason WONTFIX.

Marcos, please consider cancelling the CVE you registered for this issue.

Many thanks to Marcos for the bug report.