Erik Vesterlund
Erik Vesterlund

Reputation: 451

Segmentation fault due to free or malloc?

I started writing some code (see below) and when I tried running it (gcc file.c; ./a.out) I got a segfault and I don't understand why. If I comment out

free(filename); // or
double *data = ...;

there's no segfault. What's going on? I didn't know what to search for but I found this question and followed the GDB instructions in the third answer. I don't understand the output (I've never used GDB or any other debugger) but maybe you do. (gdb) r

Program received signal SIGSEGV, Segmentation fault.│
0x00007ffff7a97d3c in __GI___libc_free (mem=0x7fffffffe5a0) at malloc.c:2945
2945    malloc.c: No such file or directory.

(gdb) bt

#0  0x00007ffff7a97d3c in __GI___libc_free (mem=0x7fffffffe5a0) at malloc.c:2945
#1  0x00000000004006a5 in main ()

Oh and doing away with the arg_handler doesn't make a difference.

EDIT: Code:

//#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
//#include "graphics/graphics.c"
//#include "file_operations/file_operations.c"

#define ARGS 6
#define EPS 1e-03
#define DATA_LEN 5

int arg_handler(int ac, char *args[], int *a, char *b, int *c, double *d, double *e, int *f);

int main(int argc, char *argv[]) {

  int N, nsteps, graphics;
  char *filename;
  double dt, theta_max;
  if (arg_handler(argc, argv, &N, filename, &nsteps, &dt, &theta_max, &graphics)) {
    printf("Usage: ...\n");
    free(filename);
    return -1;
  }

  if (graphics) {
    printf("Graphics not available.\n");
    graphics = 0;
  }

  double *data = malloc(N*DATA_LEN*sizeof(double));
/*
  if (read_doubles_from_file(N*DATA_LEN, data, filename)<0) {
    perror("An error occured:\n");
    return -1;
  }
*/

//  free(data);

  return 0;
}

int arg_handler(int ac, char *args[], int *a, char *b, int *c, double *d, double *e, int *f) {

  if (ac!=1+ARGS) {
    return 1;
  }
  *a = atoi(args[1]);
  b = args[2];
  *c = atoi(args[3]);
  *d = atof(args[4]);
  *e = atof(args[5]);
  *f = atoi(args[6]);
  return 0;
}

Upvotes: 0

Views: 8342

Answers (1)

Jazzwave06
Jazzwave06

Reputation: 1851

Your free(filename) call has no corresponding malloc() call; the filename pointer is coming from the argument vector. This memory doesn't have to be freed and is managed by the os when it starts a process.

Basically, your process is trying to free memory the os owns; therefore, the os prevents you from doing that and signals you so.

 // (1) >> unitialized pointer, cannot be freed.
 char *filename;

 double dt, theta_max;
 if (arg_handler(argc, argv, &N, filename, &nsteps, &dt, &theta_max, &graphics)) {
     printf("Usage: ...\n");
     // (3a) >> freeing memory owned by the os.
     // (3b) >> or freeing uninitialized pointer.
     free(filename);
     return -1;
 }

int arg_handler(int ac, char *args[], int *a, char *b, int *c, double *d, double *e, int *f) {
    if (ac!=1+ARGS) {
        // (2b) >> never initializing pointer
        return 1;
    }

    *a = atoi(args[1]);
    // (2a) >> setting value to a pointer managed by the os.
    b = args[2];
    *c = atoi(args[3]);
    *d = atof(args[4]); 
    *e = atof(args[5]);
    *f = atoi(args[6]);
    return 0;
}

Upvotes: 3

Related Questions