Error adding item to the stack

0

I have a structure Pila that saves structures of type CD , but when adding a CD to the stack, the program crashes.

From what I see it is at the moment of adding a CD to the stack, I do not know if my code is ok. I use pointers. The function receives a pointer that points to a Pila , and another that points to a CD .

I have modified several things but they do not solve my problem.

CODE:

typedef struct{ 
    char titulo[50];
    char autor[50];
    float duracion;
    int numeroCan;
}CD;

typedef struct{
    int top;
    CD cds[tamanio];
}Pila;

//Funcion para agregar un CD a la pila
void Push(Pila *ptrPila, CD *ptrCD){
    if(Full(ptrPila)){ //Verifica si la pila está llena

        printf("Pila desbordada");  

    }   
    else{//Agrega el CD a la pila
              ptrPila->cds[++(ptrPila->top)]=*ptrCD;
        printf("CD Agregado!!");

        printf("\nNombre del CD: %s",ptrCD->titulo);

    }
}
    
asked by Eduardo Reyes 28.09.2017 в 17:47
source

1 answer

0

Everything points to that at no time you have initialized the values of the structure Pila passed to the function, in particular the value of top .

For this reason top can have a random number (possibly negative, so that the call to Full fails you) that is forcing you to write in a memory area outside the scope of your program.

You could initialize the value in two different ways:

/* Definimos una pila con el valor "top" a cero */
Pila pila = { 0 };
/* También podríamos haberlo hecho así tras definirlo: */
pila.top = 0;

This would be a proof of concept with the problem solved:

#include<stdio.h>

#define tamanio 10

typedef struct{
    char titulo[50];
    char autor[50];
    float duracion;
    int numeroCan;
}CD;

typedef struct{
    int top;
    CD cds[tamanio];
}Pila;

/* Funcion para agregar un CD a la pila */
void Push(Pila *ptrPila, CD *ptrCD){
    if(ptrPila->top > tamanio){
        printf("Pila desbordada");
    } else { /* Agrega el CD a la pila */
        ptrPila->cds[++(ptrPila->top)]=*ptrCD;
        printf("CD Agregado!!");
        printf("\nNombre del CD: %s\n",ptrCD->titulo);
    }
}

int main() {
    /* Definimos el contenido de un CD */
    CD cd = { "Título", "Autor", 10.0, 5 };
    /* Definimos una pila con el valor "top" a cero */
    Pila pila = { 0 };
    /* También podríamos haberlo hecho así tras definirlo: */
    pila.top = 0;
    Push(&pila, &cd);
    return 0;
}

Your valgrind exit:

$ valgrind ./pr 
==15904== Memcheck, a memory error detector
==15904== Copyright (C) 2002-2013, and GNU GPL'd, by Julian Seward et al.
==15904== Using Valgrind-3.10.1 and LibVEX; rerun with -h for copyright info
==15904== Command: ./pr
==15904== 
CD Agregado!!
Nombre del CD: Título
==15904== 
==15904== HEAP SUMMARY:
==15904==     in use at exit: 0 bytes in 0 blocks
==15904==   total heap usage: 0 allocs, 0 frees, 0 bytes allocated
==15904== 
==15904== All heap blocks were freed -- no leaks are possible
==15904== 
==15904== For counts of detected and suppressed errors, rerun with: -v
==15904== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)

Before solving the problem this was the output of valgrind :

$ valgrind ./pr 
==15688== Memcheck, a memory error detector
==15688== Copyright (C) 2002-2013, and GNU GPL'd, by Julian Seward et al.
==15688== Using Valgrind-3.10.1 and LibVEX; rerun with -h for copyright info
==15688== Command: ./pr
==15688== 
==15688== Use of uninitialised value of size 8
==15688==    at 0x4005EC: Push (in /tmp/pr)
==15688==    by 0x4006AC: main (in /tmp/pr)
==15688== 
==15688== Invalid write of size 8
==15688==    at 0x4005EC: Push (in /tmp/pr)
==15688==    by 0x4006AC: main (in /tmp/pr)
==15688==  Address 0x120f648b60 is not stack'd, malloc'd or (recently) free'd
==15688== 
==15688== 
==15688== Process terminating with default action of signal 11 (SIGSEGV)
==15688==  Access not within mapped region at address 0x120F648B60
==15688==    at 0x4005EC: Push (in /tmp/pr)
==15688==    by 0x4006AC: main (in /tmp/pr)
==15688==  If you believe this happened as a result of a stack
==15688==  overflow in your program's main thread (unlikely but
==15688==  possible), you can try to increase the size of the
==15688==  main thread stack using the --main-stacksize= flag.
==15688==  The main thread stack size used in this run was 8388608.
==15688== 
==15688== HEAP SUMMARY:
==15688==     in use at exit: 0 bytes in 0 blocks
==15688==   total heap usage: 0 allocs, 0 frees, 0 bytes allocated
==15688== 
==15688== All heap blocks were freed -- no leaks are possible
==15688== 
==15688== For counts of detected and suppressed errors, rerun with: -v
==15688== Use --track-origins=yes to see where uninitialised values come from
==15688== ERROR SUMMARY: 2 errors from 2 contexts (suppressed: 0 from 0)

In particular you should look at the errors:

==15688== Use of uninitialised value of size 8
==15688==    at 0x4005EC: Push (in /tmp/pr)
==15688==    by 0x4006AC: main (in /tmp/pr)
==15688== 
==15688== Invalid write of size 8
==15688==    at 0x4005EC: Push (in /tmp/pr)
==15688==    by 0x4006AC: main (in /tmp/pr)
==15688==  Address 0x120f648b60 is not stack'd, malloc'd or (recently) free'd

That they tell you that you have made use of an uninitialized value and that you have written in a memory area that is not on the stack, neither hosted nor recently released.

    
answered by 29.09.2017 в 08:41