Segment Violation

2

The problem is that when executing the program it produces a segment violation and I can not find the reason why. The goal is to reach the "error detectado en la tabla" line

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

#define SIZE 1000

struct data_unit{
   int data;
   struct data_unit *next;
 };
 typedef struct data_unit unit, *unit_ptr;

 void function(unit_ptr table){

      int y;
      for (y = 0; y <SIZE-1; y++)
      {
           table[y].data = y;
           table[y].next = &table[y + 1];
      }
      table[SIZE - 1].data = SIZE - 1;
  }

 int check(unit_ptr table){

    int y;
    for (y = 0; y < SIZE; y++)
    {
         if ((table[y].data + 1) != table[y].next->data){
                return 1;
         }
    }
    return 0;
 }

 int main(int argc, char **argv)
 {
         unit_ptr buf;

         buf = (unit_ptr)calloc(SIZE, sizeof(unit_ptr));
         function(buf);
         if (check(buf))
         {
             printf("Error detectado en tabla\n");
         }
         free(buf);

         return 0;
 }
    
asked by WOLD26 13.05.2018 в 03:31
source

3 answers

1

Your program has basically two errors:

Does not reserve memory well

buf = (unit_ptr)calloc(SIZE, sizeof(unit_ptr));

You are supposed to create a reservation for SIZE elements of size unit and what you do is make SIZE reserves size unit_ptr .

The problem here is not so much that the size of unit is not the same as that of unit_ptr but that the size of the latter is smaller ... then the memory reserve given by the system is insufficient for your purposes.

The right thing here would be to do:

buf = (unit_ptr)calloc(SIZE, sizeof(unit));

Beware of iterations

for (y = 0; y < SIZE; y++)
{
     if ((table[y].data + 1) != table[y].next->data){
            return 1;
     }
}

When this loop reaches y=SIZE-1 (which will be the last item in the list) ...

Where does table[y].next point?

The answer is simple: Since the list was created with calloc , which resets all bytes to 0, tabla[SIZE-1].next will point to 0 and, as expected, that memory position does not belong to your program.

What happens here is that the Operating System detects that your program accesses memory that does not belong to it and kills your application to avoid corrupting memory of other processes (or the Operating System itself).

You have to reduce the iteration range:

for (y = 0; y < SIZE - 1; y++)
{
     if ((table[y].data + 1) != table[y].next->data){
            return 1;
     }
}

If you execute the code with these changes you will see that the program does not die but it does not show the error message that you have put in the main ... you can check that it reaches the end forcing some error in the table:

function(buf);
buf[SIZE-1].data = 0;
if (check(buf))
    
answered by 14.05.2018 / 11:24
source
1

You do not really explain what you want to do. Now seeing the code, two errors can be seen:

(1) The biggest problem lies in the line where it says:

buf = (unit_ptr) calloc (SIZE, sizeof ( unit_ptr ));

Here calloc generates a SIZE size array which is fine but the size of each of the array elements is as large as a unit_ptr (the size of a pointer) should be size of the memory pointed to by a unit_ptr ie unit.

buf = (unit_ptr) calloc (SIZE, sizeof ( unit ));

(2). In the function function cycle, you are going from 0 to SIZE-2 because it says:

for (y = 0; and

answered by 13.05.2018 в 06:43
0

The corrected final code would be like this:

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

#define SIZE 1000

struct data_unit{
   int data;
   struct data_unit *next;
 };
 typedef struct data_unit unit, *unit_ptr;

 void function(unit_ptr table){

      int y;
      for (y = 0; y < SIZE - 1; y++)
      {
           table[y].data = y;
           table[y].next = &table[y + 1];
      }
      table[SIZE - 1].data = SIZE - 1;
  }

 int check(unit_ptr table){

    int y;
    for (y = 0; y < SIZE -1; y++)
    {
         if ((table[y].data + 1) != table[y].next->data){
                return 1;
         }
    }
    return 0;
 }

 int main(int argc, char **argv)
 {
         unit_ptr buf;

         buf = (unit_ptr)calloc(SIZE, sizeof(unit));
         function(buf);
         if (check(buf))
         {
             printf("Error detectado en tabla\n");
         }
         free(buf);

         return 0;
 }
    
answered by 14.05.2018 в 11:16