Mallo c callo c не может выделить структуру - PullRequest
0 голосов
/ 06 августа 2020

Я получаю нулевую память, используя следующий код malloc / callo c. Иногда не удается выделить память для «name1», а затем происходит сбой strcpy. Пожалуйста, направьте.

struct testMalloc
{
    char name1[90];
    char name2[90]; 
    struct testMalloc* ptr;
};
int main(int argc, char* argv[])
{
    struct testMalloc* test = 0 ;   
    int size = 0;
    size = sizeof(struct testMalloc);

    printf("Size of struct is %d", size);

    test = (struct testMalloc*) calloc(sizeof(struct testMalloc));  
    
    strcpy((test->name1), "hdshdssdsdfsfffffffffffffffffffffffffffffh");

    return 0;

}

Ответы [ 5 ]

5 голосов
/ 06 августа 2020

Вы не включаете <stdlib.h>, чтобы компилятор знал подпись calloc, и в этом случае он использует K&R соглашение о вызовах.

Если вы включаете <stdlib.h>, код не будет скомпилировать перед правильным вызовом calloc.

3 голосов
/ 06 августа 2020

calloc принимает 2 аргумента: количество элементов и размер каждого элемента. Это обнулит выделенную память. То, что вы ищете, - это malloc, который принимает только 1 аргумент: общий размер выделенного фрагмента памяти, и он не обнуляет выделенную память.

2 голосов
/ 06 августа 2020
  1. Всегда проверяйте результат mallo c.
  2. Используйте объекты вместо типов в sizeof
  3. Попробуйте использовать более безопасные версии строковых функций (в этом примере переданная строка длиннее, чем массив.
  4. Вам не нужно приводить результат mallo c, и это считается плохой практикой (в настоящее время довольно устаревшей, но в любом случае)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct testMalloc
{
    char name1[20];
    char name2[90]; 
    struct testMalloc* ptr;
};

struct testMalloc *allocAndCopy(const char *str)
{
    struct testMalloc *ptr = malloc(sizeof(*ptr));
    if(ptr)
    {
        strncpy(ptr -> name1, str, sizeof(ptr -> name1));
        ptr -> name1[sizeof(ptr -> name1) - 1] = 0;
    }
    return ptr;
}


int main(int argc, char* argv[])
{
    struct testMalloc* test = allocAndCopy("hdshdssdsdfsfffffffffffffffffffffffffffffh");

    if(test) printf("the string is: %s\n", test -> name1);
}

https://godbolt.org/z/zjvvYW

1 голос
/ 06 августа 2020

Сверху вниз:

1.

Вы забыли #include stdlib.h использовать calloc() и malloc(). Неявные объявления запрещены, начиная с C99.

2.

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

Ваша программа не нуждается в передаче аргументов.

Это:

int main (void)

было бы более подходящим.

3.

int size = 0;

size никогда не должно иметь отрицательного значения. Поэтому было бы правильнее объявить его как unsigned int или даже лучше size_t.

4.

struct testMalloc* test = 0 ; 

Вы можете использовать 0 для инициализации указателя. Это совершенно верно, поскольку 0 - это константа нулевого указателя . Но лучше использовать NULL при работе с указателями, а не 0, чтобы показать назначение указателя и повысить удобочитаемость.

struct testMalloc* test = NULL; 

5.

calloc(sizeof(struct testMalloc)); 

calloc требуется два аргументы по сравнению с malloc. Первый должен быть количеством элементов, а второй размер одного элемента.

calloc(sizeof(1,struct testMalloc)); 

6.

test = (struct testMalloc*) calloc(sizeof(struct testMalloc)); 

Вам не нужно приводить возвращаемое значение malloc() или calloc().

7.

Вы забыли чтобы проверить возвращенный указатель из calloc() на нулевой указатель, если выделение не удалось. Всегда проверяйте возвращаемое значение функций управления памятью.

test = calloc(1, sizeof(struct testMalloc)); 
if (test == NULL)
{
    fputs("Allocation failed!", stderr);
    // error routine.
}
1 голос
/ 06 августа 2020

Есть несколько синтаксических ошибок:

  1. struct testMalloc* test = NULL; Так инициализируется NULL-указатель
  2. calloc(sizeof(struct testMalloc)); слишком мало аргументов передано в calloc. Правильная форма: calloc(no_of_elements, sizeof(type));

Вот правильная реализация вашего кода:

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

struct testMalloc
{
    char name1[90];
    char name2[90]; 
    struct testMalloc* ptr;
};

int main(int argc, char* argv[])
{
    struct testMalloc* test = NULL;
    size_t size = sizeof(struct testMalloc);

    printf("Size of struct is %ld\n", size);

    if((test = (struct testMalloc*)calloc(1, size)) == NULL){
        return -1; //Failed to allocate memory
    }
    else {
        strcpy((test->name1),"hdshdssdsdfsfffffffffffffffffffffffffffffh");
        printf("%s\n",test->name1);
    }
    
    return 0;
}
...