Skip to content

StrEndsWith

Description

Check whether a Str ends with a suffix.

Three call shapes via OVERLOAD + _Generic on suffix: StrEndsWith(s, suffix)suffix is Str * or Zstr. StrEndsWith(s, suffix, suffix_len)suffix is a fixed-length view (Zstr, size).

Parameters

Name Direction Description
s in Str to check.
suffix in Candidate suffix (Str * / Zstr).
suffix_len in Length of suffix when using the 3-arg fixed-length form.

Success

Returns true when s ends with suffix. The string is not modified.

Failure

Returns false. The string is not modified.

Usage example (Cross-references)

Usage examples (Cross-references)
    // Test string starts/ends with functions
    bool test_str_starts_ends_with(void) {
        WriteFmt("Testing StrStartsWith and StrEndsWith variants\n");
        DefaultAllocator alloc = DefaultAllocatorInit();
    
        // Test Str-form
        result = result && StrEndsWith(&s, &suffix);
    
        // Test Zstr-form (string literal)
    
        // Test Zstr-form (string literal)
        result = result && StrEndsWith(&s, "World");
        result = result && !StrEndsWith(&s, "Hello");
        // Test Zstr-form (string literal)
        result = result && StrEndsWith(&s, "World");
        result = result && !StrEndsWith(&s, "Hello");
    
        // Test Cstr-form (fixed-length view)
    
        // Test Cstr-form (fixed-length view)
        result = result && StrEndsWith(&s, "orld", 4);
        result = result && !StrEndsWith(&s, "ello", 4);
        // Test Cstr-form (fixed-length view)
        result = result && StrEndsWith(&s, "orld", 4);
        result = result && !StrEndsWith(&s, "ello", 4);
    
        StrDeinit(&s);
    // with "World" must be true.
    static bool test_str_ends_with_str_true(void) {
        WriteFmt("Testing StrEndsWith reports true on a match and false on a non-match\n");
        DefaultAllocator alloc = DefaultAllocatorInit();
        // A genuine suffix must report true...
        Str  suffix = StrInitFromZstr("World", &alloc);
        bool match  = StrEndsWith(&s, &suffix); // Str* -> str_ends_with_str
        // ...and a non-suffix must report false. The replace_scalar_call mutant
        // forces the return to the constant 42 (true), so this false case is what
        // actually pins the call's result.
        Str  nonsuffix = StrInitFromZstr("Hello", &alloc);
        bool no_match  = StrEndsWith(&s, &nonsuffix);
    
        bool result = match && (no_match == false);
    //   mutant : equal lengths fail the `>` test -> false.
    static bool test_ends_with_full_length_suffix(void) {
        WriteFmt("Testing StrEndsWith matches a whole-string suffix (441:21)\n");
        DefaultAllocator alloc = DefaultAllocatorInit();
        Str s = StrInitFromZstr("World", &alloc);
    
        bool result = (StrEndsWith(&s, "World") == true);
        if (!result) {
            WriteFmt("    FAIL: expected true for suffix equal to the whole string\n");
    // corrupted s must abort before s->data/s->length are read (Str.Mutants5).
    static bool test_str_ends_with_str_corrupt_s_aborts(void) {
        WriteFmt("Testing StrEndsWith validates s (should abort)\n");
        DefaultAllocator alloc = DefaultAllocatorInit();
        MAGIC_MARK_DIRTY(&s);
    
        (void)StrEndsWith(&s, &suffix); // should abort here
    
        return false;                   // unreachable on real code
    // NULL s must abort cleanly via validate_vec's NULL check (Str.Mutants5).
    static bool test_str_ends_with_zstr_null_aborts(void) {
        WriteFmt("Testing StrEndsWith(zstr) validates a NULL s (should abort)\n");
    
        (void)StrEndsWith((const Str *)NULL, "x"); // Zstr suffix -> str_ends_with_zstr
        WriteFmt("Testing StrEndsWith(zstr) validates a NULL s (should abort)\n");
    
        (void)StrEndsWith((const Str *)NULL, "x"); // Zstr suffix -> str_ends_with_zstr
    
        return false;                              // unreachable on real code
    // the validator's NULL check rather than dereferencing s->data (Str.Mutants7).
    static bool test_ends_with_cstr_validates(void) {
        WriteFmt("Testing StrEndsWith (Cstr form) validates its Str (deadend)\n");
    
        bool ends = StrEndsWith((const Str *)NULL, "x", 1);
        WriteFmt("Testing StrEndsWith (Cstr form) validates its Str (deadend)\n");
    
        bool ends = StrEndsWith((const Str *)NULL, "x", 1);
        (void)ends;
Last updated on