I'm really stumped on this one.
I have written a simple program in c to retrieve first name, last name and YOB (year of birth) from the user keyboard input (i haven't got around to parsing age into an integer yet) and I set a maximum number of characters for the input.
But whenever I allow the max characters for a field to be 50 or greater, the return value is always blank.
This is the code (60 lines), output to follow. The function causing trouble is the second to last function, getInputNoNewLine:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void flushBuffer();
char *getInput(int max, char message[]);
char *getInputNoNewline(int max, char message[]);
typedef struct Person {
char *firstName;
char *lastName;
int yob;
} Person;
void flushBuffer() {
int ch;
while ((ch = getchar()) != '\n' && ch != EOF); //flush the input buffer
}
char *getInput(int max, char message[]) {
char in[max];
char *input;
do {
printf("%s", message);
input = fgets(in, max + 2, stdin); //max + 2 accounts for characters fgets adds
if (input[strlen(input)-1] != '\n') {
printf("Sorry, maximum %d characters\n", (max));
flushBuffer();
}
} while (input[(strlen(input)-1)] != '\n');
printf("input: %s", input); //debug
return input;
}
//OFFENDING FUNCTION
char *getInputNoNewline(int max, char message[]) {
char *input;
input = getInput(max, message);
printf("raw input : %s", input); //debug
if (input[strlen(input) - 1] == '\n') { //strip new line character
input[strlen(input) - 1] = '\0';
}
printf("final input: '%s'\n", input); //debug
return input;
}
int main(int argc, char *argv[]) {
int numPlayers = 3;
char *intIn;
int i = 0;
Person players[numPlayers];
printf("Hello world Game\n");
for (i = 0; i < numPlayers; ++i) {
players[i].firstName = getInputNoNewline(50, "What is your first name: "); //50 will return blank
players[i].lastName = getInputNoNewline(49, "What is your last name: "); //49 will return fine
intIn = getInputNoNewline(4, "What is your YOB: "); //TODO: convert number to integer with sscanf
printf("-----------------------------------\n");
}
printf("Finished\n");
return 0;
}
This is the output, as you can see the first input of jim is received from fgets, but the return value is blank (raw input : ). If I was to reduce the max value from 50 to 49, as per the case for the last name field, it works perfectly fine. Any thoughts?
Hello world Game
What is your first name: jim
input: jim
raw input : final input: ''
What is your last name: smith
input: smith
raw input : smith
final input: 'smith'
What is your YOB: 1984
input: 1984
raw input : 1984
final input: '1984'
-----------------------------------
Since you allocate in
to be 50 character long, and you allow 52 characters to be read, you will run into trouble! You want to use
static char* in;
if(in!=NULL) free(in);
in = (char*)malloc(max + 2);
This addresses both the point that Alok raised (about local scope pointer not being defined once function returns), and the fact that your function allows fgets
to write max+2
characters into the buffer in
.