• src/sbbs3/qwk.cpp src/smblib/smblib.c

    From Rob Swindell (on Windows 11)@VERT to Git commit to main/sbbs/master on Fri Jul 17 03:05:43 2026
    https://gitlab.synchro.net/main/sbbs/-/commit/d180ed85f6c62dfaa909b3df
    Modified Files:
    src/sbbs3/qwk.cpp src/smblib/smblib.c
    Log Message:
    QWK vote import: don't pass a NULL sender to stricmp() (crash/assert)

    Importing an inbound QWK network REP packet whose vote record carries no
    Sender field crashed the BBS. qwk_vote() only sets the message's from-name when the packet supplies it, so a senderless ballot left msg.from NULL, which flowed votemsg() -> smb_voted_already() -> smb_msg_is_from(), where the unguarded `stricmp(msg->from, name)` dereferenced the NULL. On the Win32
    debug CRT this fires an assertion ("rhs != nullptr" in stricmp.cpp) that halts the importing event thread on a modal dialog; other builds pass NULL straight into the compare. Reachable from network input (a buggy, old, or crafted QWK peer), so it's a remotely-triggerable defect.

    Fix in two layers:

    - smblib: smb_msg_is_from() now NULL-guards all of its operands (the two
    stricmp()s and the FIDO memcmp()); a missing identity simply doesn't match.
    The unguarded compare dates to 5ea459dffff (dive-31-exam).

    - qwk: qwk_vote() rejects a vote-msg with no sender at the import boundary --
    logging the peer and skipping the ballot -- rather than importing an
    unattributable, un-deduplicatable vote (a minor ballot-stuffing hole) that
    can't be matched against prior votes anyway.

    Root-caused from a live noninvasive stack of the wedged event thread; verified by MSVC compile only (not yet exercised against a REP-with-vote packet).

    Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

    ---
    þ Synchronet þ Vertrauen þ Home of Synchronet þ [vert/cvs/bbs].synchro.net