code_device/hgsane/ini_file.cpp

244 lines
4.6 KiB
C++
Raw Normal View History

2022-05-03 03:56:07 +00:00
#include "ini_file.h"
#include <stdlib.h>
#include <string.h>
#ifdef WIN32
#define bzero(b, s) memset(b, 0, s)
#endif
simple_ini::simple_ini()
{}
simple_ini::~simple_ini()
{}
std::string simple_ini::temporary_path(void)
{
#ifdef WIN32
char path[MAX_PATH] = { 0 };
if (GetTempPathA(_countof(path) - 1, path))
{
if (path[lstrlenA(path) - 1] == '\\')
path[lstrlenA(path) - 1] = 0;
}
return path;
#else
return "/tmp";
#endif
}
bool simple_ini::skip_empty(char*& ptr)
{
char* p = ptr;
while(*ptr == ' ' || *ptr == '\t' || *ptr == '\r' || *ptr == '\n')
ptr++;
return ptr > p;
}
void simple_ini::trime(char*& ptr)
{
skip_empty(ptr);
char* tail = ptr + strlen(ptr) - 1;
while (tail >= ptr)
{
if (*tail != ' ' && *tail != '\t' && *tail != '\r' && *tail != '\n')
break;
tail--;
}
tail[1] = 0;
}
int simple_ini::load(const char* local_file)
{
int ret = 0;
#ifdef WIN32
file_ = local_file;
#else
values_.clear();
FILE* src = fopen(local_file, "rb");
if (src)
{
char line[256];
char* oper = NULL;
SECKEY sec;
bzero(line, sizeof(line));
while (fgets(line, sizeof(line) - 1, src))
{
oper = line;
simple_ini::skip_empty(oper);
if (strstr(oper, "//") == oper ||
strstr(oper, "#") == oper ||
*oper == 0)
{
bzero(line, sizeof(line));
continue;
}
if (*oper == '[')
{
oper++;
if (strstr(oper, (char*)"]"))
strstr(oper, (char*)"]")[0] = 0;
if (sec.sec != oper)
{
if (sec.vals.size())
values_.push_back(sec);
sec.vals.clear();
sec.sec = oper;
std::vector<SECKEY>::iterator it = std::find(values_.begin(), values_.end(), oper);
if (it != values_.end())
{
sec = *it;
values_.erase(it);
}
}
}
else
{
char* v = strstr(oper, "=");
if (v)
{
*v++ = 0;
trime(oper);
if (*oper)
{
trime(v);
KEYVAL kv;
kv.key = oper;
kv.val = v;
sec.vals.push_back(kv);
std::sort(sec.vals.begin(), sec.vals.end());
}
}
}
bzero(line, sizeof(line));
}
fclose(src);
if (sec.vals.size())
values_.push_back(sec);
std::sort(values_.begin(), values_.end());
}
else
ret = errno;
#endif
return ret;
}
#ifndef WIN32
int simple_ini::save(const char* local_file)
{
FILE* dst = fopen(local_file, "wb");
if (dst)
{
for (size_t i = 0; i < values_.size(); ++i)
{
std::string val(values_[i].sec);
val.insert(0, "[");
val += "]\r\n";
fwrite(val.c_str(), 1, val.length(), dst);
for (size_t j = 0; j < values_[i].vals.size(); ++j)
{
val = values_[i].vals[j].key + "=" + values_[i].vals[j].val + "\r\n";
fwrite(val.c_str(), 1, val.length(), dst);
}
val = "\r\n";
fwrite(val.c_str(), 1, val.length(), dst);
}
fclose(dst);
}
else
return errno;
}
#endif
std::string simple_ini::get(const char* sec, const char* key, const char* default_val)
{
#ifdef WIN32
char str[MAX_PATH] = { 0 };
GetPrivateProfileStringA(sec, key, default_val, str, _countof(str), file_.c_str());
return str;
#else
std::vector<SECKEY>::iterator it = std::find(values_.begin(), values_.end(), sec);
if (it == values_.end())
return default_val;
std::vector<KEYVAL>::iterator it1 = std::find(it->vals.begin(), it->vals.end(), key);
if (it1 == it->vals.end())
return default_val;
else
return it1->val;
#endif
}
void simple_ini::set(const char* sec, const char* key, const char* val)
{
#ifdef WIN32
WritePrivateProfileStringA(sec, key, val, file_.c_str());
#else
std::vector<SECKEY>::iterator it = std::find(values_.begin(), values_.end(), sec);
if (it == values_.end())
{
KEYVAL kv;
SECKEY sk;
kv.key = key;
kv.val = val;
sk.sec = sec;
sk.vals.push_back(kv);
values_.push_back(sk);
std::sort(values_.begin(), values_.end());
return;
}
std::vector<KEYVAL>::iterator it1 = std::find(it->vals.begin(), it->vals.end(), key);
if (it1 == it->vals.end())
{
KEYVAL kv;
kv.key = key;
kv.val = val;
it->vals.push_back(kv);
std::sort(it->vals.begin(), it->vals.end());
}
else
it1->val = val;
#endif
}
void simple_ini::remove(const char* sec, const char* key)
{
#ifdef WIN32
#else
std::vector<SECKEY>::iterator it = std::find(values_.begin(), values_.end(), sec);
if (it == values_.end())
return;
std::vector<KEYVAL>::iterator it1 = std::find(it->vals.begin(), it->vals.end(), key);
if (it1 != it->vals.end())
it->vals.erase(it1);
#endif
}
void simple_ini::remove(const char* sec)
{
#ifdef WIN32
std::vector<SECKEY>::iterator it = std::find(values_.begin(), values_.end(), sec);
if (it != values_.end())
values_.erase(it);
#else
#endif
}
void simple_ini::clear(void)
{
values_.clear();
}