Thread: Strcmp causes segmentation fault

  1. #1
    Registered User
    Join Date
    Dec 2020
    Posts
    9

    Strcmp causes segmentation fault

    I'm currently doing a hash search program. Here is the following code.
    Code:
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <math.h>
    
    #define M 12
    #define N 467 
    
    /*
    size of hash table is 467
    Which is a prime number and in form of 4(j)+3
    j=116
    4*116+3=467
    So suitable for square probe hashing
    */
    
    typedef struct student{
        char name[50];
        char sex[10];
        char number[M];
    }ST;
    
    void initTable(ST *A);
    void readFromFile(ST *A);
    int hashFun(char *number);
    void query(ST *A, char *number);//search
    int getPrime(int n);
    
    void initTable(ST *A){
        for(int i=0;i<N;i++){
            strcpy(A[i].name,"-");
            strcpy(A[i].sex,"-");
            strcpy(A[i].number,"-");
        }
    }
    
    int hashFun(char *number){
        /*FOLDING METHOD*/
        /*3digit+3digit+3digit+2*/
        int temp,hashNum=0;
        for(int i=0;i<M-2;i++){
            temp=0;
            temp+=(number[i]-'0');
            if(i+1<M-1){
                temp*=10;
                temp+=(number[++i]-'0');
                if(i+1<M-1){
                    temp*=10;
                    temp+=(number[++i]-'0');
                }
            }
            hashNum+=temp;
        }
        //printf("%s\t%d\t%d\n",number,hashNum,hashNum%N);
        return hashNum%N;
    }
    
    void readFromFile(ST *A){
        ST temp;
        FILE *file;
        file = fopen("data4.txt","r");
        int rehash=0;
        while(fscanf(file,"%s %s %s",temp.name,temp.sex,temp.number)>0){
            int index=hashFun(temp.number);
            int tempRehash=0;
            if(A[index].number[0]=='-'){
                strcpy(A[index].name,temp.name);
                strcpy(A[index].sex,temp.sex);
                strcpy(A[index].number,temp.number);
            }
            else{
                int n=1;
                int tempIndexLeft=index-(n*n)%N;
                int tempIndexRight=index+(n*n)%N;
                while( !(A[tempIndexLeft].number[0]=='-' || A[(tempIndexRight)%N].number[0]=='-' ) ){
                    n++;
                    tempIndexLeft=index-(n*n)%N;
                    tempIndexRight=index+(n*n)%N;
                    tempRehash++;
                }
                if(A[(index+(n*n))%N].number[0]=='-')
                    index=(index+(n*n))%N;
                else
                    index=(index-(n*n))%N;
                strcpy(A[index].name,temp.name);
                strcpy(A[index].sex,temp.sex);
                strcpy(A[index].number,temp.number);      
            }
            if(rehash<tempRehash)
                rehash=tempRehash;
        }
        printf("\nHash table built successfully.\n");
        printf("Maximum rehash time: %d\n",rehash);
        
    }
    
    void query(ST *A, char *number){
        printf("test");
        char exitCondition[]="-";
        int index=hashFun(number);
        int rehash =0; //+1 for first hash later
        //int boolFound=0;//current false
    
        int tempIndexLeft=index-(rehash*rehash)%N;
        int tempIndexRight=index+(rehash*rehash)%N;
        printf("%d\t%d",tempIndexLeft,tempIndexRight);
        while( !(strcmp(A[tempIndexLeft].number,number)==0 || strcmp(A[tempIndexRight].number,number)==0) ){
            rehash++;
            //printf("test");
            if(strcmp(A[tempIndexLeft].number,"-")!=0)
                tempIndexLeft=index-(rehash*rehash)%N;
            if(strcmp(A[tempIndexRight].number,"-")!=0)
                tempIndexRight=index+(rehash*rehash)%N;
            
            if(strcmp(A[tempIndexLeft].number,exitCondition)==0 && strcmp(A[tempIndexRight].number,exitCondition)==0)
                break;
        }
    
        printf("After %d time(s) hash,",rehash+1);
        if(strcmp(A[tempIndexLeft].number, number)==0){
            printf("Record found:\n%s %s %s\n",A[tempIndexLeft].name,A[tempIndexLeft].sex,A[tempIndexLeft].number);
        }
        else if(strcmp(A[tempIndexRight].number, number)==0){
            printf("Record found:\n%s %s %s\n",A[tempIndexRight].name,A[tempIndexRight].sex,A[tempIndexRight].number);
        }
        else{
            printf("Record not found.\n");
        }
        
    }
    
    int main(){
        ST A[N];
        char phoneNumberInput[M];
        char exitConditon[]={"0"};
        initTable(A);
        readFromFile(A);
    
        //for(int i=0;i<N;i++){
        //    printf("%s %s %s\n",A[i].name,A[i].sex,A[i].number);
        //}
        //if(strcmp(A[0].number,"13267729168")==0)
        //    printf("True");
        while(1){
            printf("\nPlease input phone number: ");
            scanf("%s",phoneNumberInput);
            printf("test");
            if(strcmp(phoneNumberInput,exitConditon)==0)
                break;
            printf("test");
            query(A,phoneNumberInput);
        }
    }
    data4.txt
    and this is the input that cause that segmentation fault:
    18638110371
    There are some other input that causes the same problem.
    GDB shows that the query were actually called, but I put some printf("test") and it wont print on the console. And gdb cannot show tempIndexLeft and tempIndexRight value at all.

  2. #2
    Registered User
    Join Date
    May 2009
    Posts
    4,183
    This is wrong!

    Code:
    char exitConditon[]={"0"};
    You need an zero terminated character array to use as an C-String!

    "0" is not equal to 0

    Tim S.
    "...a computer is a stupid machine with the ability to do incredibly smart things, while computer programmers are smart people with the ability to do incredibly stupid things. They are,in short, a perfect match.." Bill Bryson

  3. #3
    Registered User
    Join Date
    Dec 2020
    Posts
    9
    You need an zero terminated character array to use as an C-String!
    so make it
    Code:
    exitCondition[]={'0','\0'} ?

  4. #4
    Registered User
    Join Date
    Dec 2020
    Posts
    9
    It does not fix the problem

  5. #5
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,659
    My gdb works fine.
    Code:
    $ gcc -Wall -Wextra -g foo.c
    $ gdb -q ./a.out
    GNU gdb (Ubuntu 7.11.1-0ubuntu1~16.5) 7.11.1
    Reading symbols from ./a.out...done.
    (gdb) run
    Starting program: ./a.out 
    
    Hash table built successfully.
    Maximum rehash time: 37
    
    Please input phone number: 18838010228
    testtesttest231	231After 13 time(s) hash,Record found:
    SunWeifeng Male 18838010228
    
    Please input phone number: 18638110371
    
    Program received signal SIGSEGV, Segmentation fault.
    __strcmp_sse2_unaligned () at ../sysdeps/x86_64/multiarch/strcmp-sse2-unaligned.S:31
    31	../sysdeps/x86_64/multiarch/strcmp-sse2-unaligned.S: No such file or directory.
    (gdb) bt
    #0  __strcmp_sse2_unaligned () at ../sysdeps/x86_64/multiarch/strcmp-sse2-unaligned.S:31
    #1  0x0000000000400fc1 in query (A=0x7fffffff5ad0, number=0x7fffffffde40 "18638110371") at foo.c:107
    #2  0x0000000000401211 in main () at foo.c:151
    (gdb) up
    #1  0x0000000000400fc1 in query (A=0x7fffffff5ad0, number=0x7fffffffde40 "18638110371") at foo.c:107
    107	    while( !(strcmp(A[tempIndexLeft].number,number)==0 || strcmp(A[tempIndexRight].number,number)==0) ){
    (gdb) info locals
    exitCondition = "-"
    index = 274
    rehash = 16
    tempIndexLeft = 18
    tempIndexRight = 530
    (gdb) p number
    $1 = 0x7fffffffde40 "18638110371"
    (gdb) p A[tempIndexLeft]
    $2 = {name = "DuWei", '\000' <repeats 44 times>, sex = "Male\000\000\000\000\000", number = "18997317285"}
    (gdb) p A[tempIndexRight]
    Cannot access memory at address 0x7ffffffff000
    (gdb)
    Your tempIndexRight is off in the weeds somewhere.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  6. #6
    Registered User
    Join Date
    Dec 2020
    Posts
    9
    Code:
     gcc -g -Wall -Wextra topic4.c
     gdb -q ./a.out
    Reading symbols from ./a.out...
    (gdb) run
    Starting program:a.out
    
    
    Hash table built successfully.
    Maximum rehash time: 37
    
    
    Please input phone number: 13910626566
    After 3 time(s) hash,Record found:
    DongShichen Male 13910626566
    
    
    Please input phone number: 18099507992
    
    
    Program received signal SIGSEGV, Segmentation fault.
    __strcmp_avx2 () at ../sysdeps/x86_64/multiarch/strcmp-avx2.S:101
    101     ../sysdeps/x86_64/multiarch/strcmp-avx2.S: No such file or directory.
    (gdb) bt
    #0  __strcmp_avx2 () at ../sysdeps/x86_64/multiarch/strcmp-avx2.S:101
    #1  0x0000555555555a40 in query (A=0x7fffffff5ef0, numberInput=0x7fffffffe24c "18099507992") at topic4.c:107
    #2  0x0000555555555c9b in main () at topic4.c:151
    (gdb) p number
    No symbol "number" in current context.
    (gdb) info locals
    No locals.
    (gdb)
    Do you know what make my gdb not getting any of that info ?
    Last edited by StackEverFlow; 12-25-2020 at 10:16 AM.

  7. #7
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,659
    You need to compile with "-g" if you want anything other than very basic information out of gdb.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  8. #8
    Registered User
    Join Date
    Dec 2017
    Posts
    1,628
    It looks like he did use the -g option on the gcc command, but he forgot the "up" command to get to the correct stack frame.
    A little inaccuracy saves tons of explanation. - H.H. Munro

  9. #9
    Registered User
    Join Date
    Sep 2020
    Posts
    150
    When I ran the code in VS 2019 I got an exception at line 85
    Code:
    strcpy(A[index].name, temp.name);
    when index was -307.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. In GDB no segmentation fault but while running segmentation fault
    By Tamim Ad Dari in forum C++ Programming
    Replies: 2
    Last Post: 12-10-2013, 11:16 AM
  2. segmentation error on a strcmp
    By newbie73 in forum C Programming
    Replies: 7
    Last Post: 05-05-2011, 09:45 PM
  3. struct, string, strcmp(), and "segmentation fault"
    By Roger in forum C Programming
    Replies: 10
    Last Post: 11-07-2009, 10:45 PM
  4. seg fault with strcmp
    By samps005 in forum C Programming
    Replies: 2
    Last Post: 05-04-2003, 04:32 PM
  5. segmentation fault and memory fault
    By Unregistered in forum C Programming
    Replies: 12
    Last Post: 04-02-2002, 11:09 PM

Tags for this Thread