Reputation: 41
I have a function append_string, which appends str2 to str1:
void append_string(char* str1, char* str2) {
int new_length = strlen(str1)+strlen(str2);
size_t new_size = sizeof(char)*(new_length);
str1 = (char*) realloc(str1, new_size);
strcat(str1, str2);
}
As shown in the function, I'm trying to increase the size using a the combined size of the strings.
Whenever I call append_str("", "adc");
, I get "realloc(): Invalid pointer"
What did I do wrong?
Upvotes: 0
Views: 81
Reputation: 154315
At least these problems:
Attempting to reallocate something not allocated.
realloc(str1, new_size)
attempts to reallocate the string literal ""
leading to "realloc(): Invalid pointer".
Size off by 1
New size did not account for the null character.
// size_t new_size = sizeof(char)*(new_length);
size_t new_size = sizeof(char)*(new_length + 1);
Code loses the allocated pointer
Calling code lost the value of the new pointer str
.
Weak type for sizing
Use size_t
.
Instead, pass in an allocated pointer or NULL
by its address.
void append_string(char** str, const char* appendage) {
size_t new_length = strlen(*str) + strlen(appendage);
size_t new_size = sizeof(char)*(new_length + 1);
*str = realloc(*str, new_size);
strcat(*str, appendage);
}
// Usage
char *s = malloc(1);
strcpy(s, "");
append_str(&s, "adc");
puts(s);
Advanced issues include:
What to do if realloc()
returns NULL
?
How to handle appendage
overlapping str
?
Do not use strcat()
. Avoid slow code. Better to retain the original string length and copy from there.
void append_string(char** str, const char* appendage) {
size_t str_len = *str ? strlen(*str) : 0;
size_t app_len = strlen(appendage);
void *p = realloc(*str, str_len + app_len + 1);
if (p == NULL) {
// Handle Error - various approaches
free(*str);
*str = NULL;
} else {
strcpy(*str + str_len, appendage);
}
}
Still need to handle case when appendage
overlaps *str
.
void append_string_when_overlap_possible(char** str, const char* appendage) {
size_t str_len = *str ? strlen(*str) : 0;
size_t app_len = strlen(appendage);
char *p = malloc(str_len + app_len + 1);
if (p == NULL) {
// Handle Error - various approaches
free(*str);
*str = NULL;
} else {
if (*str) {
strcpy(p, *str);
}
strcpy(p + str_len, appendage);
free(*str);
*str = p;
}
}
Upvotes: 4