mirror of
https://github.com/chris2511/xca.git
synced 2026-09-14 11:06:19 +05:00
File IO exceptions added and database access improved
This commit is contained in:
parent
7066a59eaa
commit
37eb802e14
66
lib/db.cpp
66
lib/db.cpp
@ -1,5 +1,6 @@
|
||||
#include "db.h"
|
||||
#include "base.h"
|
||||
#include "exception.h"
|
||||
#ifdef __WIN32__
|
||||
#include <windows.h>
|
||||
#else
|
||||
@ -20,11 +21,7 @@ db::db(QString filename, int mode)
|
||||
name = filename;
|
||||
fd = open(CCHAR(filename), O_RDWR | O_CREAT, mode);
|
||||
if (fd<0) {
|
||||
errstr = QString("DB open() failed: ") + filename +" "+
|
||||
strerror(errno);
|
||||
dberrno = errno;
|
||||
perror(CCHAR(filename));
|
||||
|
||||
fileIOerr("open");
|
||||
} else {
|
||||
first();
|
||||
}
|
||||
@ -36,6 +33,13 @@ db::~db()
|
||||
close(fd);
|
||||
}
|
||||
|
||||
void db::fileIOerr(QString s)
|
||||
{
|
||||
errstr = QString("DB ") + s + "() '" + name + "'";
|
||||
dberrno = errno;
|
||||
throw errorEx(errstr, strerror(errno));
|
||||
}
|
||||
|
||||
void db::init_header(db_header_t *db, int ver, int len, enum pki_type type,
|
||||
const char *name)
|
||||
{
|
||||
@ -74,10 +78,8 @@ bool db::verify_magic(void)
|
||||
int db::find(enum pki_type type, const char *name)
|
||||
{
|
||||
//int len, ret=0;
|
||||
if (head_offset == OFF_EOF)
|
||||
return 1;
|
||||
|
||||
do {
|
||||
while (head_offset != OFF_EOF) {
|
||||
//printf("Comparing %s -> %s at %lu\n", head.name, name,
|
||||
//head_offset);
|
||||
if (ntohs(head.type) == type) {
|
||||
@ -92,8 +94,8 @@ int db::find(enum pki_type type, const char *name)
|
||||
if (!verify_magic()) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
} while (next() == 0);
|
||||
next();
|
||||
}
|
||||
//printf("Returning 1\n");
|
||||
return 1;
|
||||
}
|
||||
@ -104,7 +106,9 @@ void db::first(void)
|
||||
memset(&head, 0, sizeof(db_header_t) );
|
||||
head_offset = lseek(fd, 0, SEEK_SET );
|
||||
ret = read(fd, &head, sizeof(db_header_t) );
|
||||
if (ret<=0) {
|
||||
if (ret < 0 )
|
||||
fileIOerr("read");
|
||||
if (ret==0) {
|
||||
head_offset = OFF_EOF;
|
||||
return;
|
||||
}
|
||||
@ -129,7 +133,7 @@ int db::next(void)
|
||||
return 1;
|
||||
}
|
||||
if (ret < 0) {
|
||||
printf("read() failed: %s\n", strerror(errno));
|
||||
fileIOerr("read");
|
||||
return -1;
|
||||
}
|
||||
if (ret != sizeof(db_header_t)) {
|
||||
@ -169,6 +173,9 @@ int db::rename(enum pki_type type, const char *name, const char *n)
|
||||
head.name[NAMELEN-1] = '\0';
|
||||
lseek(fd, head_offset, SEEK_SET);
|
||||
ret = write(fd, &head, sizeof(head));
|
||||
if (ret < 0) {
|
||||
fileIOerr("write");
|
||||
}
|
||||
if (ret != sizeof(head)) {
|
||||
printf("DB: Write error %d - %d\n", ret, sizeof(head));
|
||||
return -1;
|
||||
@ -203,11 +210,11 @@ int db::add(const unsigned char *p, int len, int ver, enum pki_type type,
|
||||
lseek(fd, 0, SEEK_END);
|
||||
|
||||
if (write(fd, &db, sizeof(db)) != sizeof(db)) {
|
||||
printf("write() failed\n");
|
||||
fileIOerr("write");
|
||||
return -1;
|
||||
}
|
||||
if (write(fd, p, len) != len) {
|
||||
printf("write() failed\n");
|
||||
fileIOerr("write");
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
@ -225,9 +232,9 @@ int db::set(const unsigned char *p, int len, int ver, enum pki_type type,
|
||||
return add(p, len, ver, type, name);
|
||||
}
|
||||
if (ret == 0) {
|
||||
printf("offs = %x, len=%d, head.len=%d name = %s flags=%x\n",
|
||||
head_offset, len, ntohl(head.len), head.name,
|
||||
ntohs(head.flags));
|
||||
//printf("offs = %x, len=%d, head.len=%d name = %s flags=%x\n",
|
||||
// head_offset, len, ntohl(head.len), head.name,
|
||||
// ntohs(head.flags));
|
||||
lseek(fd, head_offset, SEEK_SET);
|
||||
if (len != ntohl(head.len) - sizeof(db_header_t)) {
|
||||
//printf("## Found and len unequal %d, %d\n",
|
||||
@ -239,14 +246,15 @@ int db::set(const unsigned char *p, int len, int ver, enum pki_type type,
|
||||
if (write(fd, &head, sizeof(db_header_t)) !=
|
||||
sizeof(db_header_t))
|
||||
{
|
||||
printf("erasing of %s at failed\n", head.name);
|
||||
dberrno = errno;
|
||||
fileIOerr("write");
|
||||
return -1;
|
||||
}
|
||||
if (add(p, len, ver, type, name) < 0) {
|
||||
lseek(fd, head_offset, SEEK_SET);
|
||||
head.flags = flags;
|
||||
write(fd, &head, sizeof(db_header_t));
|
||||
ret = write(fd, &head, sizeof(db_header_t));
|
||||
if (ret != sizeof(db_header_t))
|
||||
fileIOerr("write");
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -254,11 +262,11 @@ int db::set(const unsigned char *p, int len, int ver, enum pki_type type,
|
||||
head.version = htons(ver);
|
||||
if (write(fd, &head, sizeof(db_header_t)) !=
|
||||
sizeof(db_header_t)) {
|
||||
printf("write() failed\n");
|
||||
fileIOerr("write");
|
||||
return -1;
|
||||
}
|
||||
if (write(fd, p, len) != len) {
|
||||
printf("write() failed\n");
|
||||
fileIOerr("write");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
@ -284,8 +292,8 @@ unsigned char *db::load(db_header_t *u_header)
|
||||
return data;
|
||||
|
||||
} else {
|
||||
printf("read of %u bytes failed: %d\n", size, ret);
|
||||
free(data);
|
||||
fileIOerr("read");
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
@ -299,8 +307,7 @@ int db::erase(void)
|
||||
|
||||
lseek(fd, head_offset, SEEK_SET);
|
||||
if (write(fd, &head, sizeof(db_header_t)) != sizeof(db_header_t)) {
|
||||
printf("erasing of %s at %u failed\n", head.name, head_offset);
|
||||
dberrno = errno;
|
||||
fileIOerr("write");
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
@ -308,15 +315,14 @@ int db::erase(void)
|
||||
|
||||
int db::shrink(int flags)
|
||||
{
|
||||
int fdn, ret, i=0;
|
||||
int fdn, ret;
|
||||
uint32_t offs;
|
||||
char buf[BUFSIZ];
|
||||
|
||||
QString filename = name + "{new}";
|
||||
fdn = open(CCHAR(filename), O_RDWR | O_CREAT, 0644);
|
||||
if (fdn<0) {
|
||||
errstr = QString("open() failed: ") + filename +" "+
|
||||
strerror(errno);
|
||||
fileIOerr("open");
|
||||
return 1;
|
||||
}
|
||||
lseek(fd, 0, SEEK_SET);
|
||||
@ -328,9 +334,9 @@ int db::shrink(int flags)
|
||||
if ((ntohs(head.flags) & flags)) {
|
||||
//printf("Skip Entry\n");
|
||||
/* FF to the next entry */
|
||||
offs = (int)lseek(fd, head_offset, SEEK_CUR);
|
||||
offs = lseek(fd, head_offset, SEEK_CUR);
|
||||
//printf("Seeking to %d\n", offs);
|
||||
if (head_offset == (uint32_t)-1)
|
||||
if (head_offset == -1)
|
||||
break;
|
||||
continue;
|
||||
}
|
||||
|
||||
1
lib/db.h
1
lib/db.h
@ -49,6 +49,7 @@ class db
|
||||
const char *name);
|
||||
bool verify_magic(void);
|
||||
void convert_header(db_header_t *h);
|
||||
void fileIOerr(QString s);
|
||||
|
||||
public:
|
||||
off_t head_offset;
|
||||
|
||||
@ -93,9 +93,7 @@ void db_base::remFromCont(QModelIndex &idx)
|
||||
if (!idx.isValid())
|
||||
return;
|
||||
pki_base *pki = static_cast<pki_base*>(idx.internalPointer());
|
||||
printf("PKI=%p\n", pki);
|
||||
pki_base *parent_pki = pki->getParent();
|
||||
printf("PKI=%p, parent=%p\n", pki,parent_pki);
|
||||
int row = pki->row();
|
||||
|
||||
beginRemoveRows(parent(idx), row, row);
|
||||
@ -106,7 +104,7 @@ void db_base::remFromCont(QModelIndex &idx)
|
||||
void db_base::loadContainer()
|
||||
{
|
||||
db mydb(dbName);
|
||||
unsigned char *p;
|
||||
unsigned char *p = NULL;
|
||||
db_header_t head;
|
||||
|
||||
pki_base *pb, *pki;
|
||||
@ -116,14 +114,14 @@ void db_base::loadContainer()
|
||||
p = mydb.load(&head);
|
||||
if (!p) {
|
||||
printf("Load was empty !\n");
|
||||
break;
|
||||
goto next;
|
||||
}
|
||||
//printf("load item: %s\n",head.name);
|
||||
if (pb->getVersion() < head.version) {
|
||||
free(p);
|
||||
printf("Item[%s]: Version %d > known version: %d -> ignored\n",
|
||||
head.name, head.version, pb->getVersion() );
|
||||
continue;
|
||||
goto next;
|
||||
}
|
||||
pki = newPKI();
|
||||
s = head.name;
|
||||
@ -133,12 +131,14 @@ void db_base::loadContainer()
|
||||
pki->fromData(p, &head);
|
||||
}
|
||||
catch (errorEx &err) {
|
||||
err.appendString(s);
|
||||
mainwin->Error(err);
|
||||
delete pki;
|
||||
pki = NULL;
|
||||
}
|
||||
if (pki)
|
||||
inToCont(pki);
|
||||
next:
|
||||
if (mydb.next())
|
||||
break;
|
||||
}
|
||||
|
||||
@ -59,15 +59,32 @@ class errorEx
|
||||
private:
|
||||
QString msg;
|
||||
public:
|
||||
errorEx(QString txt, QString className = "") {
|
||||
errorEx(QString txt, QString className = "")
|
||||
{
|
||||
msg = txt;
|
||||
if (!className.isEmpty())
|
||||
msg += " (" + className + ")";
|
||||
}
|
||||
errorEx(const errorEx &e) { msg = e.msg; }
|
||||
QString getString() const {return msg;}
|
||||
const char *getCString() const {return msg.toAscii();}
|
||||
bool isEmpty() const { return msg.isEmpty();}
|
||||
errorEx(const errorEx &e)
|
||||
{
|
||||
msg = e.msg;
|
||||
}
|
||||
void appendString(QString s)
|
||||
{
|
||||
msg = msg + " " + s;
|
||||
}
|
||||
QString getString() const
|
||||
{
|
||||
return msg;
|
||||
}
|
||||
const char *getCString() const
|
||||
{
|
||||
return msg.toAscii();
|
||||
}
|
||||
bool isEmpty() const
|
||||
{
|
||||
return msg.isEmpty();
|
||||
}
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@ -9,7 +9,7 @@
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>506</width>
|
||||
<height>289</height>
|
||||
<height>362</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle" >
|
||||
@ -17,7 +17,7 @@
|
||||
</property>
|
||||
<layout class="QHBoxLayout" >
|
||||
<property name="margin" >
|
||||
<number>8</number>
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="spacing" >
|
||||
<number>6</number>
|
||||
@ -35,7 +35,7 @@
|
||||
</property>
|
||||
<layout class="QVBoxLayout" >
|
||||
<property name="margin" >
|
||||
<number>8</number>
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="spacing" >
|
||||
<number>6</number>
|
||||
@ -68,6 +68,13 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="butDetails" >
|
||||
<property name="text" >
|
||||
<string>Details</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<spacer>
|
||||
<property name="orientation" >
|
||||
@ -79,7 +86,7 @@
|
||||
<property name="sizeHint" >
|
||||
<size>
|
||||
<width>204</width>
|
||||
<height>16</height>
|
||||
<height>21</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
|
||||
@ -48,32 +48,27 @@
|
||||
|
||||
|
||||
#include "MainWindow.h"
|
||||
#include "lib/exception.h"
|
||||
#include <Qt/qdir.h>
|
||||
#include <Qt/qstatusbar.h>
|
||||
|
||||
void MainWindow::init_database()
|
||||
{
|
||||
initPass();
|
||||
fprintf(stderr, "Opening database: %s\n", CCHAR(dbfile));
|
||||
keys = new db_key(dbfile, this);
|
||||
reqs = new db_x509req(dbfile, this);
|
||||
certs = new db_x509(dbfile, this);
|
||||
temps = new db_temp(dbfile, this);
|
||||
crls = new db_crl(dbfile, this);
|
||||
#if 0
|
||||
certs = new db_x509(dbenv, dbfile, keys, global_tid, certList);
|
||||
temps = new db_temp(dbenv, dbfile, global_tid, tempList);
|
||||
crls = new db_crl(dbenv, dbfile, global_tid, crlList);
|
||||
reqs->setKeyDb(keys);
|
||||
certs->setKeyDb(keys);
|
||||
keys = NULL; reqs = NULL; certs = NULL; temps = NULL; crls = NULL;
|
||||
try {
|
||||
initPass();
|
||||
keys = new db_key(dbfile, this);
|
||||
reqs = new db_x509req(dbfile, this);
|
||||
certs = new db_x509(dbfile, this);
|
||||
temps = new db_temp(dbfile, this);
|
||||
crls = new db_crl(dbfile, this);
|
||||
}
|
||||
catch (errorEx &err) {
|
||||
Error(err);
|
||||
return;
|
||||
}
|
||||
|
||||
keyList->setDB(keys);
|
||||
reqList->setDB(reqs);
|
||||
certList->setDB(certs);
|
||||
tempList->setDB(temps);
|
||||
crlList->setDB(crls);
|
||||
|
||||
#endif
|
||||
connect( keys, SIGNAL(newKey(pki_key *)),
|
||||
certs, SLOT(newKey(pki_key *)) );
|
||||
connect( keys, SIGNAL(delKey(pki_key *)),
|
||||
@ -139,21 +134,34 @@ void MainWindow::close_database()
|
||||
tempView->setModel(NULL);
|
||||
crlView->setModel(NULL);
|
||||
|
||||
delete(crls);
|
||||
delete(reqs);
|
||||
delete(certs);
|
||||
delete(temps);
|
||||
delete(keys);
|
||||
if (crls)
|
||||
delete(crls);
|
||||
if (reqs)
|
||||
delete(reqs);
|
||||
if (certs)
|
||||
delete(certs);
|
||||
if (temps)
|
||||
delete(temps);
|
||||
if (keys)
|
||||
delete(keys);
|
||||
|
||||
crls = NULL;
|
||||
reqs = NULL;
|
||||
certs = NULL;
|
||||
temps = NULL;
|
||||
keys = NULL;
|
||||
settings = NULL;
|
||||
|
||||
db mydb(dbfile);
|
||||
mydb.shrink( DBFLAG_OUTDATED | DBFLAG_DELETED );
|
||||
if (!crls)
|
||||
return;
|
||||
crls = NULL;
|
||||
|
||||
try {
|
||||
db mydb(dbfile);
|
||||
mydb.shrink( DBFLAG_OUTDATED | DBFLAG_DELETED );
|
||||
}
|
||||
catch (errorEx &err) {
|
||||
MainWindow::Error(err);
|
||||
}
|
||||
}
|
||||
|
||||
/* Asymetric Key buttons */
|
||||
@ -182,12 +190,14 @@ void MainWindow::on_BNexportKey_clicked(void)
|
||||
if(keys)
|
||||
keys->storeSelectedItems(keyView);
|
||||
}
|
||||
#if 0
|
||||
void MainWindow::on_keyView_doubleClicked(QModelIndex &m)
|
||||
{
|
||||
printf("Key View double clicked\n");
|
||||
if (keys)
|
||||
keys->showItem();
|
||||
}
|
||||
#endif
|
||||
void MainWindow::on_BNimportPFX_clicked(void)
|
||||
{
|
||||
if(certs)
|
||||
|
||||
@ -85,23 +85,24 @@ void MainWindow::load_database()
|
||||
dlg->setWindowTitle(l.caption);
|
||||
dlg->setFilters(l.filter);
|
||||
dlg->setFileMode( QFileDialog::AnyFile );
|
||||
dlg->setDirectory(getPath());
|
||||
dlg->setDirectory(baseDir);
|
||||
if (dlg->exec()) {
|
||||
fname = dlg->selectedFiles()[0];
|
||||
setPath(dlg->directory().path());
|
||||
}
|
||||
delete dlg;
|
||||
if (fname.isEmpty())
|
||||
return;
|
||||
dbfile = fname;
|
||||
printf("Before close\n");
|
||||
close_database();
|
||||
fprintf(stderr, "Dir: %s, File: %s\n", CCHAR(baseDir), CCHAR(dbfile));
|
||||
printf("Before init\n");
|
||||
init_database();
|
||||
}
|
||||
|
||||
void MainWindow::load_def_database()
|
||||
{
|
||||
dbfile = DBFILE;
|
||||
dbfile = baseDir + QDir::separator() + DBFILE;
|
||||
close_database();
|
||||
init_database();
|
||||
}
|
||||
|
||||
@ -92,10 +92,10 @@ MainWindow::MainWindow(QWidget *parent )
|
||||
statusBar()->clearMessage();
|
||||
|
||||
setWindowTitle(tr(XCA_TITLE));
|
||||
dbfile = DBFILE;
|
||||
force_load = 0;
|
||||
|
||||
baseDir = getBaseDir();
|
||||
dbfile = baseDir + QDir::separator() + DBFILE;
|
||||
|
||||
setupUi(this);
|
||||
|
||||
@ -118,14 +118,18 @@ MainWindow::MainWindow(QWidget *parent )
|
||||
|
||||
init_baseDir();
|
||||
|
||||
dbfile = baseDir + QDir::separator() + dbfile;
|
||||
char *p;
|
||||
db mydb(dbfile);
|
||||
if (!mydb.find(setting, "workingdir")) {
|
||||
if ((p = (char *)mydb.load(NULL))) {
|
||||
workingdir = p;
|
||||
free(p);
|
||||
try {
|
||||
db mydb(dbfile);
|
||||
char *p;
|
||||
if (!mydb.find(setting, "workingdir")) {
|
||||
if ((p = (char *)mydb.load(NULL))) {
|
||||
workingdir = p;
|
||||
free(p);
|
||||
}
|
||||
}
|
||||
} catch (errorEx &err) {
|
||||
Error(err);
|
||||
return;
|
||||
}
|
||||
init_database();
|
||||
}
|
||||
@ -156,7 +160,8 @@ NIDlist *MainWindow::read_nidlist(QString name)
|
||||
void MainWindow::init_baseDir()
|
||||
{
|
||||
static bool done = false;
|
||||
if (done) return;
|
||||
if (done)
|
||||
return;
|
||||
fprintf(stderr, "base Dir: %s\n", CCHAR(baseDir));
|
||||
QDir d(baseDir);
|
||||
if ( ! d.exists() && !d.mkdir(baseDir)) {
|
||||
|
||||
@ -123,7 +123,7 @@ class MainWindow: public QMainWindow, private Ui::MainWindow
|
||||
void help();
|
||||
|
||||
private slots:
|
||||
void on_keyView_doubleClicked(QModelIndex &m);
|
||||
//void on_keyView_doubleClicked(QModelIndex &m);
|
||||
|
||||
void on_BNnewKey_clicked(void);
|
||||
void on_BNdeleteKey_clicked(void);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user