]>
Commit | Line | Data |
---|---|---|
95d2589c CT |
1 | #ifndef SQUID_SSL_CERTIFICATE_DB_H |
2 | #define SQUID_SSL_CERTIFICATE_DB_H | |
3 | ||
4 | #include "ssl/gadgets.h" | |
95d2589c CT |
5 | #if HAVE_STRING |
6 | #include <string> | |
7 | #endif | |
3eee6040 CT |
8 | #if HAVE_OPENSSL_OPENSSLV_H |
9 | #include <openssl/opensslv.h> | |
10 | #endif | |
95d2589c CT |
11 | |
12 | namespace Ssl | |
13 | { | |
5b3d088d | 14 | /// maintains an exclusive blocking file-based lock |
e29ccb57 A |
15 | class Lock |
16 | { | |
95d2589c | 17 | public: |
5b3d088d CT |
18 | explicit Lock(std::string const &filename); ///< creates an unlocked lock |
19 | ~Lock(); ///< releases the lock if it is locked | |
20 | void lock(); ///< locks the lock, may block | |
21 | void unlock(); ///< unlocks locked lock or throws | |
22 | bool locked() const; ///< whether our lock is locked | |
23 | const char *name() const { return filename.c_str(); } | |
95d2589c | 24 | private: |
5b3d088d | 25 | std::string filename; |
7aa9bb3e | 26 | #if _SQUID_WINDOWS_ |
95d2589c CT |
27 | HANDLE hFile; ///< Windows file handle. |
28 | #else | |
29 | int fd; ///< Linux file descriptor. | |
30 | #endif | |
31 | }; | |
32 | ||
5b3d088d CT |
33 | /// an exception-safe way to obtain and release a lock |
34 | class Locker | |
35 | { | |
36 | public: | |
37 | /// locks the lock if the lock was unlocked | |
38 | Locker(Lock &lock, const char *aFileName, int lineNo); | |
39 | /// unlocks the lock if it was locked by us | |
40 | ~Locker(); | |
41 | private: | |
42 | bool weLocked; ///< whether we locked the lock | |
43 | Lock &lock; ///< the lock we are operating on | |
44 | const std::string fileName; ///< where the lock was needed | |
e29ccb57 | 45 | const int lineNo; ///< where the lock was needed |
5b3d088d CT |
46 | }; |
47 | ||
48 | /// convenience macro to pass source code location to Locker and others | |
49 | #define Here __FILE__, __LINE__ | |
50 | ||
95d2589c CT |
51 | /** |
52 | * Database class for storing SSL certificates and their private keys. | |
53 | * A database consist by: | |
54 | * - A disk file to store current serial number | |
55 | * - A disk file to store the current database size | |
56 | * - A disk file which is a normal TXT_DB openSSL database | |
57 | * - A directory under which the certificates and their private keys stored. | |
58 | * The database before used must initialized with CertificateDb::create static method. | |
59 | */ | |
60 | class CertificateDb | |
61 | { | |
62 | public: | |
63 | /// Names of db columns. | |
64 | enum Columns { | |
65 | cnlType = 0, | |
66 | cnlExp_date, | |
67 | cnlRev_date, | |
68 | cnlSerial, | |
69 | cnlFile, | |
70 | cnlName, | |
71 | cnlNumber | |
72 | }; | |
73 | ||
74 | /// A wrapper for OpenSSL database row of TXT_DB database. | |
75 | class Row | |
76 | { | |
77 | public: | |
78 | /// Create row wrapper. | |
79 | Row(); | |
f385ac29 CT |
80 | ///Create row wrapper for row with width items |
81 | Row(char **row, size_t width); | |
95d2589c CT |
82 | /// Delete all row. |
83 | ~Row(); | |
84 | void setValue(size_t number, char const * value); ///< Set cell's value in row | |
85 | char ** getRow(); ///< Raw row | |
86 | void reset(); ///< Abandon row and don't free memory | |
87 | private: | |
88 | char **row; ///< Raw row | |
89 | size_t width; ///< Number of cells in the row | |
90 | }; | |
91 | ||
92 | CertificateDb(std::string const & db_path, size_t aMax_db_size, size_t aFs_block_size); | |
93 | /// Find certificate and private key for host name | |
94 | bool find(std::string const & host_name, Ssl::X509_Pointer & cert, Ssl::EVP_PKEY_Pointer & pkey); | |
4ece76b2 CT |
95 | /// Delete a certificate from database |
96 | bool purgeCert(std::string const & key); | |
95d2589c | 97 | /// Save certificate to disk. |
fb2178bb | 98 | bool addCertAndPrivateKey(Ssl::X509_Pointer & cert, Ssl::EVP_PKEY_Pointer & pkey, std::string const & useName); |
95d2589c | 99 | /// Create and initialize a database under the db_path |
a0b971d5 | 100 | static void create(std::string const & db_path); |
95d2589c CT |
101 | /// Check the database stored under the db_path. |
102 | static void check(std::string const & db_path, size_t max_db_size); | |
95d2589c CT |
103 | bool IsEnabledDiskStore() const; ///< Check enabled of dist store. |
104 | private: | |
105 | void load(); ///< Load db from disk. | |
106 | void save(); ///< Save db to disk. | |
107 | size_t size() const; ///< Get db size on disk in bytes. | |
108 | /// Increase db size by the given file size and update size_file | |
109 | void addSize(std::string const & filename); | |
110 | /// Decrease db size by the given file size and update size_file | |
111 | void subSize(std::string const & filename); | |
112 | size_t readSize() const; ///< Read size from file size_file | |
113 | void writeSize(size_t db_size); ///< Write size to file size_file. | |
114 | size_t getFileSize(std::string const & filename); ///< get file size on disk. | |
115 | /// Only find certificate in current db and return it. | |
116 | bool pure_find(std::string const & host_name, Ssl::X509_Pointer & cert, Ssl::EVP_PKEY_Pointer & pkey); | |
117 | ||
1bf6c6e7 | 118 | void deleteRow(const char **row, int rowIndex); ///< Delete a row from TXT_DB |
95d2589c CT |
119 | bool deleteInvalidCertificate(); ///< Delete invalid certificate. |
120 | bool deleteOldestCertificate(); ///< Delete oldest certificate. | |
121 | bool deleteByHostname(std::string const & host); ///< Delete using host name. | |
122 | ||
f385ac29 CT |
123 | /// Removes the first matching row from TXT_DB. Ignores failures. |
124 | static void sq_TXT_DB_delete(TXT_DB *db, const char **row); | |
125 | /// Remove the row on position idx from TXT_DB. Ignores failures. | |
126 | static void sq_TXT_DB_delete_row(TXT_DB *db, int idx); | |
127 | ||
95d2589c CT |
128 | /// Callback hash function for serials. Used to create TXT_DB index of serials. |
129 | static unsigned long index_serial_hash(const char **a); | |
130 | /// Callback compare function for serials. Used to create TXT_DB index of serials. | |
131 | static int index_serial_cmp(const char **a, const char **b); | |
132 | /// Callback hash function for names. Used to create TXT_DB index of names.. | |
133 | static unsigned long index_name_hash(const char **a); | |
134 | /// Callback compare function for names. Used to create TXT_DB index of names.. | |
135 | static int index_name_cmp(const char **a, const char **b); | |
136 | ||
137 | /// Definitions required by openSSL, to use the index_* functions defined above | |
138 | ///with TXT_DB_create_index. | |
3eee6040 CT |
139 | #if OPENSSL_VERSION_NUMBER > 0x10000000L |
140 | static unsigned long index_serial_LHASH_HASH(const void *a) { | |
141 | return index_serial_hash((const char **)a); | |
142 | } | |
aa818c4e | 143 | static int index_serial_LHASH_COMP(const void *arg1, const void *arg2) { |
3eee6040 CT |
144 | return index_serial_cmp((const char **)arg1, (const char **)arg2); |
145 | } | |
146 | static unsigned long index_name_LHASH_HASH(const void *a) { | |
147 | return index_name_hash((const char **)a); | |
148 | } | |
149 | static int index_name_LHASH_COMP(const void *arg1, const void *arg2) { | |
150 | return index_name_cmp((const char **)arg1, (const char **)arg2); | |
151 | } | |
152 | #else | |
95d2589c CT |
153 | static IMPLEMENT_LHASH_HASH_FN(index_serial_hash,const char **) |
154 | static IMPLEMENT_LHASH_COMP_FN(index_serial_cmp,const char **) | |
155 | static IMPLEMENT_LHASH_HASH_FN(index_name_hash,const char **) | |
156 | static IMPLEMENT_LHASH_COMP_FN(index_name_cmp,const char **) | |
3eee6040 | 157 | #endif |
95d2589c | 158 | |
95d2589c CT |
159 | static const std::string db_file; ///< Base name of the database index file. |
160 | static const std::string cert_dir; ///< Base name of the directory to store the certs. | |
161 | static const std::string size_file; ///< Base name of the file to store db size. | |
162 | /// Min size of disk db. If real size < min_db_size the db will be disabled. | |
163 | static const size_t min_db_size; | |
164 | ||
165 | const std::string db_path; ///< The database directory. | |
95d2589c CT |
166 | const std::string db_full; ///< Full path of the database index file. |
167 | const std::string cert_full; ///< Full path of the directory to store the certs. | |
168 | const std::string size_full; ///< Full path of the file to store the db size. | |
169 | ||
170 | TXT_DB_Pointer db; ///< Database with certificates info. | |
171 | const size_t max_db_size; ///< Max size of db. | |
172 | const size_t fs_block_size; ///< File system block size. | |
5b3d088d | 173 | mutable Lock dbLock; ///< protects the database file |
95d2589c CT |
174 | |
175 | bool enabled_disk_store; ///< The storage on the disk is enabled. | |
176 | }; | |
177 | ||
178 | } // namespace Ssl | |
179 | #endif // SQUID_SSL_CERTIFICATE_DB_H |