简体   繁体   中英

Segmentation Fault when using malloc

I think I've got everything fixed now. I made the mistake of incrementing the environ variable instead of treating it like an array and iterating across it. The following is what I have now and it should be good to go.

extern char **environ;

int main(int argc, char *argv[]) {
    // determine number of environment variables
    int n = 0;
    char *c = NULL;
    while ((c = environ[n++]) != NULL) {
        printf("%s\n", c);
    }
    printf("%s\n%d\n\n", c, n);

    // allocate array to store character pointers to environment array
    char **new_c;
    printf("This prints\n");
    if ((new_c = malloc(n * sizeof(*c))) == NULL) {
        printf("Error\n");
        exit(EXIT_FAILURE);
    }
    printf("This prints now too\n");
    free(c);

    // sort array of character pointers

    // parse each environment variable and output

    exit(0);
}

To start, I've read through a couple dozen malloc & segmentation fault questions on here and none seem to be the same as mine. That being said, if this is a duplicate question would you mine pointing me to the solution?

Hi all, I'm having a problem using malloc. I compiled and ran my program once and malloc worked. I then began filling in more code to solve the problem and since that first run I have received a Segmentation Fault. Below is my code in it's last working state (still giving a seg fault error though):

extern char **environ;

int main(int argc, char *argv[]) {
    // determine number of environment variables
    int n = 0;
    char *c = *environ;
    while ((c = *environ++) != NULL) {
        n++;
        printf("%s\n", c);
    }
    printf("%s\n%d\n\n", c, n);

    // allocate array to store character pointers to environment array
    printf("This prints\n");
    if ((c = malloc((size_t) n)) == NULL) {
        perror("Unable to allocate memory\n");
    }
    printf("This does not print\n");
    free(c);

    // sort array of character pointers

    // parse each environment variable and output

    exit(0);
}

The program is supposed to allocate memory for a char array that will then be used to sort, parse, and print the name-value or value-name pairs depending on what the FORMAT value is set to. The first loop works and iterates through the environ variable and prints out each name-value pair. The two printf statements I included state what I see in the terminal. Does anyone have any ideas what I'm doing wrong?

Also, I have tried using the following malloc lines:

char *new_c = malloc((size_t) n);
char *new_c = malloc(n);
char *new_c = malloc(1);
char *new_c = malloc(sizeof(n));
int *ptr = malloc((size_t) n);

There are probably a few others I tried but I'm still baffled. There are so few lines of code that I'm not sure how I could be messing anything up this early on. Also, for giggles here's what I get when I use free in the terminal (showing I have memory available):

              total        used        free      shared  buff/cache   available
Mem:        3036836     1404340      902852      104712      729644     1491248
Swap:             0           0           0

I've also tried calling malloc outside of the if statement as such:

c = malloc((size_t) n);
if (c == NULL) {
    perror("Unable to allocate memory\n");
}

Here you are modifying the global environ :

while ((c = *environ++) != NULL) {

After the while loop, environ points to uninitialized memory.

malloc() looks for some environment variables which can modify its behaviour and is now dereferencing a pointer to uninitialized memory. Use this:

int i = 0;
while ((c = environ[i++]) != NULL) {

This should fix the segmentation fault.

Two things with this:

if ((c = malloc((size_t) n)) == NULL) {
    perror("Unable to allocate memory\n");
}

You are allocating n bytes, here. It sounds like you want to allocate space for n pointers to char , so you should replace with:

malloc(n * sizeof(char *))

If this is indeed what you're trying to do, then c should be char ** , not char * , and better still would be:

c = malloc(n * sizeof *c)

Incidentally, you appear to be using c for two completely different things. It's generally better not to do this with variables - since it makes your program harder to understand - and instead to use one variable to loop through to print your environment variables, and a different one to store your dynamically allocated array.

Also, you call perror() if malloc() fails, but then you just continue right on with your program as if there was no error. You should actually respond to a failure of this nature, if nothing else by calling exit(EXIT_FAILURE) after reporting it.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM