Вот такая караганда живёт уже больше года и не кашляет:
//IniFile enables handling the storage and retrieval
//of application-specific information and settings
//in a standard file. An INI file stores information
//in logical groupings, called "sections."
//Within each section, actual data values are stored
//in named keys. Keys take the form:
//
//[section]
//keyname=value
//
// все строки файла имеют длину MAX_LEN_INISTR
// Ограничение введено для того, чтобы работать с файлом
// через буфер редактирования на одну строку.
//
// v1.0 (2007-02-06)
//-----------------------------------------------------------------------------------
// Includes
//-----------------------------------------------------------------------------------
#include <string.h>
#include "F34x_MSD_File_System.h"
#include "IniFiles.h"
//-----------------------------------------------------------------------------------
// Global CONSTANTS
//-----------------------------------------------------------------------------------
#define MAX_LEN_INISTR 32
//----------------------------------------------------------------------------
// setbuf
//----------------------------------------------------------------------------
//
// заполнение буфера редактирования
// ФОРМАТ: <keyname=value ENDLINE>
// длина: len
//----------------------------------------------------------------------------
static char * setbuf(char * buf, int len, char * keyname, char * value)
{
int xdata i;
memset (buf, ' ', len);
i= strlen(keyname);
memcpy (buf, keyname, i);
buf[i]= '=';
memcpy (buf+i+1,value,strlen(value));
i= strlen(ENDLINE);
memcpy (buf+len-i, ENDLINE, i);
return buf;
}
//----------------------------------------------------------------------------
// setrow
//----------------------------------------------------------------------------
//
// вставка <offset> символов в ini-файл
// в текущем смещении <pos>
//----------------------------------------------------------------------------
static BYTE setrow(char * buf, int pos, int offset, FILE *f)
{
BYTE xdata res=1;
int xdata n,k;
n= (f->size - pos)/MAX_LEN_INISTR;
k= (f->size - pos)%MAX_LEN_INISTR;
if (n > 0) f->pos= f->size - MAX_LEN_INISTR;
while (n > 0) //перенесем целые строки
{
res &= fread(f,buf,MAX_LEN_INISTR) >0;
f->pos= f->pos - MAX_LEN_INISTR + offset;
res &= fwrite(f,buf,MAX_LEN_INISTR) >0;
f->pos= f->pos - 2*MAX_LEN_INISTR - offset;
n--;
}
f->pos= pos; //перенесем остаток целой строки
res &= fread(f,buf,k) >0;
f->pos += offset - k;
res &= fwrite(f,buf,k) >0;
return res;
}
//----------------------------------------------------------------------------
// fgetsini
//----------------------------------------------------------------------------
//
// Чтение строки значения параметра <value> из ini-файла
// ATTN: параметр <[section]> указывать в квадратных скобках
// ФОРМАТ:
// [section]
// keyname=value
//----------------------------------------------------------------------------
char* fgetsini(char * buf, char * section, char * keyname, char * defaultvalue, FILE *f)
{
int i=0;
if (!(f->isopen))
return defaultvalue;
*buf= 0;
f->pos=0;
while (f->pos < f->size)
{
fgets(buf,MAX_LEN_INISTR, f);
if (strstr(buf, section)) //нашли нужную секцию
do //до следующей секции
{
fgets(buf,MAX_LEN_INISTR, f);
if (strstr(buf, keyname) && ((i=strpos(buf, '='))>0))
return buf+i+1;
} while (!strchr(buf,'['));
}
return defaultvalue;
}
//----------------------------------------------------------------------------
// fputsini
//----------------------------------------------------------------------------
//
// Запись строки значения параметра <value> в ini-файл
// (исп. буфер редактирования на одну строку)
// ФОРМАТ:
// [section]
// keyname=value
//----------------------------------------------------------------------------
BYTE fputsini(char * section, char * keyname, char * value, FILE *f)
{
char xdata buf[MAX_LEN_INISTR];
int xdata keypos;
BYTE xdata res=1;
if (!(f->isopen))
return 0;
*buf= 0;
f->pos=0;
while (f->pos < f->size)
{
fgets(buf,MAX_LEN_INISTR, f);
if (strstr(buf, section)) //нашли нужную секцию
{ do //до следующей секции или до конца файла, если секция последняя
{
keypos= f->pos;
fgets(buf,MAX_LEN_INISTR, f);
if (strstr(buf, keyname) && (strpos(buf, '=')>0))
{ //нашли нужный параметр
if (strlen(buf) < MAX_LEN_INISTR - strlen(ENDLINE))
res &= setrow(buf,keypos,MAX_LEN_INISTR-strlen(buf)- strlen(ENDLINE),f);//выравнивание строки
setbuf(buf,MAX_LEN_INISTR,keyname,value);
f->pos= keypos;
res &= fwrite(f,buf,MAX_LEN_INISTR) >0;
return res;
}
} while ((buf[0] != '[') && (f->pos < f->size));
if (f->pos < f->size) //вставить пустую строку перед след.секцией
res &= setrow(buf,keypos,MAX_LEN_INISTR,f);
//добавление имени параметра и значения в найденную секцию
setbuf(buf,MAX_LEN_INISTR,keyname,value);
f->pos= keypos;
res &= fwrite(f,buf,MAX_LEN_INISTR) >0;
return res;
}
}
// не нашли нужную секцию - добавление в конец файла
// новой секции, имени параметра и значения в эту секцию
res &= fwrite(f,section,strlen(section)) >0;
res &= fwrite(f,ENDLINE,strlen(ENDLINE)) >0;
setbuf(buf,MAX_LEN_INISTR,keyname,value);
res &= fwrite(f,buf,MAX_LEN_INISTR) >0;
return res;
}
-
- Лихо работаете с элементами структуры FILE. У меня файловая система попроще (PHAT из состава EtherNUT) такого не умеет. Написал нечто аналогичное на fgets/fputs, но не нравится. - Сидоргек(26.08.2008 16:06)
- FILE - это благоприобретённое от Silabs. Оказалась весьма удобной. Рэйлвэй Каген(363 знак., 26.08.2008 19:18)
- Лихо работаете с элементами структуры FILE. У меня файловая система попроще (PHAT из состава EtherNUT) такого не умеет. Написал нечто аналогичное на fgets/fputs, но не нравится. - Сидоргек(26.08.2008 16:06)