Reputation: 2042
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char **argv) {
if (argc != 3) {
fprintf(stderr, "Usage: greeting message name\n");
exit(1);
}
char greeting[20];
char *name = argv[2];
// Your code goes here
for (int i = 0; i < strlen(argv[1]); i++) {
if (i < 20) {
greeting[i] = argv[1][i];
}
else {
greeting[i] = '\0';
}
}
int greeting_len = strlen(greeting);
strcat(greeting, " ");
strncat(greeting, name, 20-greeting_len-2);
printf("%s\n", greeting);
return 0;
}
In this practice, I am required to concatenate the two command line arguments, which are greeting
and name
, together and separated by a space. What's more, the greeting and the string after concentrated cannot be longer than 20 characters.
When I run
./a.out "Good morninggggggggggggggggggg" "Emmanuel"
, there is an error saying
*** stack smashing detected ***: ./a.out terminated
Aborted (core dumped)
How can I fix it?
Upvotes: 0
Views: 81
Reputation: 16540
the following proposed code:
argv[1]
and argv[2]
and now, the proposed code:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char **argv)
{
if (argc != 3)
{
fprintf(stderr, "Usage: greeting message name\n");
exit(1);
}
char *greeting = malloc( strlen( argv[1] ) + strlen( argv[2] ) +1 +1 );
if( !greeting )
{
perror( "malloc failed" );
exit( EXIT_FAILURE );
}
strcpy( greeting, argv[1] );
strcat( greeting, " " );
strcat( greeting, argv[2] );
printf("%s\n", greeting);
free( greeting );
return 0;
}
Upvotes: 0
Reputation: 780673
If the message
argument is longer than 20 characters, your first loop will write outside the bounds of greeting
. The if
statement doesn't stop the loop, it keeps going, but assigns null bytes instead of argv[1][i]
.
And if the message
argument fits into greeting
, you never add a null byte at all. The loop stops after copying the last character, not including the null terminator.
You can simply use strncpy()
, and then set the last byte of greeting
to a null byte.
strncpy(greeting, argv[1], sizeof greeting);
greeting[sizeof greeting - 1] = '\0';
You need to check if you've hit the limit before adding the space:
if (greeting_len < 18) {
greeting[greeting_len] = ' ';
greeting[greeting_len+1] = '\0';
greeting_len++;
}
if (greeting_len < 18) {
strncat(greeting, name, 19-greeting_len);
}
But if you can use snprintf()
it's all much easier:
snprintf(greeting, sizeof greeting, "%s %s", argv[1], name);
Upvotes: 2