[SCM] Samba Shared Repository - branch master updated

Andrew Bartlett abartlet at samba.org
Wed Apr 10 23:59:01 UTC 2024


The branch, master has been updated
       via  81598b42455 s3:libsmb_xattr: ace_compare() uses NUMERIC_CMP()
       via  e35d54fd4d3 s3:util:sharesec ace_compare() uses NUMERIC_CMP()
       via  31101a9fa15 s3:smbcacls: use NUMERIC_CMP in ace_compare
       via  5e99262aaf5 s3:util:net_registry: registry_value_cmp() uses NUMERIC_CMP()
       via  a197be2003d s4:wins: use NUMERIC_CMP in nbtd_wins_randomize1Clist_sort()
       via  d8b97649ef4 s4:wins: winsdb_addr_sort_list() uses NUMERIC_CMP()
       via  66d47537e42 s4:wins: use NUMERIC_CMP in winsdb_addr_sort_list()
       via  42ead213484 s4:dns_server: use NUMERIC_CMP in rec_cmp()
       via  ed3ab87bdb0 s4:rpc_server: compare_SamEntry() uses NUMERIC_CMP()
       via  dd4a0c27681 s3:lib:util_tdb: use NUMERIC_CMP() in tdb_data_cmp()
       via  4641a971517 libcli/security: use NUMERIC_CMP in dom_sid_compare_auth()
       via  cb94202c1cf libcli/security: use NUMERIC_CMP in dom_sid_compare()
       via  21a071e4864 ldb: reduce non-transitive comparisons in ldb_msg_element_compare()
       via  5c36bc82415 ldb: avoid non-transitive comparison in ldb_val_cmp()
       via  e1519c36678 util:datablob: avoid non-transitive comparison in data_blob_cmp()
       via  838c6847029 ldb:attrib_handlers: ldb_comparison_binary uses NUMERIC_CMP()
       via  f78b964cd81 ldb:attrib_handlers: ldb_comparison_Boolean uses NUMERIC_CMP()
       via  997b72d79e6 util: charset:util_str: use NUMERIC_CMP in strncasecmp_m_handle
       via  6159b098cf3 lib/torture: add assert_int_{less,greater} macros
       via  3414a894ad6 s3:libsmb:namequery: use NUMERIC_CMP in addr_compare
       via  4a9d274d43b s3:libsmb:namequery: note intransitivity in addr_compare()
       via  f07ae699070 util:charset:codepoints: codepoint_cmpi warning about non-transitivity
       via  675fdeee3d6 util:charset:codepoints: condepoint_cmpi uses NUMERIC_CMP()
       via  d4ce8231f98 util:test: test_ms_fn_match_protocol_no_wildcard: allow -1
       via  f788a399996 util:charset:util_str: use NUMERIC_CMP in strcasecmp_m_handle
       via  a512759d7b2 torture:charset: test more of strcasecmp_m
       via  dda0bb6fc71 torture:charset: use < and > assertions for strncasecmp_m
       via  ac0a8cd92ca torture:charset: use < and > assertions for strcasecmp_m
       via  09c98ff1263 util:binsearch: user NUMERIC_CMP()
       via  ee4ebcccd7d s4: use numeric_cmp in dns_common_sort_zones()
       via  623adcf4aae s4:dsdb:mod:operational: use NUMERIC_CMP in pso_compare
       via  a6d76d6ee9f s4:ntvfs: use NUMERIC_CMP in stream_name_cmp
       via  75e51bd99b7 ldb:ldb_dn: use safe NUMERIC_CMP in ldb_dn_compare()
       via  5150b318f48 ldb:ldb_dn: use safe NUMERIC_CMP in ldb_dn_compare_base()
       via  de1b94f79ea ldb: add NUMERIC_CMP macro to ldb.h
       via  5ab93f48c57 util:tsort.h: add a macro for safely comparing numbers
       via  8b6a584170e lib/fuzzing/decode_ndr_X_crash: guess the pipe from filename
       via  73e4f6026ad ldb: avoid out of bounds read and write in ldb_qsort()
      from  60df2a09a43 selftest: move some more expected failures to expectedfail.d

https://git.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 81598b42455d6758941da532c668b6d4e969cc40
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:33:47 2024 +1300

    s3:libsmb_xattr: ace_compare() uses NUMERIC_CMP()
    
    the access_mask is the easiest to overflow with subtraction -- other
    fields are 8 or 16 bit.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    
    Autobuild-User(master): Andrew Bartlett <abartlet at samba.org>
    Autobuild-Date(master): Wed Apr 10 23:58:12 UTC 2024 on atb-devel-224

commit e35d54fd4d381df67ab9b4f8390e2109b2142678
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:08:02 2024 +1300

    s3:util:sharesec ace_compare() uses NUMERIC_CMP()
    
    ace->access_mask is uint32_t, so can overflow a signed int.
    This would be easy to trigger, as it is a flags field rather than an
    allocation count.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 31101a9fa1503be9d8137e42466f57d85136a156
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:56:48 2024 +1300

    s3:smbcacls: use NUMERIC_CMP in ace_compare
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 5e99262aaf5fc6601f3859c8b060b680b11bf6ea
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:25:54 2024 +1300

    s3:util:net_registry: registry_value_cmp() uses NUMERIC_CMP()
    
    v->type is an int-sized enum, so overflow might be possible if it could
    be arbitrarily set.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit a197be2003d7e248b1e1294f4ad5473f48762bce
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:53:32 2024 +1300

    s4:wins: use NUMERIC_CMP in nbtd_wins_randomize1Clist_sort()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit d8b97649ef4d3ccaf53878021be0e2d4824b982c
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:16:21 2024 +1300

    s4:wins: winsdb_addr_sort_list() uses NUMERIC_CMP()
    
    expire_time is time_t, which is at least int-sized, so overflow is
    possible (if this code ever runs).
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 66d47537e42caa528c7fab670d9c35d27c513cce
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:54:09 2024 +1300

    s4:wins: use NUMERIC_CMP in winsdb_addr_sort_list()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 42ead213484840121ce6bc0db22941ea0a019105
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:22:24 2024 +1300

    s4:dns_server: use NUMERIC_CMP in rec_cmp()
    
    dnsp_DnssrvRpcRecord.dwTimeStamp is uint32_t, making overflow possible.
    
    dnsp_DnssrvRpcRecord.wType is an enum, which has the size of an int,
    though it may be hard to set it to overflowing values.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit ed3ab87bdb0f6c6a9ea6323ed240fe267220b759
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:10:45 2024 +1300

    s4:rpc_server: compare_SamEntry() uses NUMERIC_CMP()
    
    SamEntry.idx is uint32_t.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit dd4a0c276813b2c8516061110a7e580aa9afcf40
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:01:24 2024 +1300

    s3:lib:util_tdb: use NUMERIC_CMP() in tdb_data_cmp()
    
    Although these are size_t, in practice TDB data is limited to 32 bit.
    Even so, overflow of a signed int is possible.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 4641a97151783c2ae825582e91b4676d66dcb713
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 13:53:58 2024 +1300

    libcli/security: use NUMERIC_CMP in dom_sid_compare_auth()
    
    These numbers are all 8 bit, so overflow is unlikely.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit cb94202c1cf990e871ee2e8e43c577a0e4b9ee6f
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 13:43:47 2024 +1300

    libcli/security: use NUMERIC_CMP in dom_sid_compare()
    
    sid->num_auths is always small (int8 < 16), so this is cosmetic only.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 21a071e4864dd739840c2ad4adb0c71ec33f8427
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 11:26:25 2024 +1300

    ldb: reduce non-transitive comparisons in ldb_msg_element_compare()
    
    We can still have inconsistent comparisons, because two elements with
    the same number of values will always return -1 if they are unequal,
    which means they will sort differently depending on the order in which
    they are compared.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 5c36bc82415b246fccec9eae693da82b7aa45b81
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 11:22:58 2024 +1300

    ldb: avoid non-transitive comparison in ldb_val_cmp()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit e1519c3667841ce27b15983eae378799ef9936f7
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 11:07:06 2024 +1300

    util:datablob: avoid non-transitive comparison in data_blob_cmp()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 838c68470299045c5b1c9bdbd527edbeedebf2d6
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 17:43:03 2024 +1300

    ldb:attrib_handlers: ldb_comparison_binary uses NUMERIC_CMP()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit f78b964cd81db11097e78099c0699f571f20e126
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 17:32:48 2024 +1300

    ldb:attrib_handlers: ldb_comparison_Boolean uses NUMERIC_CMP()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 997b72d79e651ddbc20e67006ae176229528dc6f
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 16:16:44 2024 +1300

    util: charset:util_str: use NUMERIC_CMP in strncasecmp_m_handle
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 6159b098cf35a8043682bfd4c4ea17ef0da6e8ee
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Fri Apr 5 14:22:11 2024 +1300

    lib/torture: add assert_int_{less,greater} macros
    
    In some situations, like comparison functions for qsort, we don't care
    about the actual value, just whethger it was greater or less than
    zero.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 3414a894ad6640fa8e282d650b1cc5319991545f
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 16:13:07 2024 +1300

    s3:libsmb:namequery: use NUMERIC_CMP in addr_compare
    
    This one was OK, as the numbers are tightly bound, but there is no
    real reason not to do it safely.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 4a9d274d43b1adac113419c649bbf530d180229d
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 16:10:38 2024 +1300

    s3:libsmb:namequery: note intransitivity in addr_compare()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit f07ae6990702f8806c0c815454b80a5596b7219a
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 14:56:16 2024 +1300

    util:charset:codepoints: codepoint_cmpi warning about non-transitivity
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 675fdeee3d6570fdf5a055890dc3386a8db5fd88
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 15:53:29 2024 +1300

    util:charset:codepoints: condepoint_cmpi uses NUMERIC_CMP()
    
    If these are truly unicode codepoints (< ~2m) there is no overflow,
    but the type is defined as uint32_t.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit d4ce8231f986a359dc657cd1a6b416270a53c7d3
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 17:23:15 2024 +1300

    util:test: test_ms_fn_match_protocol_no_wildcard: allow -1
    
    We have changed strcasecmp_m() to return -1 in a place where it used
    to return -3. This upset a test, but it shouldn't have: the exact
    value of the negative int is not guaranteed by the function.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit f788a399996a73b2aa206ec2b15f5943b06660e0
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 15:49:55 2024 +1300

    util:charset:util_str: use NUMERIC_CMP in strcasecmp_m_handle
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit a512759d7b216cacc0a780b3304549b7945f919c
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Fri Apr 5 14:46:48 2024 +1300

    torture:charset: test more of strcasecmp_m
    
    We now test cases:
    
    1. where the first string compares less
    2. one of the strings ends before the other
    3. the strings differ on a character other than the first.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit dda0bb6fc71bae91f3158f69462cb79fdad210fb
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Fri Apr 5 14:43:42 2024 +1300

    torture:charset: use < and > assertions for strncasecmp_m
    
    strncasecmp_m is supposed to return a negative, zero, or positive
    number, not necessarily the difference between the codepoints in
    the first  character that differs, which we have been asserting up to
    now.
    
    This fixes a knownfail on 32 bit.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit ac0a8cd92ca4497bfcfad30e2b4d47547b582b92
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Fri Apr 5 13:14:38 2024 +1300

    torture:charset: use < and > assertions for strcasecmp_m
    
    strcasecmp_m is supposed to return a negative, zero, or positive
    number, depending on whether the first argument is less than, equal to,
    or greater than the second argument (respectively).
    
    We have been asserting that it returns exactly the difference between
    the codepoints in the first character that differs.
    
    This fixes a knownfail on 32 bit.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 09c98ff1263eb05933f1956e201655dd41e28a0c
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 15:47:10 2024 +1300

    util:binsearch: user NUMERIC_CMP()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit ee4ebcccd7d9d89dda59615b3653df2632fb1a5d
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:55:54 2024 +1300

    s4: use numeric_cmp in dns_common_sort_zones()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 623adcf4aae00ac06e82d98a75ce4644890501e6
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:55:27 2024 +1300

    s4:dsdb:mod:operational: use NUMERIC_CMP in pso_compare
    
    prec_{1,2} are uint32_t, and if one is not set we are defaulting to
    0xffffffff (a.k.a UINT32_MAX), so an overflow when cast to int seems
    extremely likely.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit a6d76d6ee9f7cfcabe2c20b872b8b1cb598928a6
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:52:50 2024 +1300

    s4:ntvfs: use NUMERIC_CMP in stream_name_cmp
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 75e51bd99b7a029afd98b55283eddad835319ed6
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:51:04 2024 +1300

    ldb:ldb_dn: use safe NUMERIC_CMP in ldb_dn_compare()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 5150b318f4894a8036b2a394c446afd513f8cb60
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:50:47 2024 +1300

    ldb:ldb_dn: use safe NUMERIC_CMP in ldb_dn_compare_base()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit de1b94f79ea8694ecdddab4b455d539caa7e77e2
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 17:53:39 2024 +1300

    ldb: add NUMERIC_CMP macro to ldb.h
    
    In other places we tend to include tsort.h, which also has TYPESAFE_QSORT.
    
    ldb.h already has TYPESAFE_QSORT, so it might as well have NUMERIC_CMP.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 5ab93f48c575db1a3c5a707258cc44f707a5eeb0
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Wed Apr 3 12:43:27 2024 +1300

    util:tsort.h: add a macro for safely comparing numbers
    
    In many places we use `return a - b;` in a comparison function. This can
    be problematic if the comparison is used in a sort, as `a - b` is not
    guaranteed to do what we expect. For example:
    
    * if a and b are 2s-complement ints, a is INT_MIN and b is INT_MAX, then
      a - b = 1, which is wrong.
    
    * if a and b are 64 bit pointers, a - b could wrap around many times in
      a cmp function returning 32 bit ints. (We do this often).
    
    The issue is not just that a sort could go haywire.
    Due to a bug in glibc, this could result in out-of-bounds access:
    
    https://www.openwall.com/lists/oss-security/2024/01/30/7
    
    (We have replicated this bug in ldb_qsort).
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 8b6a584170eeb5082a188879be88e5f414b0be81
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Mar 28 12:57:54 2024 +1300

    lib/fuzzing/decode_ndr_X_crash: guess the pipe from filename
    
    Usually we are dealing with a filename that tells you what the pipe is,
    and there is no reason for this debug helper not to be convenient
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

commit 73e4f6026ad04b73074b413bd8c838ca48ffde7f
Author: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
Date:   Thu Apr 4 11:06:00 2024 +1300

    ldb: avoid out of bounds read and write in ldb_qsort()
    
    If a compare function is non-transitive (for example, if it evaluates
    A > B and B > C, but A < C), this implementation of qsort could access
    out-of-bounds memory. This was found in glibc's qsort by Qualys, and
    their write-up for OSS-Security explains it very well:
    
     https://www.openwall.com/lists/oss-security/2024/01/30/7
    
    An example of a non-transitive compare is one in which does this
    
     int cmp(const void *_a, const void *_b)
     {
            int a = *(int *)_a;
            int b = *(int *)_b;
            return a - b;
     }
    
    which does the right thing when the magnitude of the numbers is small,
    but which will go wrong if a is INT_MIN and b is INT_MAX. Likewise, if
    a and b are e.g. uint32_t, the value can wrap when cast to int.
    
    We have functions that are non-transitive regardless of subtraction.
    For example, here (which is not used with ldb_qsort):
    
     int codepoint_cmpi(codepoint_t c1, codepoint_t c2)
            if (c1 == c2 ||
                toupper_m(c1) == toupper_m(c2)) {
                    return 0;
            }
            return c1 - c2;
     }
    
    The toupper_m() is only called on equality case. Consider {'a', 'A', 'B'}.
         'a' == 'A'
         'a' >  'B'  (lowercase letters come after upper)
         'A' <  'B'
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15569
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15625
    
    Signed-off-by: Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>

-----------------------------------------------------------------------

Summary of changes:
 lib/fuzzing/decode_ndr_X_crash               | 12 +++++++++--
 lib/ldb/common/attrib_handlers.c             |  4 ++--
 lib/ldb/common/ldb_dn.c                      |  4 ++--
 lib/ldb/common/ldb_msg.c                     | 13 +++++++++---
 lib/ldb/common/qsort.c                       |  2 +-
 lib/ldb/include/ldb.h                        | 16 ++++++++++++++
 lib/torture/torture.h                        | 20 ++++++++++++++++++
 lib/util/charset/codepoints.c                | 15 +++++++++++++-
 lib/util/charset/tests/charset.c             | 31 +++++++++++++++-------------
 lib/util/charset/util_str.c                  |  9 ++++----
 lib/util/data_blob.c                         |  5 +++--
 lib/util/tests/binsearch.c                   |  6 ++++--
 lib/util/tests/test_ms_fnmatch.c             |  2 +-
 lib/util/tsort.h                             | 19 +++++++++++++++++
 libcli/security/dom_sid.c                    | 14 +++++++------
 selftest/knownfail-32bit                     |  8 -------
 source3/lib/util_tdb.c                       |  4 ++--
 source3/libsmb/libsmb_xattr.c                | 14 +++++++++----
 source3/libsmb/namequery.c                   | 14 ++++++++++---
 source3/utils/net_registry.c                 |  2 +-
 source3/utils/sharesec.c                     |  8 +++----
 source3/utils/smbcacls.c                     | 15 +++++++-------
 source4/dns_server/dnsserver_common.c        |  6 +++---
 source4/dsdb/samdb/ldb_modules/operational.c |  2 +-
 source4/nbt_server/wins/winsdb.c             |  5 +++--
 source4/nbt_server/wins/winsserver.c         |  3 ++-
 source4/ntvfs/posix/pvfs_streams.c           |  3 ++-
 source4/rpc_server/samr/dcesrv_samr.c        |  2 +-
 28 files changed, 180 insertions(+), 78 deletions(-)


Changeset truncated at 500 lines:

diff --git a/lib/fuzzing/decode_ndr_X_crash b/lib/fuzzing/decode_ndr_X_crash
index 63c3cd747d7..d90e7efe122 100755
--- a/lib/fuzzing/decode_ndr_X_crash
+++ b/lib/fuzzing/decode_ndr_X_crash
@@ -61,8 +61,9 @@ def process_one_file(f):
 
 def main():
     parser = argparse.ArgumentParser()
-    parser.add_argument('-p', '--pipe', default='$PIPE',
-                        help='pipe name (for output command line)')
+    parser.add_argument('-p', '--pipe', default=None,
+                        help=('pipe name (for output command line, '
+                              'default is a guess or "$PIPE")'))
     parser.add_argument('-t', '--type', default=None, choices=TYPES,
                         help='restrict to this type')
     parser.add_argument('-o', '--opnum', default=None, type=int,
@@ -91,6 +92,13 @@ def main():
         sys.exit(1)
 
     for fn in args.FILES:
+        if pipe is None:
+            m = re.search(r'clusterfuzz-testcase.+-fuzz_ndr_([a-z]+)', fn)
+            if m is None:
+                pipe = '$PIPE'
+            else:
+                pipe = m.group(1)
+
         if args.crash_filter is not None:
             if not re.search(args.crash_filter, fn):
                 print_if_verbose(f"skipping {fn}")
diff --git a/lib/ldb/common/attrib_handlers.c b/lib/ldb/common/attrib_handlers.c
index 15470cfcc74..baccf193f88 100644
--- a/lib/ldb/common/attrib_handlers.c
+++ b/lib/ldb/common/attrib_handlers.c
@@ -287,7 +287,7 @@ static int ldb_comparison_Boolean(struct ldb_context *ldb, void *mem_ctx,
 			   const struct ldb_val *v1, const struct ldb_val *v2)
 {
 	if (v1->length != v2->length) {
-		return v1->length - v2->length;
+		return NUMERIC_CMP(v1->length, v2->length);
 	}
 	return strncasecmp((char *)v1->data, (char *)v2->data, v1->length);
 }
@@ -300,7 +300,7 @@ int ldb_comparison_binary(struct ldb_context *ldb, void *mem_ctx,
 			  const struct ldb_val *v1, const struct ldb_val *v2)
 {
 	if (v1->length != v2->length) {
-		return v1->length - v2->length;
+		return NUMERIC_CMP(v1->length, v2->length);
 	}
 	return memcmp(v1->data, v2->data, v1->length);
 }
diff --git a/lib/ldb/common/ldb_dn.c b/lib/ldb/common/ldb_dn.c
index 39fe1e81f0d..7325a000f0a 100644
--- a/lib/ldb/common/ldb_dn.c
+++ b/lib/ldb/common/ldb_dn.c
@@ -1111,7 +1111,7 @@ int ldb_dn_compare_base(struct ldb_dn *base, struct ldb_dn *dn)
 
 		/* compare attr.cf_value. */
 		if (b_vlen != dn_vlen) {
-			return b_vlen - dn_vlen;
+			return NUMERIC_CMP(b_vlen, dn_vlen);
 		}
 		ret = strncmp(b_vdata, dn_vdata, b_vlen);
 		if (ret != 0) return ret;
@@ -1197,7 +1197,7 @@ int ldb_dn_compare(struct ldb_dn *dn0, struct ldb_dn *dn1)
 
 		/* compare attr.cf_value. */
 		if (dn0_vlen != dn1_vlen) {
-			return dn0_vlen - dn1_vlen;
+			return NUMERIC_CMP(dn0_vlen, dn1_vlen);
 		}
 		ret = strncmp(dn0_vdata, dn1_vdata, dn0_vlen);
 		if (ret != 0) {
diff --git a/lib/ldb/common/ldb_msg.c b/lib/ldb/common/ldb_msg.c
index 53f675ed183..bbb7ff96233 100644
--- a/lib/ldb/common/ldb_msg.c
+++ b/lib/ldb/common/ldb_msg.c
@@ -93,7 +93,7 @@ struct ldb_val *ldb_msg_find_val(const struct ldb_message_element *el,
 static int ldb_val_cmp(const struct ldb_val *v1, const struct ldb_val *v2)
 {
 	if (v1->length != v2->length) {
-		return v1->length - v2->length;
+		return NUMERIC_CMP(v1->length, v2->length);
 	}
 	return memcmp(v1->data, v2->data, v1->length);
 }
@@ -749,9 +749,16 @@ int ldb_msg_element_compare(struct ldb_message_element *el1,
 	unsigned int i;
 
 	if (el1->num_values != el2->num_values) {
-		return el1->num_values - el2->num_values;
+		return NUMERIC_CMP(el1->num_values, el2->num_values);
 	}
-
+	/*
+	 * Note this is an inconsistent comparison, unsuitable for
+	 * sorting. If A has values {a, b} and B has values {b, c},
+	 * then
+	 *
+	 * ldb_msg_element_compare(A, B) returns -1, meaning A < B
+	 * ldb_msg_element_compare(B, A) returns -1, meaning B < A
+	 */
 	for (i=0;i<el1->num_values;i++) {
 		if (!ldb_msg_find_val(el2, &el1->values[i])) {
 			return -1;
diff --git a/lib/ldb/common/qsort.c b/lib/ldb/common/qsort.c
index 012aaf3c403..bae35e6b1b1 100644
--- a/lib/ldb/common/qsort.c
+++ b/lib/ldb/common/qsort.c
@@ -227,7 +227,7 @@ void ldb_qsort (void *const pbase, size_t total_elems, size_t size,
     while ((run_ptr += size) <= end_ptr)
       {
 	tmp_ptr = run_ptr - size;
-	while ((*cmp) ((void *) run_ptr, (void *) tmp_ptr, opaque) < 0)
+	while (tmp_ptr > base_ptr && (*cmp) ((void *) run_ptr, (void *) tmp_ptr, opaque) < 0)
 	  tmp_ptr -= size;
 
 	tmp_ptr += size;
diff --git a/lib/ldb/include/ldb.h b/lib/ldb/include/ldb.h
index e98300d9e8d..b6625d9d96e 100644
--- a/lib/ldb/include/ldb.h
+++ b/lib/ldb/include/ldb.h
@@ -2335,6 +2335,22 @@ do { \
 } while (0)
 #endif
 
+#ifndef NUMERIC_CMP
+/*
+ * NUMERIC_CMP is a safe replacement for `a - b` in comparison
+ * functions. It will work on integers, pointers, and floats.
+ *
+ * Rather than
+ *
+ *      return a - b;
+ *
+ * use
+ *
+ *     return NUMERIC_CMP(a, b);
+ */
+#define NUMERIC_CMP(a, b) (((a) > (b)) - ((a) < (b)))
+#endif
+
 
 
 /**
diff --git a/lib/torture/torture.h b/lib/torture/torture.h
index 2e86e3173cc..2194703d5fc 100644
--- a/lib/torture/torture.h
+++ b/lib/torture/torture.h
@@ -534,6 +534,26 @@ static inline void torture_dump_data_str_cb(const char *buf, void *private_data)
 	} \
 	} while(0)
 
+#define torture_assert_int_less(torture_ctx,got,limit,cmt)\
+	do { int __got = (got), __limit = (limit); \
+	if (__got >= __limit) { \
+		torture_result(torture_ctx, TORTURE_FAIL, \
+			__location__": "#got" was %d (0x%X), expected < %d (0x%X): %s", \
+			__got, __got, __limit, __limit, cmt); \
+		return false; \
+	} \
+	} while(0)
+
+#define torture_assert_int_greater(torture_ctx,got,limit,cmt)\
+	do { int __got = (got), __limit = (limit); \
+	if (__got <= __limit) { \
+		torture_result(torture_ctx, TORTURE_FAIL, \
+			__location__": "#got" was %d (0x%X), expected > %d (0x%X): %s", \
+			__got, __got, __limit, __limit, cmt); \
+		return false; \
+	} \
+	} while(0)
+
 #define torture_assert_int_equal_goto(torture_ctx,got,expected,ret,label,cmt)\
 	do { int __got = (got), __expected = (expected); \
 	if (__got != __expected) { \
diff --git a/lib/util/charset/codepoints.c b/lib/util/charset/codepoints.c
index ea2c4be7fe6..80226278faf 100644
--- a/lib/util/charset/codepoints.c
+++ b/lib/util/charset/codepoints.c
@@ -26,6 +26,7 @@
 #include "dynconfig/dynconfig.h"
 #include "lib/util/debug.h"
 #include "lib/util/byteorder.h"
+#include "lib/util/tsort.h"
 
 #ifdef strcasecmp
 #undef strcasecmp
@@ -16479,11 +16480,23 @@ _PUBLIC_ bool isupper_m(codepoint_t val)
 */
 _PUBLIC_ int codepoint_cmpi(codepoint_t c1, codepoint_t c2)
 {
+	/*
+	 * FIXME: this is unsuitable for use in a sort, as the
+	 * comparison is intransitive.
+	 *
+	 * The problem is toupper_m() is only called on equality case,
+	 * which has strange effects.
+	 *
+	 *    Consider {'a', 'A', 'B'}.
+	 *     'a' == 'A'
+	 *     'a' >  'B'  (lowercase letters come after upper)
+	 *     'A' <  'B'
+	 */
 	if (c1 == c2 ||
 	    toupper_m(c1) == toupper_m(c2)) {
 		return 0;
 	}
-	return c1 - c2;
+	return NUMERIC_CMP(c1, c2);
 }
 
 
diff --git a/lib/util/charset/tests/charset.c b/lib/util/charset/tests/charset.c
index 547dc51e59d..bca5449c579 100644
--- a/lib/util/charset/tests/charset.c
+++ b/lib/util/charset/tests/charset.c
@@ -72,16 +72,19 @@ static bool test_strcasecmp_m(struct torture_context *tctx)
 	const char file_iso8859_1[7] = { 0x66, 0x69, 0x6c, 0x65, 0x2d, 0xe9, 0 };
 	/* file.{accented e} in utf8 */
 	const char file_utf8[8] =      { 0x66, 0x69, 0x6c, 0x65, 0x2d, 0xc3, 0xa9, 0 };
-	torture_assert_int_equal(tctx, strcasecmp_m("foo", "bar"), 4, "different strings both lower");
-	torture_assert_int_equal(tctx, strcasecmp_m("foo", "Bar"), 4, "different strings lower/upper");
-	torture_assert_int_equal(tctx, strcasecmp_m("Foo", "bar"), 4, "different strings upper/lower");
-	torture_assert_int_equal(tctx, strcasecmp_m("AFoo", "_bar"), 2, "different strings upper/lower");
+	torture_assert_int_greater(tctx, strcasecmp_m("foo", "bar"), 0, "different strings both lower");
+	torture_assert_int_less(tctx, strcasecmp_m("bar", "foo"), 0, "different strings both lower");
+	torture_assert_int_greater(tctx, strcasecmp_m("foo", "Bar"), 0, "different strings lower/upper");
+	torture_assert_int_greater(tctx, strcasecmp_m("Foo", "bar"), 0, "different strings upper/lower");
+	torture_assert_int_greater(tctx, strcasecmp_m("AFoo", "_bar"), 0, "different strings upper/lower");
 	torture_assert_int_equal(tctx, strcasecmp_m("foo", "foo"), 0, "same case strings");
 	torture_assert_int_equal(tctx, strcasecmp_m("foo", "Foo"), 0, "different case strings");
-	torture_assert_int_equal(tctx, strcasecmp_m(NULL, "Foo"),  -1, "one NULL");
-	torture_assert_int_equal(tctx, strcasecmp_m("foo", NULL),  1, "other NULL");
+	torture_assert_int_greater(tctx, strcasecmp_m("food", "Foo"), 0, "strings differ towards the end");
+	torture_assert_int_less(tctx, strcasecmp_m("food", "Fool"), 0, "strings differ towards the end");
+	torture_assert_int_less(tctx, strcasecmp_m(NULL, "Foo"),  0, "one NULL");
+	torture_assert_int_greater(tctx, strcasecmp_m("foo", NULL),  0, "other NULL");
 	torture_assert_int_equal(tctx, strcasecmp_m(NULL, NULL),   0, "both NULL");
-	torture_assert_int_equal(tctx, strcasecmp_m(file_iso8859_1, file_utf8), 38,
+	torture_assert_int_greater(tctx, strcasecmp_m(file_iso8859_1, file_utf8), 0,
 		"file.{accented e} should differ");
 	return true;
 }
@@ -151,19 +154,19 @@ static bool test_strncasecmp_m(struct torture_context *tctx)
 	const char file_iso8859_1[7] = { 0x66, 0x69, 0x6c, 0x65, 0x2d, 0xe9, 0 };
 	/* file.{accented e} in utf8 */
 	const char file_utf8[8] =      { 0x66, 0x69, 0x6c, 0x65, 0x2d, 0xc3, 0xa9, 0 };
-	torture_assert_int_equal(tctx, strncasecmp_m("foo", "bar", 3), 4, "different strings both lower");
-	torture_assert_int_equal(tctx, strncasecmp_m("foo", "Bar", 3), 4, "different strings lower/upper");
-	torture_assert_int_equal(tctx, strncasecmp_m("Foo", "bar", 3), 4, "different strings upper/lower");
-	torture_assert_int_equal(tctx, strncasecmp_m("AFoo", "_bar", 4), 2, "different strings upper/lower");
+	torture_assert_int_greater(tctx, strncasecmp_m("foo", "bar", 3), 0, "different strings both lower");
+	torture_assert_int_greater(tctx, strncasecmp_m("foo", "Bar", 3), 0, "different strings lower/upper");
+	torture_assert_int_greater(tctx, strncasecmp_m("Foo", "bar", 3), 0, "different strings upper/lower");
+	torture_assert_int_greater(tctx, strncasecmp_m("AFoo", "_bar", 4), 0, "different strings upper/lower");
 	torture_assert_int_equal(tctx, strncasecmp_m("foo", "foo", 3), 0, "same case strings");
 	torture_assert_int_equal(tctx, strncasecmp_m("foo", "Foo", 3), 0, "different case strings");
 	torture_assert_int_equal(tctx, strncasecmp_m("fool", "Foo", 3),0, "different case strings");
 	torture_assert_int_equal(tctx, strncasecmp_m("fool", "Fool", 40), 0, "over size");
 	torture_assert_int_equal(tctx, strncasecmp_m("BLA", "Fool", 0),0, "empty");
-	torture_assert_int_equal(tctx, strncasecmp_m(NULL, "Foo", 3),  -1, "one NULL");
-	torture_assert_int_equal(tctx, strncasecmp_m("foo", NULL, 3),  1, "other NULL");
+	torture_assert_int_less(tctx, strncasecmp_m(NULL, "Foo", 3),  0, "one NULL");
+	torture_assert_int_greater(tctx, strncasecmp_m("foo", NULL, 3),  0, "other NULL");
 	torture_assert_int_equal(tctx, strncasecmp_m(NULL, NULL, 3),   0, "both NULL");
-	torture_assert_int_equal(tctx, strncasecmp_m(file_iso8859_1, file_utf8, 6), 38,
+	torture_assert_int_greater(tctx, strncasecmp_m(file_iso8859_1, file_utf8, 6), 0,
 		"file.{accented e} should differ");
 	return true;
 }
diff --git a/lib/util/charset/util_str.c b/lib/util/charset/util_str.c
index 1650c9b8232..c52b77384ce 100644
--- a/lib/util/charset/util_str.c
+++ b/lib/util/charset/util_str.c
@@ -26,6 +26,7 @@
 #include "system/locale.h"
 #include "charset.h"
 #include "lib/util/fault.h"
+#include "lib/util/tsort.h"
 
 #ifdef strcasecmp
 #undef strcasecmp
@@ -79,10 +80,10 @@ _PUBLIC_ int strcasecmp_m_handle(struct smb_iconv_handle *iconv_handle,
 			continue;
 		}
 
-		return l1 - l2;
+		return NUMERIC_CMP(l1, l2);
 	}
 
-	return *s1 - *s2;
+	return NUMERIC_CMP(*s1, *s2);
 }
 
 /**
@@ -156,14 +157,14 @@ _PUBLIC_ int strncasecmp_m_handle(struct smb_iconv_handle *iconv_handle,
 			continue;
 		}
 
-		return l1 - l2;
+		return NUMERIC_CMP(l1, l2);
 	}
 
 	if (n == 0) {
 		return 0;
 	}
 
-	return *s1 - *s2;
+	return NUMERIC_CMP(*s1, *s2);
 }
 
 /**
diff --git a/lib/util/data_blob.c b/lib/util/data_blob.c
index 69a340c6fb8..15582000205 100644
--- a/lib/util/data_blob.c
+++ b/lib/util/data_blob.c
@@ -22,6 +22,7 @@
 #include "attr.h"
 #include "data_blob.h"
 #include "lib/util/samba_util.h"
+#include "lib/util/tsort.h"
 
 const DATA_BLOB data_blob_null = { NULL, 0 };
 
@@ -121,12 +122,12 @@ _PUBLIC_ int data_blob_cmp(const DATA_BLOB *d1, const DATA_BLOB *d2)
 		return 1;
 	}
 	if (d1->data == d2->data) {
-		return d1->length - d2->length;
+		return NUMERIC_CMP(d1->length, d2->length);
 	}
 	ret = memcmp(d1->data, d2->data, MIN(d1->length, d2->length));
 	if (ret == 0) {
 		/* Note this ordering is used in conditional aces */
-		return d1->length - d2->length;
+		return NUMERIC_CMP(d1->length, d2->length);
 	}
 	return ret;
 }
diff --git a/lib/util/tests/binsearch.c b/lib/util/tests/binsearch.c
index b3ecda165f3..24840156c73 100644
--- a/lib/util/tests/binsearch.c
+++ b/lib/util/tests/binsearch.c
@@ -23,17 +23,19 @@
 
 #include "includes.h"
 #include "lib/util/binsearch.h"
+#include "lib/util/tsort.h"
 #include "torture/torture.h"
 #include "torture/local/proto.h"
 
 static int int_cmp(int a, int b)
 {
-	return a - b;
+	return NUMERIC_CMP(a, b);
 }
 
 static int int_cmp_p(int a, int *b)
 {
-	return a - *b;
+	int _b = *b;
+	return NUMERIC_CMP(a, _b);
 }
 
 static bool test_binsearch_v(struct torture_context *tctx)
diff --git a/lib/util/tests/test_ms_fnmatch.c b/lib/util/tests/test_ms_fnmatch.c
index d11c7bed4be..2261f9bb111 100644
--- a/lib/util/tests/test_ms_fnmatch.c
+++ b/lib/util/tests/test_ms_fnmatch.c
@@ -36,7 +36,7 @@ static void test_ms_fn_match_protocol_no_wildcard(void **state)
 	/* no wildcards in pattern, a simple strcasecmp_m */
 	cmp = ms_fnmatch_protocol("pattern", "string", PROTOCOL_COREPLUS,
 				  true);	/* case sensitive */
-	assert_int_equal(cmp, -3);
+	assert_true(cmp < 0);
 }
 
 static void test_ms_fn_match_protocol_pattern_upgraded(void **state)
diff --git a/lib/util/tsort.h b/lib/util/tsort.h
index 811d6cd2f77..18e82d6c9fe 100644
--- a/lib/util/tsort.h
+++ b/lib/util/tsort.h
@@ -37,4 +37,23 @@ do { \
 } while (0)
 #endif
 
+
+#ifndef NUMERIC_CMP
+/*
+ * NUMERIC_CMP is a safe replacement for `a - b` in comparison
+ * functions. It will work on integers, pointers, and floats.
+ *
+ * Rather than
+ *
+ *      return a - b;
+ *
+ * use
+ *
+ *     return NUMERIC_CMP(a, b);
+ *
+ * and you won't have any troubles if a - b would overflow.
+ */
+#define NUMERIC_CMP(a, b) (((a) > (b)) - ((a) < (b)))
+#endif
+
 #endif
diff --git a/libcli/security/dom_sid.c b/libcli/security/dom_sid.c
index eaece2a55f5..21012b70884 100644
--- a/libcli/security/dom_sid.c
+++ b/libcli/security/dom_sid.c
@@ -28,6 +28,7 @@
 #include "librpc/gen_ndr/security.h"
 #include "dom_sid.h"
 #include "lib/util/smb_strtox.h"
+#include "lib/util/tsort.h"
 
 /*****************************************************************
  Compare the auth portion of two sids.
@@ -46,11 +47,12 @@ int dom_sid_compare_auth(const struct dom_sid *sid1,
 		return 1;
 
 	if (sid1->sid_rev_num != sid2->sid_rev_num)
-		return sid1->sid_rev_num - sid2->sid_rev_num;
+		return NUMERIC_CMP(sid1->sid_rev_num, sid2->sid_rev_num);
 
 	for (i = 0; i < 6; i++)
-		if (sid1->id_auth[i] != sid2->id_auth[i])
-			return sid1->id_auth[i] - sid2->id_auth[i];
+		if (sid1->id_auth[i] != sid2->id_auth[i]) {
+			return NUMERIC_CMP(sid1->id_auth[i], sid2->id_auth[i]);
+		}
 
 	return 0;
 }
@@ -71,9 +73,9 @@ int dom_sid_compare(const struct dom_sid *sid1, const struct dom_sid *sid2)
 		return 1;
 
 	/* Compare most likely different rids, first: i.e start at end */
-	if (sid1->num_auths != sid2->num_auths)
-		return sid1->num_auths - sid2->num_auths;
-
+	if (sid1->num_auths != sid2->num_auths) {
+		return NUMERIC_CMP(sid1->num_auths, sid2->num_auths);
+	}
 	for (i = sid1->num_auths-1; i >= 0; --i) {
 		if (sid1->sub_auths[i] < sid2->sub_auths[i]) {
 			return -1;
diff --git a/selftest/knownfail-32bit b/selftest/knownfail-32bit
index 2946f3e9936..8ab625d969e 100644
--- a/selftest/knownfail-32bit
+++ b/selftest/knownfail-32bit
@@ -65,14 +65,8 @@
 # [171(1386)/261 at 6m24s, 4 errors] samba4.local.charset
 # UNEXPECTED(failure): samba4.local.charset.strcasecmp(none)
 # REASON: Exception: Exception: ../../lib/util/charset/tests/charset.c:56: strcasecmp("foo", "bar") was 1 (0x1), expected 4 (0x4): different strings both lower
-# UNEXPECTED(failure): samba4.local.charset.strcasecmp_m(none)
-# REASON: Exception: Exception: ../../lib/util/charset/tests/charset.c:85: strcasecmp_m(file_iso8859_1, file_utf8) was 1 (0x1), expected 38 (0x26): file.{accented e}
-#  should differ
 # UNEXPECTED(failure): samba4.local.charset.strncasecmp(none)
 # REASON: Exception: Exception: ../../lib/util/charset/tests/charset.c:132: strncasecmp("foo", "bar", 3) was 1 (0x1), expected 4 (0x4): different strings both lower
-# UNEXPECTED(failure): samba4.local.charset.strncasecmp_m(none)
-# REASON: Exception: Exception: ../../lib/util/charset/tests/charset.c:167: strncasecmp_m(file_iso8859_1, file_utf8, 6) was 1 (0x1), expected 38 (0x26): file.{accent
-# ed e} should differ
 # command:  /home/samba/samba.git/bin/smbtorture  $LOADLIST --configfile=$SMB_CONF_PATH --option='fss:sequence timeout=1' --maximum-runtime=$SELFTEST_MAXTIME --based
 # ir=$SELFTEST_TMPDIR --format=subunit --option=torture:progress=no --target=samba4 ncalrpc:localhost local.charset 2>&1  | python3 /home/samba/samba.git/selftest/fi
 # lter-subunit --fail-on-empty --prefix="samba4.local.charset." --suffix="(none)"
@@ -82,9 +76,7 @@
 # ERROR: Testsuite[samba4.local.charset]
 # REASON: Exit code was 1
 ^samba4.local.charset.strcasecmp.none
-^samba4.local.charset.strcasecmp_m.none
 ^samba4.local.charset.strncasecmp.none
-^samba4.local.charset.strncasecmp_m.none
 #
 # [229(2702)/261 at 8m44s, 5 errors] samba.tests.samba_tool.provision_lmdb_size
 # UNEXPECTED(failure): samba.tests.samba_tool.provision_lmdb_size.samba.tests.samba_tool.provision_lmdb_size.ProvisionLmdbSizeTestCase.test_134217728b(none)
diff --git a/source3/lib/util_tdb.c b/source3/lib/util_tdb.c
index d85f676fbcf..3c7c1945f58 100644
--- a/source3/lib/util_tdb.c
+++ b/source3/lib/util_tdb.c
@@ -324,11 +324,11 @@ int tdb_data_cmp(TDB_DATA t1, TDB_DATA t2)
 		return 1;
 	}
 	if (t1.dptr == t2.dptr) {
-		return t1.dsize - t2.dsize;
+		return NUMERIC_CMP(t1.dsize, t2.dsize);
 	}
 	ret = memcmp(t1.dptr, t2.dptr, MIN(t1.dsize, t2.dsize));
 	if (ret == 0) {
-		return t1.dsize - t2.dsize;
+		return NUMERIC_CMP(t1.dsize, t2.dsize);
 	}
 	return ret;
 }
diff --git a/source3/libsmb/libsmb_xattr.c b/source3/libsmb/libsmb_xattr.c
index dcb2f9e74a7..a9023419376 100644
--- a/source3/libsmb/libsmb_xattr.c
+++ b/source3/libsmb/libsmb_xattr.c


-- 
Samba Shared Repository



More information about the samba-cvs mailing list