0

This simple program creates a linked list that has an acronym and its complete phrase. There are two functions:

The first one creates a node and if the list is empty it puts the node in the first place, otherwise it is put at the end of the list

void createNode(struct node **list, char *siglaElem, char *parolaElem) {
    struct node *new_node;
    new_node = malloc(sizeof(struct node));
    strcpy(new_node->sigla,siglaElem);
    strcpy(new_node->parola,parolaElem);
    new_node->next = NULL;

    if (*list == NULL) {
        *list = new_node;
    } else {
        while ((*list) != NULL) {
            (*list) = (*list)->next;
        }
        (*list)->next = new_node;
    }
}

The second function scans the entire list.

int scanList(struct node **list, char *siglaElem, char *parolaElem) {
    struct node *scroll = *list;
    for (; scroll != NULL; scroll = scroll->next) {
        if (strcmp(scroll->sigla, siglaElem) == 0) {
            if (strcmp(scroll->parola, parolaElem) == 0)
                return 1;
            else 
                return 2;
        }
    }
    createNode(list, siglaElem, parolaElem);
    return 0;
}
  • It returns 1 if it finds the same acronym and phrase in the list
  • It returns 2 if it finds a node with the same acronym but a different phrase
  • Finally it returns 0 if there is no node with the same acronym in the list, it calls the first function and it creates one.

The main() function

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

struct node {
    char *sigla;
    char *parola;
    struct node *next;
};

int scanList(struct node **list, char *sigla, char *parola);
void createNode(struct node **list, char *siglaElem, char *parolaElem);

int main() {
    struct node *first = NULL;
    createNode(&first, "SI", "Sistema Informatico");
    createNode(&first, "OS", "Operating System");
    printf("%d %d\n", scanList(&first, "SI", "Sistema Informatico"), scanList(&first, "OS", "Operating System"));
    return 0;
}

I can't understand why I'm getting Segmentation Fault: 11

What I think is that I'm doing something wrong with the loops. Any solution?

Mattia Righetti
  • 1,265
  • 1
  • 18
  • 31

2 Answers2

1

There is an error inside createNode on the else clause you advance the list until (*list) points to NULL and after that you dereference (*list) with the -> operator but as we said it points to NULL already. There could be more errors this is just a quick observation to get you going. If you're working on linux I've recently discovered a user friendly debugger called Nemiver give it a spin.

arpl
  • 3,505
  • 3
  • 18
  • 16
1

There are two errors in your createNode function, the first one is that you didn't allocate memory for sigla and parola, the second error is that you change the main pointer of your list.

Solution:

 void createNode(struct node **list, char *siglaElem, char *parolaElem) {

    struct node *new_node;
    struct node *tmp;

    new_node = malloc(sizeof(struct node));
    new_node->sigla = malloc(sizeof(char) * (strlen(siglaElem)+1));
    new_node->parola = malloc(sizeof(char) * (strlen(parolaElem)+1));

    strcpy(new_node->sigla, siglaElem);
    strcpy(new_node->parola, parolaElem);
    new_node->next = NULL;

    if (*list == NULL) {
       *list = new_node;
    } else {
       tmp = *list;
       while (tmp->next != NULL)
          tmp = tmp->next;
       tmp->next = new_node;
    }
}

I didn't check the return of malloc but do it to be sure that your variable was correctly allocated, and you can also use gdb or valgrind to debug your code :) !

ar-ms
  • 735
  • 6
  • 14
  • Can you explain me why the program does execute properly even if I don't allocate memory for the two strings sigla and parola? Isn't that already included in the struct node? – Mattia Righetti Feb 15 '16 at 00:19
  • 1
    It's purely due to chance, it works fine because the memory used by strcpy to copy the string was in an authorized memory domain for your program or your OS is not restrictive, but it's not always the case and will result in segmentation fault in majority cases. – ar-ms Feb 15 '16 at 00:29
  • Got it. Just one more question. What should I change if the struct's parola and sigla were arrays like: char sigla[2] and char parola[20]? – Mattia Righetti Feb 15 '16 at 00:33
  • 1
    Use the macro #define to set the size, it's avoid you to have have hardcoded number all around so if you decide to change the size you just need to modify this define.Don't forget to add 1, sigla[2] becomes sigla[3] the same for parola, use the function memset to set all the content off the array to 0 like this memset(new_node->sigla, 0, 3) and now you don't need to allocate memory for sigla and parola using malloc. – ar-ms Feb 15 '16 at 00:45