Doing it with scanf is a pain. Why not use a regular expression from C?
Here's a complete working program to show how easy it can be.
Start by reading all the data into a single string, data. I'm just using a constant.
Compile your pattern with regcomp, then apply it with regexec to your string.
It returns an array of matched groups which correspond to the (.*?) parts of the pattern.
Group 0 is of no interest in this example as it is just the entire data.
For the other 2 groups, you get the indexes in the string of the start and end of the match.
Use strndup() to copy these. Use strtok to split this dup on the newline \n character.
You have in ptr at each point each var and value.
/* regex example. meuh on stackoverflow */
#include <stdlib.h>
#include <sys/types.h>
#include <regex.h>
#include <errno.h>
#include <string.h>
#include <stdio.h>
void pexit(char *str){
extern int errno;
perror(str);
exit(errno);
}
#define NUMMATCH (1+2) /* max num matching capture groups in pattern */
main(int argc, char **argv){
regex_t myexpn;
regmatch_t matches[NUMMATCH] = {0};
int rc,i;
char *data = "\n\
MY_VARIABLE_BEGIN\n\
var1 \n\
var2\n\
...\n\
MY_VARIABLE_END\n\
MY_VALUES_BEGIN\n\
val1\n\
val2\n\
...\n\
MY_VALUES_END\n\
";
char *delim = "\n";
char *pattern = "\\s*MY_VARIABLE_BEGIN\\s*(.*?)MY_VARIABLE_END.*?MY_VALUES_BEGIN\\s*(.*?)MY_VALUES_END";
/* need REG_EXTENDED to use () in pattern else \\(\\) */
rc = regcomp(&myexpn, pattern, REG_EXTENDED);
if(rc!=0)pexit("regcomp");
rc = regexec(&myexpn, data, NUMMATCH, matches, 0);
if(rc==REG_NOMATCH)printf("no match\n");
else{
for(i = 1;i<NUMMATCH;i++){ /* ignore group 0 which is whole match */
if(matches[i].rm_so!=-1){
char *dup = strndup(data+matches[i].rm_so, matches[i].rm_eo-matches[i].rm_so);
printf(" match %d %d..%d \"%s\"\n",i, matches[i].rm_so, matches[i].rm_eo, dup);
char *ptr = strtok(dup, delim);
while(ptr){
printf(" token: %s\n",ptr);
ptr = strtok(NULL, delim);
}
free(dup);
}
}
}
regfree(&myexpn);
}
This prints out:
match 1 19..34 "var1
var2
...
"
token: var1
token: var2
token: ...
match 2 66..80 "val1
val2
...
"
token: val1
token: val2
token: ...
fgets(3)), then scan the start of the string for theMY_part, and if not, parse the variable (using e.g.sscanf(3)and store the variable into an array (increasing the array as necessary with e.g.realloc(3)). This is a very general way to do; you may be able to use some constraints on your input data. - user707650