3 01-28-02 : Change the location of temporary files created in write_private_profile_string
4 now done in TmpDirectory.
5 01-29-02 : Correct bug when the '=' character is not present.
6 06-18-02 : Return default value if file does not exist, new write_private_profile_int function.
9 /***** Routines to read profile strings -- by Joseph J. Graf ******/
10 /***** corrections and improvements -- by D. Fober - Grame ******/
12 corrections: buffer sizes control
13 improvements: behavior more similar to windows
24 #include "profport.h" /* function prototypes in here */
28 static int read_line (FILE *fp
, char *bp
, int size
);
29 static int read_section(FILE *fp
, char *section
);
30 static int read_entry (FILE *fp
, char *entry
, char *buff
, int size
);
31 static char * read_value (char *buff
);
32 static int read_int_value (char *buff
, int def
);
33 static char * read_file (char *file
);
34 static char * str_search (char * buff
, char * str
, int stopCond
);
36 /*****************************************************************
37 * Function: read_line()
38 * Arguments: <FILE *> fp - a pointer to the file to be read from
39 * <char *> bp - a pointer to the copy buffer
40 * <int> size - size of the copy buffer
41 * Returns: the line length if successful -1 otherwise
42 ******************************************************************/
43 static int read_line(FILE *fp
, char *bp
, int size
)
46 int i
= 0, limit
= size
-2;
48 /* Read one line from the source file */
49 while (((c
= getc(fp
)) != '\n') && (i
< limit
)) {
60 static int read_section (FILE *fp
, char *section
)
62 char buff
[MAX_LINE_LENGTH
];
63 char t_section
[MAX_LINE_LENGTH
];
66 sprintf(t_section
,"[%s]", section
); /* Format the section name */
67 slen
= strlen (t_section
);
68 /* Move through file 1 line at a time until a section is matched or EOF */
70 n
= read_line(fp
, buff
, MAX_LINE_LENGTH
);
73 } while (strncmp (buff
,t_section
, slen
));
77 static int read_entry (FILE *fp
, char *entry
, char *buff
, int size
)
79 int n
, elen
= strlen (entry
);
82 n
= read_line(fp
, buff
, size
);
85 else if (*buff
== '[')
87 } while (strncmp (buff
, entry
, elen
));
91 #define isBlank(c) ((c == ' ') || (c == '\t'))
92 static char * read_value (char *buff
)
94 char * eq
= strrchr (buff
,'='); /* Parse out the equal sign */
97 while (*eq
&& isBlank(*eq
))
99 // return *eq ? eq : 0;
105 #define isSignedDigit(c) (isdigit(c) || (c == '+') || (c == '-'))
106 static int read_int_value (char *buff
, int def
)
108 char * val
= read_value (buff
);
109 char value
[20]; int i
;
111 if (!*val
) return def
;
113 for (i
= 0; isSignedDigit(*val
) && (i
<= 10); i
++ )
116 return value
[0] ? atoi(value
) : def
;
119 static char * read_file (char *file
)
121 FILE *fd
= fopen (file
,"r");
122 int size
; char * buff
= 0;
125 if (fseek (fd
, 0, SEEK_END
) == -1) goto err
;
127 if (size
< 0) goto err
;
128 if (fseek (fd
, 0, SEEK_SET
) == -1) goto err
;
129 buff
= (char *) malloc (size
+1);
132 fread (buff
, 1, size
, fd
);
140 static char * str_search (char * buff
, char * str
, int stopCond
)
143 int len
= strlen (str
);
144 while (*ptr
&& strncmp (ptr
, str
, len
)) {
145 while (*ptr
&& (*ptr
++ != '\n'))
147 if (*ptr
== stopCond
)
150 return *ptr
? ptr
: 0;
153 /**************************************************************************
154 * Function: get_private_profile_int()
155 * Arguments: <char *> section - the name of the section to search for
156 * <char *> entry - the name of the entry to find the value of
157 * <int> def - the default value in the event of a failed read
158 * <char *> file_name - the name of the .ini file to read from
159 * Returns: the value located at entry
160 ***************************************************************************/
161 int get_private_profile_int(char *section
,
162 char *entry
, int def
, char *file_name
)
164 FILE *fp
= fopen(file_name
,"r");
165 char buff
[MAX_LINE_LENGTH
];
167 if( !fp
) return def
; /* Return default value if file does not exist */
168 if (!read_section (fp
, section
)) goto err
;
169 if (!read_entry (fp
, entry
, buff
, MAX_LINE_LENGTH
)) goto err
;
170 def
= read_int_value (buff
, def
);
176 /**************************************************************************
177 * Function: get_private_profile_string()
178 * Arguments: <char *> section - the name of the section to search for
179 * <char *> entry - the name of the entry to find the value of
180 * <char *> def - default string in the event of a failed read
181 * <char *> buffer - a pointer to the buffer to copy into
182 * <int> buffer_len - the max number of characters to copy
183 * <char *> file_name - the name of the .ini file to read from
184 * Returns: the number of characters copied into the supplied buffer
185 ***************************************************************************/
187 int get_private_profile_string(char *section
, char *entry
, char *def
,
188 char *buffer
, int buffer_len
, char *file_name
)
190 FILE *fp
= fopen (file_name
,"r");
191 char buff
[MAX_LINE_LENGTH
];
194 if( !fp
) goto err
; /* Return default value if file does not exist */
195 if (!read_section (fp
, section
)) goto err
;
196 if (!read_entry (fp
, entry
, buff
, MAX_LINE_LENGTH
)) goto err
;
197 val
= read_value (buff
);
203 strncpy (buffer
, def
, buffer_len
- 1);
204 buffer
[buffer_len
] = '\0';
206 else buffer
[buffer_len
] = '\0';
207 return strlen (buffer
);
211 /***************************************************************************
212 * Function: write_private_profile_string()
213 * Arguments: <char *> section - the name of the section to search for
214 * <char *> entry - the name of the entry to find the value of
215 * <char *> buffer - pointer to the buffer that holds the string
216 * <char *> file_name - the name of the .ini file to read from
217 * Returns: TRUE if successful, otherwise FALSE
218 ***************************************************************************/
219 int write_private_profile_string(char *section
,
220 char *entry
, char *buffer
, char *file_name
)
223 char * content
= read_file(file_name
);
224 FILE * fd
= fopen(file_name
,"w");
225 char t_section
[MAX_LINE_LENGTH
], *ptr
;
230 fprintf (fd
, "[%s]\n%s = %s\n", section
, entry
, buffer
);
234 sprintf(t_section
,"[%s]",section
); /* Format the section name */
235 ptr
= str_search (content
, t_section
, 0); /* look for the section start */
237 /* no such section: add the new section at end of file */
238 fprintf (fd
, "%s\n[%s]\n%s = %s\n", content
, section
, entry
, buffer
);
242 eptr
= str_search (ptr
, entry
, '[');
244 /* no such entry: looks for next section */
245 eptr
= str_search (++ptr
, "[", 0);
247 /* section is the last one */
248 fprintf (fd
, "%s\n%s = %s\n", content
, entry
, buffer
);
251 while (*ptr
&& (*ptr
!= '\n')) ptr
++;
253 fprintf (fd
, "%s\n%s = %s", content
, entry
, buffer
);
255 fprintf (fd
, "%s", ptr
);
260 fprintf (fd
, "%s%s = %s", content
, entry
, buffer
);
261 while (*eptr
&& (*eptr
!= '\n')) eptr
++;
262 if (eptr
) fprintf (fd
, "%s", eptr
);
268 if (content
) free(content
);
273 /***************************************************************************
274 * Function: write_private_profile_int()
275 * Arguments: <char *> section - the name of the section to search for
276 * <char *> entry - the name of the entry to find the value of
277 * <int> buffer - the value to be written
278 * <char *> file_name - the name of the .ini file to read from
279 * Returns: TRUE if successful, otherwise FALSE
280 ***************************************************************************/
281 int write_private_profile_int(char *section
,
282 char *entry
, int val
, char *file_name
)
285 sprintf(buffer
, "%d", val
);
286 return write_private_profile_string (section
,entry
, buffer
, file_name
);
289 #endif // #ifndef WIN32
292 /**************************************************************************
293 * Function: get_private_profile_float()
294 * Arguments: <char *> section - the name of the section to search for
295 * <char *> entry - the name of the entry to find the value of
296 * <float> def - the default value in the event of a failed read
297 * <char *> file_name - the name of the .ini file to read from
298 * Returns: the value located at entry
299 * Warning: The float value to be read must not contain more than 100 digits.
300 * Author: CD, 15/11/2006.
301 ***************************************************************************/
302 #define maxFloatLen 100
303 float get_private_profile_float (char * section
, char * entry
, float def
, char * file_name
)
306 char buffer
[ maxFloatLen
], *endptr
;
308 if ( get_private_profile_string(section
, entry
, "", buffer
, maxFloatLen
, file_name
) > 0 )
310 result
= (float)strtod(buffer
, &endptr
);
311 if ((result
==0) && (endptr
==buffer
))