常见cfg、ini文件如下:
[config1]
setting=192.168.1.1
[config2]
setting=192.168.1.2
[config3]
setting=192.168.1.3
示例代码使用
// opt_ini.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//#include <iostream>
#include "cfg.h"int main()
{cfg_load("config.cfg");cfg_print();cfg_set("config1","setting","192.168.101.78");cfg_save("config2.cfg");cfg_print();cfg_release();
}// 运行程序: Ctrl + F5 或调试 >“开始执行(不调试)”菜单
// 调试程序: F5 或调试 >“开始调试”菜单// 入门使用技巧:
// 1. 使用解决方案资源管理器窗口添加/管理文件
// 2. 使用团队资源管理器窗口连接到源代码管理
// 3. 使用输出窗口查看生成输出和其他消息
// 4. 使用错误列表窗口查看错误
// 5. 转到“项目”>“添加新项”以创建新的代码文件,或转到“项目”>“添加现有项”以将现有代码文件添加到项目
// 6. 将来,若要再次打开此项目,请转到“文件”>“打开”>“项目”并选择 .sln 文件
示例代码运行结果:
附主要代码:
static int cfg_parse_stream(CFG_reader reader, void* stream, CFG_handler handler,void* user)
{char line[CFG_MAX_LINE];size_t max_line = CFG_MAX_LINE;char section[MAX_SECTION] = "";char prev_name[MAX_NAME] = "";char* start;char* end;char* name;char* value;int lineno = 0;int error = 0;#define HANDLER(u, s, n, v) handler(u, s, n, v)while (reader(line, (int)max_line, stream) != NULL) {lineno++;start = line;if (lineno == 1 && (unsigned char)start[0] == 0xEF &&(unsigned char)start[1] == 0xBB &&(unsigned char)start[2] == 0xBF) {start += 3;}start = lskip(rstrip(start));if (strchr(CFG_START_COMMENT_PREFIXES, *start)) {/* Start-of-line comment */}else if (*prev_name && *start && start > line) {end = find_chars_or_comment(start, NULL);if (*end)*end = '\0';rstrip(start);if (!HANDLER(user, section, prev_name, start) && !error)error = lineno;}else if (*start == '[') {/* A "[section]" line */end = find_chars_or_comment(start + 1, "]");if (*end == ']') {*end = '\0';strncpy0(section, start + 1, sizeof(section));*prev_name = '\0';}else if (!error) {/* No ']' found on section line */error = lineno;}}else if (*start) {/* Not a comment, must be a name[=:]value pair */end = find_chars_or_comment(start, "=:");if (*end == '=' || *end == ':') {*end = '\0';name = rstrip(start);value = end + 1;end = find_chars_or_comment(value, NULL);if (*end)*end = '\0';value = lskip(value);rstrip(value);/* Valid name[=:]value pair found, call handler */strncpy0(prev_name, name, sizeof(prev_name));if (!HANDLER(user, section, name, value) && !error)error = lineno;}else if (!error) {error = lineno;}}}return error;
}static int cfg_parse_file(FILE* file, CFG_handler handler, void* user)
{return cfg_parse_stream((CFG_reader)fgets, file, handler, user);
}static int cfg_parse(const char* filename, CFG_handler handler, void* user)
{FILE* file;int error;file = fopen(filename, "r");if (!file) {cfg_error("%s:%03d open %s error!\n", __FUNCTION__, __LINE__, filename);return -1;}error = cfg_parse_file(file, handler, user);fclose(file);return error;
}
int User;
static char Prev_section[50];static unsigned int TrailerDateOfProduction(char* s)
{unsigned int ret;int i;ret = 0;if (!s){return 0;}while (*s != '\0') {if (*s=='-')s++;if (*s >= '0' && *s <= '9')i = *s - '0';else if (*s >= 'a' && *s <= 'f')i = *s - 'a' + 0xa;else if (*s >= 'A' && *s <= 'F')i = *s - 'A' + 0xa;elsereturn 0;ret = (ret << 4) + i;s++;}return ret;
}/*** \description cfg init.* * \author sunsz* \date 2023/09/23 * */
static int GetConfig(void* user, const char* section, const char* name, const char* value){size_t len = 0;unsigned int cfg_num = 0;unsigned int cfg_data_num = 0;User = *((int*)user);if (!section) {return 1;}if (!name) {return 1;}if (!value) {cfg_error("%s:%03d [%s]%s = null\n", __FUNCTION__, __LINE__, section, name);return 1;}if (section && (!_stricmp(section, Prev_section))) {len = strlen(section);cfg_num = _cfg_config.cfg_section_num - 1;cfg_data_num = _cfg_config.cfg_section[cfg_num].cfg_data_num;_cfg_config.cfg_section[cfg_num].cfg_section_name = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_section_name != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_section_name, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_section_name, section);} len = strlen(name);_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name, name);}len = strlen(value);_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value, value);}_cfg_config.cfg_section[cfg_num].cfg_data_num++;strcpy(Prev_section, section);return 0;}else if (section) {cfg_num = _cfg_config.cfg_section_num;cfg_data_num = _cfg_config.cfg_section[cfg_num].cfg_data_num;len = strlen(section);_cfg_config.cfg_section[cfg_num].cfg_section_name = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_section_name != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_section_name, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_section_name, section);}len = strlen(name);_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name, name);}len = strlen(value);_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value, value);}_cfg_config.cfg_section[cfg_num].cfg_data_num++;_cfg_config.cfg_section_num++;strcpy(Prev_section, section);return 0;}return 0;
}
/*** \description set cfg value.* * \author sunsz* \date 2023/09/23 * */
int cfg_set(const char*section, const char*name, const char*value) {int len = 0;int _sectionin = 0;unsigned int cfg_num = 0;unsigned int cfg_data_num = 0;cfg_debug("%s:%03d\n", __FUNCTION__, __LINE__);if (section == NULL || name == NULL || value == NULL) {cfg_error("%s:%03d parameter null!\n", __FUNCTION__, __LINE__);return 1;}for (size_t i = 0; i < _cfg_config.cfg_section_num; i++) {if (!_stricmp(_cfg_config.cfg_section[i].cfg_section_name, section)) {_sectionin = 1;for (size_t j = 0; j < _cfg_config.cfg_section[i].cfg_data_num; j++) {if (_cfg_config.cfg_section[i].cfg_data[j].cfg_name) {if (!_stricmp(_cfg_config.cfg_section[i].cfg_data[j].cfg_name, name)) {if (_cfg_config.cfg_section[i].cfg_data[j].cfg_value != NULL) {len = strlen(_cfg_config.cfg_section[i].cfg_data[j].cfg_value);memset(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, 0, len);free(_cfg_config.cfg_section[i].cfg_data[j].cfg_value);_cfg_config.cfg_section[i].cfg_data[j].cfg_value = NULL;if (value[0]) {len = strlen(value);_cfg_config.cfg_section[i].cfg_data[j].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[i].cfg_data[j].cfg_value != NULL) {memset(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, value);}}else {len = 1;_cfg_config.cfg_section[i].cfg_data[j].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[i].cfg_data[j].cfg_value != NULL) {memset(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, "");}}}else {if (value[0]) {len = strlen(value);_cfg_config.cfg_section[i].cfg_data[j].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[i].cfg_data[j].cfg_value != NULL) {memset(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, value);}}else {len = 1;_cfg_config.cfg_section[i].cfg_data[j].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[i].cfg_data[j].cfg_value != NULL) {memset(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[i].cfg_data[j].cfg_value, "");}}}return 0;}}}//没有找到nameif (name[0] && value[0]) {len = strlen(name);cfg_data_num = _cfg_config.cfg_section[i].cfg_data_num;_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_name = malloc(len + 1);if (_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_name != NULL) {memset(_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_name, 0, len + 1);strcpy(_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_name, name);}len = strlen(value);_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_value != NULL) {memset(_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[i].cfg_data[cfg_data_num].cfg_value, value);}_cfg_config.cfg_section[i].cfg_data_num++;return 0;}} }if (!_sectionin) {//没有找到sectionif (name[0] && value[0]) {len = strlen(section);cfg_num = _cfg_config.cfg_section_num;cfg_data_num = _cfg_config.cfg_section[cfg_num].cfg_data_num;_cfg_config.cfg_section[cfg_num].cfg_section_name = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_section_name != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_section_name, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_section_name, section);}len = strlen(name);_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_name, name);}len = strlen(value);_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value = malloc(len + 1);if (_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value != NULL) {memset(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value, 0, len + 1);strcpy(_cfg_config.cfg_section[cfg_num].cfg_data[cfg_data_num].cfg_value, value);}_cfg_config.cfg_section[cfg_num].cfg_data_num++;_cfg_config.cfg_section_num++;return 0;}}return 1;
}
/*** \description get value by section and name.* * \author sunsz* \date 2023/09/23 * */
char* cfg_get(const char* section, const char* name) {int len = 0;int _sectionin = 0;unsigned int cfg_num = 0;unsigned int cfg_data_num = 0;cfg_debug("%s:%03d\n", __FUNCTION__, __LINE__);if (section == NULL || name == NULL) {cfg_error("%s:%03d parameter null!\n", __FUNCTION__, __LINE__);return NULL;}for (size_t i = 0; i < _cfg_config.cfg_section_num; i++) {if (!_stricmp(_cfg_config.cfg_section[i].cfg_section_name, section)) {_sectionin = 1;for (size_t j = 0; j < _cfg_config.cfg_section[i].cfg_data_num; j++) {if (_cfg_config.cfg_section[i].cfg_data[j].cfg_name) {if (!_stricmp(_cfg_config.cfg_section[i].cfg_data[j].cfg_name, name))return _cfg_config.cfg_section[i].cfg_data[j].cfg_value;}}}}return NULL;
}
/*** \description write cfg data to log.* * \author sunsz* \date 2023/09/23 * */
void cfg_print() {cfg_debug("%s:%03d\n", __FUNCTION__, __LINE__);cfg_info("\n");for (size_t i = 0; i < _cfg_config.cfg_section_num; i++) {cfg_info("[%s]\n", _cfg_config.cfg_section[i].cfg_section_name);for (size_t j = 0; j < _cfg_config.cfg_section[i].cfg_data_num; j++) {cfg_info("%s=%s\n", _cfg_config.cfg_section[i].cfg_data[j].cfg_name, _cfg_config.cfg_section[i].cfg_data[j].cfg_value);}}
}
/*** \description write cfg data.* * \author sunsz* \date 2023/09/23 * */
int cfg_save(const char* cfg_name) {FILE* file;char buffer[1024] = { 0x00 };cfg_debug("%s:%03d\n", __FUNCTION__, __LINE__);file = fopen(cfg_name, "w");if (!file) {cfg_error("%s:%03d open %s error!\n",__FUNCTION__,__LINE__, cfg_name);return 1;}for (size_t i = 0; i < _cfg_config.cfg_section_num; i++) {memset(buffer, 0, 1024);sprintf(buffer, "[%s]\n", _cfg_config.cfg_section[i].cfg_section_name);fwrite(buffer,1,strlen(buffer), file);for (size_t j = 0; j < _cfg_config.cfg_section[i].cfg_data_num; j++) {sprintf(buffer, "%s=%s\n", _cfg_config.cfg_section[i].cfg_data[j].cfg_name, _cfg_config.cfg_section[i].cfg_data[j].cfg_value);fwrite(buffer, 1, strlen(buffer), file);}}fclose(file);return 0;
}
/*** \description release cfg memory.* * \author sunsz* \date 2023/09/23 * */
void cfg_release() {cfg_debug("%s:%03d\n", __FUNCTION__, __LINE__);for (size_t i = 0; i < _cfg_config.cfg_section_num; i++) {if (_cfg_config.cfg_section[i].cfg_section_name != NULL) {free(_cfg_config.cfg_section[i].cfg_section_name);_cfg_config.cfg_section[i].cfg_section_name = NULL;}for (size_t j = 0; j < _cfg_config.cfg_section[i].cfg_data_num; j++) {if (_cfg_config.cfg_section[i].cfg_data[j].cfg_name != NULL) {free(_cfg_config.cfg_section[i].cfg_data[j].cfg_name);_cfg_config.cfg_section[i].cfg_data[j].cfg_name = NULL;}if (_cfg_config.cfg_section[i].cfg_data[j].cfg_value != NULL) {free(_cfg_config.cfg_section[i].cfg_data[j].cfg_value);_cfg_config.cfg_section[i].cfg_data[j].cfg_value = NULL;}}_cfg_config.cfg_section[i].cfg_data_num = 0;}_cfg_config.cfg_section_num = 0;
}
/*** \description read cfg.* * \author sunsz* \date 2023/09/23 * */
int cfg_load(const char *cfg_name) {static int u = 100;int e;*Prev_section = '\0';cfg_debug("%s:%03d\n", __FUNCTION__, __LINE__);memset(&_cfg_config, 0, sizeof(CFG_CONFIG));_cfg_config.cfg_section_num = 0;e = cfg_parse(cfg_name, GetConfig, &u);u++;return e;
}