-rw-r--r-- | lib/.gitignore | 7 | ||||
-rw-r--r-- | lib/Makefile.am | 16 | ||||
-rw-r--r-- | lib/exception.cc | 66 | ||||
-rw-r--r-- | lib/pointer_map.cc | 74 | ||||
-rw-r--r-- | lib/pqxx_pile.cc | 17 |
5 files changed, 180 insertions, 0 deletions
diff --git a/lib/.gitignore b/lib/.gitignore new file mode 100644 index 0000000..7a5e754 --- a/dev/null +++ b/lib/.gitignore | |||
@@ -0,0 +1,7 @@ | |||
1 | Makefile.in | ||
2 | .libs | ||
3 | .deps | ||
4 | Makefile | ||
5 | *.lo | ||
6 | *.o | ||
7 | *.la | ||
diff --git a/lib/Makefile.am b/lib/Makefile.am new file mode 100644 index 0000000..a904569 --- a/dev/null +++ b/lib/Makefile.am | |||
@@ -0,0 +1,16 @@ | |||
1 | lib_LTLIBRARIES = libkonforka.la | ||
2 | |||
3 | INCLUDES = -I${top_srcdir}/include | ||
4 | AM_CXXFLAGS = ${PQXX_CFLAGS} | ||
5 | LDADD = ${PQXX_LIBS} | ||
6 | |||
7 | EXTRA_DIST = pqxx_pile.cc | ||
8 | EXTRA_SOURCES= | ||
9 | if HAVE_PQXX | ||
10 | EXTRA_SOURCES += pqxx_pile.cc | ||
11 | endif | ||
12 | |||
13 | libkonforka_la_SOURCES = \ | ||
14 | exception.cc \ | ||
15 | pointer_map.cc \ | ||
16 | ${EXTRA_SOURCES} | ||
diff --git a/lib/exception.cc b/lib/exception.cc new file mode 100644 index 0000000..65302bf --- a/dev/null +++ b/lib/exception.cc | |||
@@ -0,0 +1,66 @@ | |||
1 | #include <string.h> | ||
2 | #include <errno.h> | ||
3 | #include "konforka/exception.h" | ||
4 | |||
5 | namespace konforka { | ||
6 | |||
7 | /* | ||
8 | * code_point | ||
9 | */ | ||
10 | |||
11 | code_point::code_point(const string& w) | ||
12 | : where(w), line(-1) { } | ||
13 | code_point::code_point(const string& fi,const string& fu,int l) | ||
14 | : file(fi), function(fu), line(l) { | ||
15 | make_where(); | ||
16 | } | ||
17 | |||
18 | const char *code_point::c_str() const throw() { | ||
19 | return where.c_str(); | ||
20 | } | ||
21 | |||
22 | void code_point::make_where() { | ||
23 | static char tmp[8]; | ||
24 | snprintf(tmp,sizeof(tmp),"%d",line); | ||
25 | where = file + ":" + tmp + " [" + function + "]"; | ||
26 | } | ||
27 | |||
28 | /* | ||
29 | * exception | ||
30 | */ | ||
31 | |||
32 | exception::exception(const string& whe,const string& wha) | ||
33 | : _where(whe), _what(wha) { } | ||
34 | exception::exception(const string& fi,const string& fu,int l,const string& w) | ||
35 | : _where(fi,fu,l), _what(w) { } | ||
36 | exception::~exception() throw() { } | ||
37 | |||
38 | const char *exception::where() const throw() { | ||
39 | return _where.c_str(); | ||
40 | } | ||
41 | const char *exception::what() const throw() { | ||
42 | return _what.c_str(); | ||
43 | } | ||
44 | |||
45 | void exception::see(const string& w) { | ||
46 | _seen.push_back(code_point(w)); | ||
47 | } | ||
48 | void exception::see(const string& fi,const string& fu,int l) { | ||
49 | _seen.push_back(code_point(fi,fu,l)); | ||
50 | } | ||
51 | |||
52 | /* | ||
53 | * system_error | ||
54 | */ | ||
55 | |||
56 | system_error::system_error(const string& whe,const string& wha) | ||
57 | : _errno(errno), exception(whe,wha) { } | ||
58 | system_error::system_error(const string& fi,const string& fu,int l,const string& w) | ||
59 | : _errno(errno), exception(fi,fu,l,w) { } | ||
60 | system_error::~system_error() throw() { } | ||
61 | |||
62 | const char *system_error::why() const throw() { | ||
63 | return strerror(errno); // TODO: strerror_r | ||
64 | } | ||
65 | |||
66 | } | ||
diff --git a/lib/pointer_map.cc b/lib/pointer_map.cc new file mode 100644 index 0000000..44f7ebc --- a/dev/null +++ b/lib/pointer_map.cc | |||
@@ -0,0 +1,74 @@ | |||
1 | #include <cassert> | ||
2 | #include <map> | ||
3 | #include <string> | ||
4 | using namespace std; | ||
5 | #include "konforka/exception.h" | ||
6 | #include "konforka/pointer_map.h" | ||
7 | |||
8 | namespace konforka { | ||
9 | |||
10 | /* | ||
11 | * to_t->from_t->from->to | ||
12 | */ | ||
13 | class mpointer_t { | ||
14 | public: | ||
15 | void *ptr; | ||
16 | int ref; | ||
17 | |||
18 | mpointer_t() : ptr(0), ref(0) { } | ||
19 | |||
20 | void _ref() { ref++; } | ||
21 | void _unref() { ref--; } | ||
22 | }; | ||
23 | typedef map<void*,mpointer_t> map_ptr_1_t; | ||
24 | typedef map<string,map_ptr_1_t> map_ptr_2_t; | ||
25 | typedef map<string,map_ptr_2_t> map_ptr_t; | ||
26 | |||
27 | static map_ptr_t pointer_map; | ||
28 | |||
29 | void _map_pointer(const type_info& tf,void *pf,const type_info& tt,void *pt) { | ||
30 | mpointer_t& mpt = pointer_map[tf.name()][tt.name()][pf]; | ||
31 | if(mpt.ref) { | ||
32 | if(mpt.ptr != pt) | ||
33 | throw exception(CODEPOINT,"trying to remap existing pointer with different value"); | ||
34 | }else{ | ||
35 | mpt.ptr = pt; | ||
36 | } | ||
37 | mpt.ref++; | ||
38 | } | ||
39 | void _unmap_pointer(const type_info& tf,void *pf,const type_info& tt,void *pt) { | ||
40 | map_ptr_t::iterator i1 = pointer_map.find(tf.name()); | ||
41 | if(i1==pointer_map.end()) | ||
42 | throw exception(CODEPOINT,"no pointer of such type has ever been mapped"); | ||
43 | map_ptr_2_t::iterator i2 = i1->second.find(tt.name()); | ||
44 | if(i2==i1->second.end()) | ||
45 | throw exception(CODEPOINT,"no pointer has ever been mapped to the object of this type"); | ||
46 | map_ptr_1_t::iterator i3 = i2->second.find(pf); | ||
47 | if(i3==i2->second.end()) | ||
48 | throw exception(CODEPOINT,"this pointer has never been mapped"); | ||
49 | assert(i3->second.ref>0); | ||
50 | if(--(i3->second.ref)) | ||
51 | return; | ||
52 | i2->second.erase(i3); | ||
53 | if(!i2->second.empty()) | ||
54 | return; | ||
55 | i1->second.erase(i2); | ||
56 | if(!i1->second.empty()) | ||
57 | return; | ||
58 | pointer_map.erase(i1); | ||
59 | } | ||
60 | void *_mapped_pointer(const type_info& tf,void *pf,const type_info& tt) { | ||
61 | map_ptr_t::iterator i1 = pointer_map.find(tf.name()); | ||
62 | if(i1==pointer_map.end()) | ||
63 | throw exception(CODEPOINT,"no pointer of such type has ever been mapped"); | ||
64 | map_ptr_2_t::iterator i2 = i1->second.find(tt.name()); | ||
65 | if(i2==i1->second.end()) | ||
66 | throw exception(CODEPOINT,"no pointer has ever been mapped to the object of this type"); | ||
67 | map_ptr_1_t::iterator i3 = i2->second.find(pf); | ||
68 | if(i3==i2->second.end()) | ||
69 | throw exception(CODEPOINT,"this pointer has never been mapped"); | ||
70 | assert(i3->second.ref>0); | ||
71 | return i3->second.ptr; | ||
72 | } | ||
73 | |||
74 | } | ||
diff --git a/lib/pqxx_pile.cc b/lib/pqxx_pile.cc new file mode 100644 index 0000000..d6623bb --- a/dev/null +++ b/lib/pqxx_pile.cc | |||
@@ -0,0 +1,17 @@ | |||
1 | #include "konforka/pqxx_pile.h" | ||
2 | |||
3 | namespace konforka { | ||
4 | |||
5 | template class resource_pile_generic_ptr_factory<string,pqxx::connection>; | ||
6 | template class resource_pile_generic_ptr_factory<string,pqxx::lazyconnection>; | ||
7 | template class resource_pile_generic_ptr_factory<string,pqxx::asyncconnection>; | ||
8 | |||
9 | template class resource_pile_base<string,pqxx::connection*,resource_pile_generic_ptr_factory<string,pqxx::connection> >; | ||
10 | template class resource_pile_base<string,pqxx::lazyconnection*,resource_pile_generic_ptr_factory<string,pqxx::lazyconnection> >; | ||
11 | template class resource_pile_base<string,pqxx::asyncconnection*,resource_pile_generic_ptr_factory<string,pqxx::asyncconnection> >; | ||
12 | |||
13 | template class pqxx_piled_connection_base<pqxx::connection>; | ||
14 | template class pqxx_piled_connection_base<pqxx::lazyconnection>; | ||
15 | template class pqxx_piled_connection_base<pqxx::asyncconnection>; | ||
16 | |||
17 | } | ||