How to access a double pointer structure in another structure - c

I'm having trouble accessing my double pointer struct within my structure.
typedef struct monster
{
char *name;
char *element;
int population;
} monster;
typedef struct region
{
char *name;
int nmonsters;
int total_population;
monster **monsters;
} region;
region **
readRegion (FILE * infile, int *regionCount)
{
region **temp;
char garbage[50];
char garbage2[50];
char rName[50];
int monsterNum;
fscanf (infile, "%d %s", regionCount, garbage);
temp = malloc (*regionCount * sizeof (region *));
for (int i = 0; i < *regionCount; i++)
{
fscanf (infile, "%s%d%s", rName, &monsterNum, garbage2);
temp[i] = createRegion (inFile, rName, monsterNum);
}
return temp;
}
region *
createRegion (FILE * inFile, char *rName, int nMonsters)
{
region *r = malloc (sizeof (region));
char rMonster[50];
int rLength;
r->name = malloc ((strlen (rName) + 1) * sizeof (char));
strcpy (r->name, rName);
r->nmonsters = nMonsters;
for (int i = 0; i < nMonsters; i++)
{
r->monsters.name = (nMonsters * sizeof (r->monsters.name));
fscanf (in, "%s", rMonster);
r->monsters.name = malloc ((strlen (rMonster) + 1) * sizeof (char));
strcpy (r->monsters.name, rMonster);
}
return r;
}
Hopefully my code is readable where you can get the jist of what im trying to do with the monster** monsters pointer in my region struct. Any explnation on how to access and use a double struct pointer within a structure would help.

I've tried to clean up and re-interpret your createRegion to read a lot more like traditional C:
region* createRegion(FILE * inFile, char *rName, int nMonsters) {
region *r = malloc(sizeof(region));
char buffer[1024];
r->name = strdup(rName);
r->nmonsters = nMonsters;
r->monsters = calloc(nMonsters, sizeof(monster*));
for (int i=0; i < nMonsters; i++) {
// Allocate a monster
monster *m = malloc(sizeof(monster));
fscanf(in,"%s", buffer);
m->name = strdup(buffer);
m->element = NULL; // TBD?
m->population = 1; // TBD?
// Put this monster in the monsters pointer array
r->monsters[i] = m;
}
return r;
}
Where the key here is you must allocate the monsters. Here it's done individually, but you could also allocate as a slab:
region* createRegion(FILE * inFile, char *rName, int nMonsters) {
region *r = malloc(sizeof(region));
char buffer[1024];
r->name = strdup(rName);
r->nmonsters = nMonsters;
// Make a single allocation, which is usually what's returned from
// C functions that allocate N of something
monsters* m = calloc(nMonsters, sizeof(monster));
// Normally you'd see a definition like m in the region struct, but
// that's not the case here because reasons.
r->monsters = calloc(nMonsters, sizeof(monster*));
for (int i=0; i < nMonsters; i++) {
fscanf(in,"%s", buffer);
m[i].name = strdup(buffer);
m[i].element = NULL; // TBD?
m[i].population = 1; // TBD?
// Put this monster in the monsters pointer array
r->monsters[i] = &m[i];
}
return r;
}
Note I've switched out the highly quirky strlen-based code with a simple strdup call. It's also very odd to see sizeof(char) used since on any computer you're likely to interface with, be it an embedded microcontroller or a fancy mainframe, that will be 1.

Inasmuch as you are asking about accessing a double pointer inside a structure, I think your issue is mostly about this function:
region *
createRegion (FILE * inFile, char *rName, int nMonsters)
{
region *r = malloc (sizeof (region));
char rMonster[50];
int rLength;
r->name = malloc ((strlen (rName) + 1) * sizeof (char));
strcpy (r->name, rName);
r->nmonsters = nMonsters;
[Point A]
So far, so good, but here you start to run off the rails.
for (int i = 0; i < nMonsters; i++)
{
r->monsters.name = (nMonsters * sizeof (r->monsters.name));
Hold on. r->monsters has type monster **, but you are trying to access it as if it were a monster. Moreover, r->monsters has never had a value assigned to it, so there's very little indeed that you can safely do with it.
I think the idea must be that r->monsters is to be made to point to a dynamically-allocated array of monster *, and that the loop allocates and initializes the monsters, and writes pointers to them into the array.
You need to allocate space for the array, then, but you only need or want to allocate the array once. Do that before the loop, at Point A, above, something like this:
r->monsters = malloc(nMonsters * sizeof(*r->monsters)); // a monster **
Then, inside the loop, you need to allocate space for one monster, and assign a pointer to that to your array:*
r->monsters[i] = malloc(sizeof(*r->monsters[i])); // a monster *
Then, to access the actual monster objects, you need to either dererference and use the direct member selection operator (.) ...
(*r->monsters[i]).name = /* ... */;
... or use the indirect member selection operator (->) ...
r->monsters[i]->name = /* ... */;
. The two are equivalent, but most C programmers seem to prefer the latter style.
At this point, however, I note that in the body of the loop, you seem to be trying to make two separate assignments to the monster's name member. That doesn't make sense, and the first attempt definitely doesn't make sense, because you seem to be trying to assign a number to a pointer.
fscanf (in, "%s", rMonster);
r->monsters.name = malloc ((strlen (rMonster) + 1) * sizeof (char));
strcpy (r->monsters.name, rMonster);
Using the above, then, and taking advantage of the fact that sizeof(char) is 1 by definition, it appears that what you want is
// ...
r->monsters[i]->name = malloc(strlen(rMonster) + 1);
strcpy (r->monsters[i]->name, rMonster);
And finally,
}
return r;
}
Note well that corresponding to the two levels of indirection in type monster **, each access to an individual monster property via r->members requires two levels of derferencing. In the expressions above, one is provided by the indexing operator, [], and the other is provided by the indirect member access operator, ->.
* Or you could allocate space for all of the monsters in one go, before the loop, and inside the loop just initialize them and the array of pointers to them. The use of a monster ** suggests the individual allocation approach, but which to choose depends somewhat on how these will be used. The two options are substantially interchangeable, but not wholly equivalent.

Related

How to allocate memory for structure?

I'm learning C.
I have a structure, and if I need to set array of structures -> so I allocate memory for this array. But do I need separately allocate memory for fields in this structure?
Like this:
struct Call{
char *country;
int duration;
};
int main(){
struct Call *calls;
int n;
scanf_s("%d", n);
calls = (struct Call *) calloc(n+1 , sizeof(struct Call));
}
You need not to allocate space for data members of objects of the structure type because they belong to the objects.
But it seems you will need to allocate a character array the pointer to which will be stored in the data member country if you want that objects will be owners of the corresponding strings.
For example
struct Call *calls = calloc( 1, sizeof( struct Call ) );
const char *country = "Some country";
calls->country = malloc( strlen( country ) + 1 );
strcpy( calls->country, country );
When you will deallocate memory for objects of the type struct Call you will need at first to free the memory allocated for character arrays pointed to by data members country.
Yes, you must initialize any pointer before you can dereference it. This means allocating memory for it, or assigning it to already-allocated memory. That's a universal rule in C, there's no special cases for pointers in structures. C will not "recursively" allocate memory for you. Among other things, how would it know how much you need? Consider your simplified code below
int main(){
struct Call *calls;
calls = calloc(1 , sizeof(struct Call));
}
Assuming calloc succeeded, calls now points to a memory block that contains space for a single struct Call, which includes space for the char pointer and int. However, country itself is still an unintialized pointer, and you must allocate space for it or point it to something already-allocated before you can safely dereference it
calls->country = malloc(25);
if (calls->country == NULL) exit(-1); // handle error how you want
strcpy(calls->country, "Portugal");
printf("%s\n", calls->country); // prints Portugal
or something like
char myCountry[] = "Spain";
calls->country = myCountry;
myCountry[0] = 'X';
printf("%s\n", calls->country); // prints Xpain
Also see Do I cast the result of malloc?
You need to allocate space for the struct and for char array.
You probably want to dynamically add calls to the array so you need to know the size of the array as well:
typedef struct Call{
char *country;
int duration;
}Call;
typedef struct
{
size_t size;
Call call[];
}Calls_t;
Calls_t *addCall(Calls_t *calls, const int duration, const char *country)
{
size_t newsize = calls ? calls -> size + 1 : 1;
calls = realloc(calls, sizeof(*calls) + newsize * sizeof(calls -> call[0]));
if(calls)
{
calls -> size = newsize;
calls -> call[newsize - 1].country = malloc(strlen(country) + 1);
if(!calls -> call[newsize - 1].country)
{
/* error handling */
}
strcpy(calls -> call[newsize - 1].country, country);
calls -> call[newsize - 1].duration = duration;
}
return calls;
}
void printCalls(const Calls_t *calls)
{
if(calls)
for(size_t i = 0; i < calls -> size; i++)
printf("Call %zu: Country:%s Duration:%d\n", i + 1, calls -> call[i].country, calls -> call[i].duration);
}
int main(void)
{
Calls_t *calls = NULL, *tmp;
tmp = addCall(calls, 10, "Poland");
if(tmp) calls = tmp;
tmp = addCall(calls, 20, "UK");
if(tmp) calls = tmp;
tmp = addCall(calls, 30, "US");
if(tmp) calls = tmp;
printCalls(calls);
/* free allocated memory */
}
https://godbolt.org/z/Kb5bKMfYY

How to properly free char** in C

I have really been confused about this 2D char array
char **arg = malloc(sizeof(char*) * argc)
for (int i = 0; i < argc; i++)
arg[i] = malloc(sizeof(char) * size)
...
...
Now suppose after a series of operations, I forget the variable argc, how can I free those memory?
Can I do something like this? Is this absolutely correct under all circumstances?
char **tmp = arg;
while (*tmp != NULL){
free(*tmp);
tmp++;
}
free(arg);
No
while(*tmp != NULL){
you may reach above a point where you will dereference memory which hasn't been assigned to and trigger undefined behaviour.
Or as suggested you can explicitly assign a NULL to the last allocated pointer, and in that case it will work.
As others have said, the problems with freeing in a loop as shown is that an extra item (argc + 1) needs to be allocated and it has to be set to NULL. An alternative technique is to first allocate the space for the pointers as you have done
char **arg = malloc(sizeof(char*) * argc)
Then, if you know all the subsequent items are the same size, allocate it in one huge block and set the rest of the elements at spaced offsets
arg[0] = malloc(sizeof(char) * size * argc);
for (int i = 1; i < argc; ++i)
arg[i] = arg[i - 1] + size;
Freeing the space is a doddle: no need to even remember argc
free(arg[0]); /* this will free the memory used by all the elements */
free(arg);
The big disadvantages to this technique is that if any of the array elements overrun, it will corrupt the next item. This cannot be detected so easily with a heap check unless it is the last item.
if you define your char * array like this:
char **arg = calloc( 1, sizeof( char * ) * argc );
you can be sure that every undefined pointer will be equal to NULL
and then you can use the while loop almost like you suggested:
char *tmp = *arg;
while ( tmp != NULL ) {
free( tmp );
tmp++;
}
free(arg);

pointer of a matrix in C

tPeca* criarPecas(FILE *pFile, int tam){
int i = 0,linhaV,colunaV,j = 0;
char ***elemento = (char***)malloc(tam*sizeof(char**));;
tPeca *pecaJogo = (tPeca*)malloc(tam*sizeof(tPeca));
if(pecaJogo==NULL)
return NULL;
for(i=0;i<tam;i++){
j=0;
fscanf (pFile, "%[^;]", pecaJogo[i].nome);
fscanf (pFile, ";%d", &pecaJogo[i].qtd);
fscanf (pFile, ";%d", &linhaV);
pecaJogo[i].linha = linhaV;
fscanf (pFile, ";%d", &colunaV);
pecaJogo[i].coluna = colunaV;
**elemento[i] = (char**)malloc(linhaV * sizeof(char*));
*elemento[i][j] = (char*)malloc(colunaV * sizeof(char));
j++;
}
return pecaJogo;
}
*** elemento is a pointer of a matriz, i think that i have problem with malloc... I received Segmentation Fault
These two statements are where I guess you ran into your problem:
**elemento[i] = (char**)malloc(linhaV * sizeof(char*));
*elemento[i][j] = (char*)malloc(colunaV * sizeof(char));
You created char *** above, and attempted to create an array of pointers:
char ***elemento = (char***)malloc(tam*sizeof(char**));;
Should be:
//this step creates an array of pointers
char ***elemento = malloc(tam*sizeof(char*));
//Note: there is no need to cast the return of [m][c][re]alloc in C
// The rules are different in C++ however.
Now you can put elemento in a loop to allocate pointer space for each of the pointers you created:
//this step creates an array pointers for each element of the array created above:
for(i=0;i<tam;i++) //assuming size is also tam (you specified nothing else)
{
elemento[i] = malloc(tam*sizeof(char *));//each ith element will
//now have tam elements of its own.
}
Next, you allocate memory at each location:
for(i=0;i<tam;i++)
{
for(j=0;j<tam;j++)
{
elemento[i][j] = malloc(someValue*sizeof(char));
//Note: sizeof(char) == 1, so could be:
//elemento[i][j] = malloc(someValue);
}
}
Now you have a fully allocated 3D array.
Putting it all together, (A simple 2D example)
When you create memory for a multi-dimensional array, you must create a combination of array of pointers, and memory for each. For 2D example, (used for an array of strings perhaps) you could do this:
char ** allocMemory(char ** a, int numStrings, int maxStrLen)
{
int i;
a = calloc(sizeof(char*)*(numStrings), sizeof(char*));//create array of pointers
for(i=0;i<numStrings; i++)
{
a[i] = calloc(sizeof(char)*maxStrLen + 1, sizeof(char));//create memory at each location
}
return a;
}
You must also create method to free memory:
void freeMemory(char ** a, int numStrings)
{
int i;
for(i=0;i<numStrings; i++)
if(a[i]) free(a[i]);
free(a);
}
Usage:
char **array = {0};
...
array = allocMemory(array, 10, 80);
...
freeMemory(array, 10);
Will create memory, and addresses sufficient to contain 10 arrays of 80 character strings (arrays of char), then free it.
This could be expanded to 3D by adding another layer (for loop) of pointer creation, as shown at top of post). In this implementation, the inner most loop always creates the actual memory for each of the address locations you create.

how to initialize the array of pointers to a structure to zero

I am allocating memory for array of pointers to structure through malloc and want to initialize it with zero like mentioned below . Assuming the structure contains member of type int and char [] (strings) ? so how can i zero out this struct.
Code : suppose i want to allocate for 100
struct A **a = NULL;
a = (struct **)malloc(sizeof( (*a) * 100);
for(i=1; i < 100; i++)
a[i] = (struct A*)malloc(sizeof(a));
Also please explain me why is it necessary to initialize with zero .
Platform : Linux , Programing language : C
I know we can use memset or bzero . I tried it bt it was crashing , may be i was noy using it properly so pls tell me the correct way .
Use of calloc would be most in line with the example above.
First, C arrays are zero-based, not one-based. Next, you are allocating only enough space to hold one pointer, but you are storing 100 pointers into it. Are you trying to allocate 100 As, or are you trying to allocate 100 sets of 100 As each? Finally, the malloc inside your loop allocates space for the sizeof a, not sizeof (struct A).
I'll assume that you are trying to allocate an array of 100 pointers to A, each pointer pointing to a single A.
Solutions: You could use calloc:
struct A **a;
/* In C, never cast malloc(). In C++, always cast malloc() */
a = malloc(100 * sizeof( (*a)));
for(i=0; i < 100; i++)
a[i] = calloc(1, sizeof(struct A));
Or, you could use memset:
struct A **a;
a = malloc(100 * sizeof(*a));
for(i = 0; i < 100; i++) {
a[i] = malloc(sizeof(struct A));
memset(a[i], 0, sizeof(struct A));
}
You ask "why is it necessary to initialize with zero?" It isn't. The relevant requirement is this: you must assign a value to your variables or initialize your variable before you use them for the first time. That assignment or initialization might be zero, or it might be 47 or it might be "John Smith, Esq". It just has to be some valid assignment.
As a matter of convenience, you might choose to initialize all of your members of struct A to zero, which you can do in one single operation (memset or calloc). If zero is not a useful initial value for you, you could initialize the structure members by hand, for example:
struct A **a;
a = malloc(100 * sizeof(*a));
for(i = 0; i < 100; i++) {
a[i] = malloc(sizeof(struct A));
a[i]->index = i;
a[i]->small_prime = 7;
strcpy(a[i]->name, name_database[i]);
}
As long as you never refer to the value of an uninitialized and unassigned variable, you are good.
You can use memset() to set the whole array to 0
OTOH,
a = (struct **)malloc(sizeof( (a*)));
for(i=1; i < 100; i++)
a[i] = (struct*)malloc(sizeof(a) * 100);
is wrong, because you have just created one element of a * but in the next line when the loop goes to 2nd iteration, it will access illegal memory. So to allocate 100 elements of a *, your first malloc() should be as follows
a = (struct **)malloc(sizeof(a *) * 100);
The correct code (including error handling) would more or less will look as follows:
if ((a = (struct **)malloc(sizeof(a*) * 100)) == NULL) {
printf("unable to allocate memory \n");
return -1;
}
for(i=0; i<100; i++) {
if ((a[i] = (struct*)malloc(sizeof(a) * 100)) == NULL) {
printf("unable to allocate memory \n");
return -1;
}
memset(a[i], 0, 100);
}
or as an alternative to malloc() and memset(), you can use calloc()
You dont need many malloc's, one calloc is enough:
int i;
struct A **a = calloc(100,sizeof**a+sizeof*a),*mem=a+100;
for(i=0;i<100;++i)
{
a[i]=&mem[i];
}
...
free(a); /* and you only need ONE free */

How to allocate and deallocate heap memory for 2D array?

I'm used to PHP, but I'm starting to learn C. I'm trying to create a program that reads a file line by line and stores each line to an array.
So far I have a program that reads the file line by line, and even prints each line as it goes, but now I just need to add each line to an array.
My buddy last night was telling me a bit about it. He said I'd have to use a multidimensional array in C, so basically array[x][y]. The [y] part itself is easy, because I know the maximum amount of bytes that each line will be. However, I don't know how many lines the file will be.
I figure I can make it loop through the file and just increment an integer each time and use that, but I feel that there might be a more simple way of doing it.
Any ideas or even a hint in the right direction? I appreciate any help.
To dynamically allocate a 2D array:
char **p;
int i, dim1, dim2;
/* Allocate the first dimension, which is actually a pointer to pointer to char */
p = malloc (sizeof (char *) * dim1);
/* Then allocate each of the pointers allocated in previous step arrays of pointer to chars
* within each of these arrays are chars
*/
for (i = 0; i < dim1; i++)
{
*(p + i) = malloc (sizeof (char) * dim2);
/* or p[i] = malloc (sizeof (char) * dim2); */
}
/* Do work */
/* Deallocate the allocated array. Start deallocation from the lowest level.
* that is in the reverse order of which we did the allocation
*/
for (i = 0; i < dim1; i++)
{
free (p[i]);
}
free (p);
Modify the above method. When you need another line to be added do *(p + i) = malloc (sizeof (char) * dim2); and update i. In this case you need to predict the max numbers of lines in the file which is indicated by the dim1 variable, for which we allocate the p array first time. This will only allocate the (sizeof (int *) * dim1) bytes, thus much better option than char p[dim1][dim2] (in c99).
There is another way i think. Allocate arrays in blocks and chain them when there is an overflow.
struct _lines {
char **line;
int n;
struct _lines *next;
} *file;
file = malloc (sizeof (struct _lines));
file->line = malloc (sizeof (char *) * LINE_MAX);
file->n = 0;
head = file;
After this the first block is ready to use. When you need to insert a line just do:
/* get line into buffer */
file.line[n] = malloc (sizeof (char) * (strlen (buffer) + 1));
n++;
When n is LINE_MAX allocate another block and link it to this one.
struct _lines *temp;
temp = malloc (sizeof (struct _lines));
temp->line = malloc (sizeof (char *) * LINE_MAX);
temp->n = 0;
file->next = temp;
file = file->next;
Something like this.
When one block's n becomes 0, deallocate it, and update the current block pointer file to the previous one. You can either traverse from beginning single linked list and traverse from the start or use double links.
There's no standard resizable array type in C. You have to implement it yourself, or use a third-party library. Here's a simple bare-bones example:
typedef struct int_array
{
int *array;
size_t length;
size_t capacity;
} int_array;
void int_array_init(int_array *array)
{
array->array = NULL;
array->length = 0;
array->capacity = 0;
}
void int_array_free(int_array *array)
{
free(array->array);
array->array = NULL;
array->length = 0;
array->capacity = 0;
}
void int_array_push_back(int_array *array, int value)
{
if(array->length == array->capacity)
{
// Not enough space, reallocate. Also, watch out for overflow.
int new_capacity = array->capacity * 2;
if(new_capacity > array->capacity && new_capacity < SIZE_T_MAX / sizeof(int))
{
int *new_array = realloc(array->array, new_capacity * sizeof(int));
if(new_array != NULL)
{
array->array = new_array;
array->capacity = new_capacity;
}
else
; // Handle out-of-memory
}
else
; // Handle overflow error
}
// Now that we have space, add the value to the array
array->array[array->length] = value;
array->length++;
}
Use it like this:
int_array a;
int_array_init(&a);
int i;
for(i = 0; i < 10; i++)
int_array_push_back(&a, i);
for(i = 0; i < a.length; i++)
printf("a[%d] = %d\n", i, a.array[i]);
int_array_free(&a);
Of course, this is only for an array of ints. Since C doesn't have templates, you'd have to either put all of this code in a macro for each different type of array (or use a different preprocessor such as GNU m4). Or, you could use a generic array container that either used void* pointers (requiring all array elements to be malloc'ed) or opaque memory blobs, which would require a cast with every element access and a memcpy for every element get/set.
In any case, it's not pretty. Two-dimensional arrays are even uglier.
Instead of an array here, you could also use a linked list, The code is simpler, but the allocation is more frequent and may suffer from fragmentation.
As long as you don't plan to do much random access (Which is O(n) here), iteration is about as simple as a regular array.
typedef struct Line Line;
struct Line{
char text[LINE_MAX];
Line *next;
};
Line *mkline()
{
Line *l = malloc(sizeof(Line));
if(!l)
error();
return l;
}
main()
{
Line *lines = mkline();
Line *lp = lines;
while(fgets(lp->text, sizeof lp->text, stdin)!=NULL){
lp->next = mkline();
lp = lp->next;
}
lp->next = NULL;
}
If you are using C you will need to implement the resizing of the array yourself. C++ and the SDL has this done for you. It is called a vector. http://www.cplusplus.com/reference/stl/vector/
While a multidimensional array can solve this problem, a rectangular 2D array would not really be the natural C solution.
Here is a program that initially reads the file into a linked list, and then allocates a vector of pointers of the right size. Each individual character does then appear as array[line][col] but in fact each row is only as long as it needs to be. It's C99 except for <err.h>.
#include <err.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
typedef struct strnode {
char *s;
struct strnode *next;
} strnode;
strnode *list_head;
strnode *list_last;
strnode *read1line(void) {
char space[1024];
if(fgets(space, sizeof space, stdin) == NULL)
return NULL;
strnode *node = malloc(sizeof(strnode));
if(node && (node->s = malloc(strlen(space) + 1))) {
strcpy(node->s, space);
node->next = NULL;
if (list_head == NULL)
list_head = node;
else
list_last->next = node;
list_last = node;
return node;
}
err(1, NULL);
}
int main(int ac, char **av) {
int n;
strnode *s;
for(n = 0; (s = read1line()) != NULL; ++n)
continue;
if(n > 0) {
int i;
strnode *b;
char **a = malloc(n * sizeof(char *));
printf("There were %d lines\n", n);
for(b = list_head, i = 0; b; b = b->next, ++i)
a[i] = b->s;
printf("Near the middle is: %s", a[n / 2]);
}
return 0;
}
You can use the malloc and realloc functions to dynamically allocate and resize an array of pointers to char, and each element of the array will point to a string read from the file (where that string's storage is also allocated dynamically). For simplicity's sake we'll assume that the maximum length of each line is less than M characters (counting the newline), so we don't have to do any dynamic resizing of individual lines.
You'll need to keep track of the array size manually each time you extend it. A common technique is to double the array size each time you extend, rather than extending by a fixed size; this minimizes the number of calls to realloc, which is potentially expensive. Of course that means you'll have to keep track of two quantities; the total size of the array and the number of elements currently read.
Example:
#define INITIAL_SIZE ... // some size large enough to cover most cases
char **loadFile(FILE *stream, size_t *linesRead)
{
size_t arraySize = 0;
char **lines = NULL;
char *nextLine = NULL;
*linesRead = 0;
lines = malloc(INITIAL_SIZE * sizeof *lines);
if (!lines)
{
fprintf(stderr, "Could not allocate array\n");
return NULL;
}
arraySize = INITIAL_SIZE;
/**
* Read the next input line from the stream. We're abstracting this
* out to keep the code simple.
*/
while ((nextLine = getNextLine(stream)))
{
if (arraySize <= *linesRead)
{
char **tmp = realloc(lines, arraysSize * 2 * sizeof *tmp);
if (tmp)
{
lines = tmp;
arraySize *= 2;
}
}
lines[(*linesRead)++] = nextLine;
)
return lines;
}

Resources