Search code examples
arrayscstringpointerschar

Search and get the first string and index from a string arrays in C


I need to get the first item from an string arrays in C, this is my code:

#include <stdio.h>
#include <string.h>

int main() {
    char *codes[16] = {
        "VVVV", "VVVB", "VVBV", "VVBB", "VBVV", "VBVB", "VBBV", "VBBB",
        "BVVV", "BVVB", "BVBV", "BVBB", "BBVV", "BBVB", "BBBV", "BBBB"
    };
    char code[4];
    int ret = 0;
    int j = 0;

    printf("Enter code to search: ");
    scanf("%s", code);
    
    for (j = 0; j < 16; j++) {
        printf("\ncode to search is:  %s, j value: %d, codes[j]: %s",
               code, j, codes[j]);  
        ret = strcmp(code, codes[j]);
        if (ret == 0) {
            printf("\nValue of index: %d\n", j);
        }
    }
}

When I enter the first code to search (VVVV) I get a void value in position 0, and It doesn't return the index 0. Another values works but the first doesn't.

This is the output:

Enter code to search: VVVV

code to search is:  VVVV, j value: 0, codes[j]: 
code to search is:  VVVV, j value: 1, codes[j]: VVVB
code to search is:  VVVV, j value: 2, codes[j]: VVBV
code to search is:  VVVV, j value: 3, codes[j]: VVBB
code to search is:  VVVV, j value: 4, codes[j]: VBVV
code to search is:  VVVV, j value: 5, codes[j]: VBVB
code to search is:  VVVV, j value: 6, codes[j]: VBBV
code to search is:  VVVV, j value: 7, codes[j]: VBBB
code to search is:  VVVV, j value: 8, codes[j]: BVVV
code to search is:  VVVV, j value: 9, codes[j]: BVVB
code to search is:  VVVV, j value: 10, codes[j]: BVBV
code to search is:  VVVV, j value: 11, codes[j]: BVBB
code to search is:  VVVV, j value: 12, codes[j]: BBVV
code to search is:  VVVV, j value: 13, codes[j]: BBVB
code to search is:  VVVV, j value: 14, codes[j]: BBBV
code to search is:  VVVV, j value: 15, codes[j]: BBBB

What could be wrong?


Solution

  • Your code has a buffer overflow, which is a very dangerous kind of undefined behaviour.

    The following line

    char code[4];
    

    declares an array of char that can hold up to 3 characters plus a null-terminator character, which add up to 4 characters total. This is because C strings are null-terminated.

    When you attempt to scan a 4 character string (don't forget the 5th \0 that's added automatically) into a 3 character buffer (plus the 4th \0), your code overflows. Therefore, you need to change the line above to

    char code[5];
    

    That said, your code is far from being trouble-safe. And yes, I mean that scanf() call. I suggest you read this post as it explains the pitfalls of that function, and provides alternative solutions.

    Here is a better version of your code:

    #include <stdio.h>
    #include <stdbool.h>
    #include <string.h>
    
    int main(void)
    {
        char *codes[] = { // Let your array be flexible in case you want to add to it later.
            "VVVV", "VVVB", "VVBV", "VVBB",
            "VBVV", "VBVB", "VBBV", "VBBB",
            "BVVV", "BVVB", "BVBV", "BVBB",
            "BBVV", "BBVB", "BBBV", "BBBB"
        };
        
        // Computes the size (number of items) of an array object.
        // Doesn't work for pointers to arrays.
        // Also, use size_t as it's the appropriate type for sizes.
        size_t ncodes = sizeof(codes) / sizeof(codes[0]);
        
        char code[5]; // <-- 4 characters + \0
        printf("Enter code to search: ");
        
        if (scanf(" %4[^\n]", code) != 1) {
            printf("Error: scanf() failed.\n");
            return 1;
        }
        
        bool found = false;
        
        for(size_t j = 0; j < ncodes; ++j) {
            if (strcmp(code, codes[j]) == 0) {
                printf("Code found at index: %zu\n", j);
                found = true;
                break; // Stop looping when you find the first occurence
            }
        }
        
        if (!found) {
            printf("Code %s not found.\n", code);
        }
    }