SIGSEGV, Segmentation Fault with C ++ in Code :: Blocks

1

I am adding nodes to a simple linked list, the nodes save two double values.

When I debug the program in Code::Blocks I get an error that says:

"Program received signal SIGSEGV, Segmentation fault." 

Then it tells me which section of the code has detected the problem, is when I try to call a function that adds a node from another that indicates how many times it should do it.

The debugger shows the error twice and then says that the program went down. This error does not prevent the program from running, but I think it is causing some later things not to work as they should. How could I fix it?

I followed the recommendation to remove a pointer as a global variable, besides taking care of details to avoid being null, the error lasts, the code goes like this now:

In main the important lines are the following:

Nodo *cls_val;
Nodo *n0 = new Nodo;
cls_val = n0;
n0->info = "Inicio de la lista";
Rangos(cls_val);

The Rangos function is like this:

void Rangos(Nodo *cb)
{
    double mini = 1;
    for(int i = 0; i < clss; i++)
    {
        cb = Agr_Rango(mini, mini+anch, cb);
        cb = cb->sig;
        mini += anch;
    }
}

Finally, the famous Agr_Rangos where the conflicting line is:

Nodo* Agr_Rango(double mnm, double mxm, Nodo *cab)
{
    Nodo *ni, *ptr;
    ni = new Nodo;
    ni->mn = mnm;
    ni->mx = mxm;
    ptr = cab;
    if(ptr == NULL)
    {
        cab = ni;
    }
    else
    {
        while(ptr->sig != NULL) //Aquí señala el problema.
            ptr = ptr->sig;
        ptr->sig = ni;
    }
    return ptr;
}
    
asked by Karman 12.04.2016 в 04:10
source

1 answer

0

SIGSEGV is the error that the system throws when trying to access invalid memory.

Here you can see details in MSDN (English) and here details on Wikipedia.

So, at the moment when ptr->sig throw SIGSEGV , variable ptr is pointing to invalid memory. The variable ptr has been assigned in previous lines with the content of cls_val which, you mention that it is a global variable.

Check the following:

  • cls_val has been initialized correctly before being used.
  • cls_val contains valid values when assigned to ptr .
  • cls_val does not point to NULL , nullptr or 0 when assigned to ptr .
  • cls_val is not accessed from another thread simultaneously to access made from Agr_Rango .
  • cls_val is not confused with another local variable of the same name in another context.

On the other hand, avoids the use of global variables as much as possible:

  • Lack of location : The code is easier to understand when its scope is limited. Global variables can be read or modified from any part of the program, this makes it difficult to reason about their use or remember all the points in which they are used.
  • They lack access control or restriction verification : A global variable can be read or written from anywhere in the program, several rules about its use can be forgotten or violated.
  • Concurrency problems : If global variables can be accessed from multiple threads, it is necessary to synchronize them. When working with dynamically linked modules that use global variables, the resulting system may not be secure even when the modules are independent.
  • Namespace pollution : Global variables are in all contexts. You can end up using a global variable when you thought you were using a local or vice versa! (either by ignorance, misspelling the name or forgetting to create the local variable). Also, if you link modules with global variables whose name is the same, if you are lucky, you will have link errors ... if you are not lucky the linker will consider the variables as the same even if it was not your intention.
  • More link problems (in English) : I translated the points that I thought were most relevant to your problem.

If you want a more detailed solution, I'm afraid we'll need the full code.

Edited

The problem could be in the functions Rangos and Agr_Rango in which you pass the pointer to use per copy ; let's see as an example the Rangos function (because it's shorter):

void Rangos(Nodo *cb)
{
    double mini = 1;
    for(int i = 0; i < clss; i++)
    {
        cb = Agr_Rango(mini, mini+anch, cb);
        cb = cb->sig;
        mini += anch;
    }
}

The cb parameter is a copy of the cls_val pointer, so when you initialize it to the value of Agr_Rango what you are modifying is not the cls_val external% if not your copy ; to get the functionality you expect, you must pass a pointer to a pointer or a pointer reference:

Nodo *cls_val;
Nodo *n0 = new Nodo;
cls_val = n0;
n0->info = "Inicio de la lista";
Rangos(&cls_val); // <--- pasar como PUNTERO!!

void Rangos(Nodo **cb) // <--- puntero a puntero
{
    double mini = 1;
    for(int i = 0; i < clss; i++)
    {
        *cb = Agr_Rango(mini, mini+anch, cb); // <-- modificar valor apuntado
        *cb = (*cb)->sig;                     // <-- modificar valor apuntado
        mini += anch;
    }
}

I personally prefer the pointer reference version:

Nodo *cls_val;
Nodo *n0 = new Nodo;
cls_val = n0;
n0->info = "Inicio de la lista";
Rangos(cls_val); // <--- No requiere cambio alguno

void Rangos(Nodo *&cb) // <--- referencia!
{
    double mini = 1;
    for(int i = 0; i < clss; i++)
    {
        cb = Agr_Rango(mini, mini+anch, cb); // <--- No requiere cambio
        cb = cb->sig;                        // <--- No requiere cambio
        mini += anch;
    }
}

You should make this change in both Rangos and Agr_Rango . You can see a simplified example of what I think is your problem here :

void puntero(int *parametro)
{
    parametro = new int{456};
}

void puntero_a_puntero(int **parametro)
{
    *parametro = new int{789};
}

void referencia_a_puntero(int *&parametro)
{
    parametro = new int{111};
}

int *p = new int{123};

// p no es mocificado, sigue apuntando al valor 123, no a 456
puntero(p);
// p es modificado por puntero, apunta al valor 789
puntero_a_puntero(&p);
// p es modificado por referencia, apunta al valor 111
referencia_a_puntero(p);

PS: I already know that my example has memory leaks, it's just an example.

    
answered by 13.04.2016 / 09:21
source