I am parsing a macro definition from a Makefile into two strings, the name of the macro and the body. For example here is a macro definition line from my Makefile:
macro-1 = body-1
My code produces a bus error/segmentation fault.
static void parse_macro_def(const char* line)
{
char* m_name;
int name_pos = 0;
int i = 0;
while(line[i++] != '=') //iterate until an equal sign is found
{
if(!isspace(line[i])) //copy characters to m_name unless the character is whitespace
{
m_name[name_pos++] = line[i];
}
}
}
m_name[name_pos] = '\0';
m_name should be set to macro-1
Thanks for all the help!
You don’t initialize
m_nameso it points anywhere, so you are writing at random, and crashing.You need to allocate and return the space, or pass the space in (along with the length of the space), ensuring you don’t overwrite in every case.
You should note that white space characters in a macro name are a bug in the macro definition. There can be leading white space; there can be trailing white space; but there can’t be white space in the middle of a name. Now, if you are assuming that you have been given a valid, working
Makefileto parse, you may be able to get away with ignoring this subtlety. If you’re writing a replacement formake, you can’t.Unless you’ve previously validated that there is an equals sign in the string, you should also check that you don’t run off the end of the string (you don’t scan past a NUL
'\0'). In fact, in robust code, you’d probably ensure that out of paranoia.And, while writing that, I realized that you increment
iin thewhilecondition, and then check whether the next character is a space in the body of the loop. That’s a little aconventional, shall we say. If you come across a macro:you will copy the
=intom_namewhen the loop condition checks theO. And, AFAICS, you won’t copy theM.Note that your line:
is outside any function and therefore a syntax error.