summaryrefslogtreecommitdiff
path: root/ncurses/tinfo/hashed_db.c
diff options
context:
space:
mode:
Diffstat (limited to 'ncurses/tinfo/hashed_db.c')
-rw-r--r--ncurses/tinfo/hashed_db.c163
1 files changed, 120 insertions, 43 deletions
diff --git a/ncurses/tinfo/hashed_db.c b/ncurses/tinfo/hashed_db.c
index bf7a968..b594205 100644
--- a/ncurses/tinfo/hashed_db.c
+++ b/ncurses/tinfo/hashed_db.c
@@ -1,5 +1,5 @@
/****************************************************************************
- * Copyright (c) 2006,2008 Free Software Foundation, Inc. *
+ * Copyright (c) 2006-2011,2013 Free Software Foundation, Inc. *
* *
* Permission is hereby granted, free of charge, to any person obtaining a *
* copy of this software and associated documentation files (the *
@@ -36,12 +36,81 @@
#if USE_HASHED_DB
-MODULE_ID("$Id: hashed_db.c,v 1.14 2008/12/13 20:59:02 tom Exp $")
+MODULE_ID("$Id: hashed_db.c,v 1.17 2013/12/15 00:33:01 tom Exp $")
#if HASHED_DB_API >= 2
static DBC *cursor;
#endif
+typedef struct _myconn {
+ struct _myconn *next;
+ DB *db;
+ char *path;
+ bool modify;
+} MYCONN;
+
+static MYCONN *connections;
+
+static void
+cleanup(void)
+{
+ while (connections != 0) {
+ _nc_db_close(connections->db);
+ }
+}
+
+static DB *
+find_connection(const char *path, bool modify)
+{
+ DB *result = 0;
+ MYCONN *p;
+
+ for (p = connections; p != 0; p = p->next) {
+ if (!strcmp(p->path, path) && p->modify == modify) {
+ result = p->db;
+ break;
+ }
+ }
+
+ return result;
+}
+
+static void
+drop_connection(DB * db)
+{
+ MYCONN *p, *q;
+
+ for (p = connections, q = 0; p != 0; q = p, p = p->next) {
+ if (p->db == db) {
+ if (q != 0)
+ q->next = p->next;
+ else
+ connections = p->next;
+ free(p->path);
+ free(p);
+ break;
+ }
+ }
+}
+
+static void
+make_connection(DB * db, const char *path, bool modify)
+{
+ MYCONN *p = typeCalloc(MYCONN, 1);
+
+ if (p != 0) {
+ p->db = db;
+ p->path = strdup(path);
+ p->modify = modify;
+ if (p->path != 0) {
+ p->next = connections;
+ connections = p;
+ } else {
+ free(p);
+ }
+ }
+}
+
/*
* Open the database.
*/
@@ -51,50 +120,57 @@ _nc_db_open(const char *path, bool modify)
DB *result = 0;
int code;
+ if (connections == 0)
+ atexit(cleanup);
+
+ if ((result = find_connection(path, modify)) == 0) {
+
#if HASHED_DB_API >= 4
- db_create(&result, NULL, 0);
- if ((code = result->open(result,
- NULL,
- path,
- NULL,
- DB_HASH,
- modify ? DB_CREATE : DB_RDONLY,
- 0644)) != 0) {
- result = 0;
- }
+ db_create(&result, NULL, 0);
+ if ((code = result->open(result,
+ NULL,
+ path,
+ NULL,
+ DB_HASH,
+ modify ? DB_CREATE : DB_RDONLY,
+ 0644)) != 0) {
+ result = 0;
+ }
#elif HASHED_DB_API >= 3
- db_create(&result, NULL, 0);
- if ((code = result->open(result,
- path,
- NULL,
- DB_HASH,
- modify ? DB_CREATE : DB_RDONLY,
- 0644)) != 0) {
- result = 0;
- }
+ db_create(&result, NULL, 0);
+ if ((code = result->open(result,
+ path,
+ NULL,
+ DB_HASH,
+ modify ? DB_CREATE : DB_RDONLY,
+ 0644)) != 0) {
+ result = 0;
+ }
#elif HASHED_DB_API >= 2
- if ((code = db_open(path,
- DB_HASH,
- modify ? DB_CREATE : DB_RDONLY,
- 0644,
- (DB_ENV *) 0,
- (DB_INFO *) 0,
- &result)) != 0) {
- result = 0;
- }
+ if ((code = db_open(path,
+ DB_HASH,
+ modify ? DB_CREATE : DB_RDONLY,
+ 0644,
+ (DB_ENV *) 0,
+ (DB_INFO *) 0,
+ &result)) != 0) {
+ result = 0;
+ }
#else
- if ((result = dbopen(path,
- modify ? (O_CREAT | O_RDWR) : O_RDONLY,
- 0644,
- DB_HASH,
- NULL)) == 0) {
- code = errno;
- }
+ if ((result = dbopen(path,
+ modify ? (O_CREAT | O_RDWR) : O_RDONLY,
+ 0644,
+ DB_HASH,
+ NULL)) == 0) {
+ code = errno;
+ }
#endif
- if (result != 0) {
- T(("opened %s", path));
- } else {
- T(("cannot open %s: %s", path, strerror(code)));
+ if (result != 0) {
+ make_connection(result, path, modify);
+ T(("opened %s", path));
+ } else {
+ T(("cannot open %s: %s", path, strerror(code)));
+ }
}
return result;
}
@@ -107,6 +183,7 @@ _nc_db_close(DB * db)
{
int result;
+ drop_connection(db);
#if HASHED_DB_API >= 2
result = db->close(db, 0);
#else
@@ -209,7 +286,7 @@ NCURSES_EXPORT(bool)
_nc_db_have_index(DBT * key, DBT * data, char **buffer, int *size)
{
bool result = FALSE;
- int used = data->size - 1;
+ int used = (int) data->size - 1;
char *have = (char *) data->data;
(void) key;
@@ -232,7 +309,7 @@ NCURSES_EXPORT(bool)
_nc_db_have_data(DBT * key, DBT * data, char **buffer, int *size)
{
bool result = FALSE;
- int used = data->size - 1;
+ int used = (int) data->size - 1;
char *have = (char *) data->data;
if (*have++ == 0) {