@@ -47,6 +47,26 @@ state(File&& df_, File&& kf_, File&& lf_,
47
47
" File requirements not met" );
48
48
}
49
49
50
+ template <class Hasher , class File >
51
+ basic_store<Hasher, File>::state::
52
+ state (File&& df_, File&& kf_,
53
+ path_type const & dp_, path_type const & kp_,
54
+ detail::key_file_header const & kh_)
55
+ : df(std::move(df_))
56
+ , kf(std::move(kf_))
57
+ , dp(dp_)
58
+ , kp(kp_)
59
+ , hasher(kh_.salt)
60
+ , p0(kh_.key_size, " p0" )
61
+ , p1(kh_.key_size, " p1" )
62
+ , c1(kh_.key_size, kh_.block_size, " c1" )
63
+ , kh(kh_)
64
+ {
65
+ static_assert (is_File<File>::value,
66
+ " File requirements not met" );
67
+ }
68
+
69
+
50
70
// ------------------------------------------------------------------------------
51
71
52
72
template <class Hasher , class File >
@@ -214,6 +234,92 @@ open(
214
234
ec, args...);
215
235
}
216
236
237
+ template <class Hasher , class File >
238
+ template <class ... Args>
239
+ void
240
+ basic_store<Hasher, File>::
241
+ open_read_only (
242
+ path_type const & dat_path,
243
+ path_type const & key_path,
244
+ error_code& ec,
245
+ Args&&... args)
246
+ {
247
+ static_assert (is_Hasher<Hasher>::value,
248
+ " Hasher requirements not met" );
249
+ using namespace detail ;
250
+ BOOST_ASSERT (! is_open ());
251
+ ec_ = {};
252
+ ecb_.store (false );
253
+
254
+ File df (args...);
255
+ File kf (args...);
256
+ df.open (file_mode::read, dat_path, ec);
257
+ if (ec)
258
+ return ;
259
+ kf.open (file_mode::read, key_path, ec);
260
+ if (ec)
261
+ return ;
262
+
263
+ dat_file_header dh;
264
+ read (df, dh, ec);
265
+ if (ec)
266
+ return ;
267
+ verify (dh, ec);
268
+ if (ec)
269
+ return ;
270
+
271
+ key_file_header kh;
272
+ read (kf, kh, ec);
273
+ if (ec)
274
+ return ;
275
+ verify<Hasher>(kh, ec);
276
+ if (ec)
277
+ return ;
278
+
279
+ verify<Hasher>(dh, kh, ec);
280
+ if (ec)
281
+ return ;
282
+
283
+ boost::optional<state> s;
284
+ s.emplace (std::move (df), std::move (kf),
285
+ dat_path, key_path, kh);
286
+ thresh_ = std::max<std::size_t >(65536UL ,
287
+ kh.load_factor * kh.capacity );
288
+ frac_ = thresh_ / 2 ;
289
+ buckets_ = kh.buckets ;
290
+ modulus_ = ceil_pow2 (kh.buckets );
291
+ // VFALCO TODO This could be better
292
+ if (buckets_ < 1 )
293
+ {
294
+ ec = error::short_key_file;
295
+ return ;
296
+ }
297
+ s_.emplace (std::move (*s));
298
+ open_ = true ;
299
+ read_only_ = true ;
300
+ ctx_->insert (*this );
301
+ }
302
+
303
+ template <class Hasher , class File >
304
+ template <class ... Args>
305
+ void
306
+ basic_store<Hasher, File>::
307
+ open_read_only (
308
+ path_type const & dir_path,
309
+ error_code& ec,
310
+ Args&&... args){
311
+ BOOST_ASSERT (boost::filesystem::exists (dir_path));
312
+
313
+ boost::filesystem::path fs_dir_path (dir_path);
314
+
315
+ boost::filesystem::path dat_path =
316
+ fs_dir_path / detail::default_dat_file ();
317
+ boost::filesystem::path key_path =
318
+ fs_dir_path / detail::default_key_file ();
319
+
320
+ open_read_only (dat_path.string (), key_path.string (), ec, args...);
321
+ }
322
+
217
323
template <class Hasher , class File >
218
324
void
219
325
basic_store<Hasher, File>::
@@ -223,6 +329,10 @@ close(error_code& ec)
223
329
{
224
330
open_ = false ;
225
331
ctx_->erase (*this );
332
+
333
+ if (read_only_)
334
+ return ;
335
+
226
336
if (! s_->p1 .empty ())
227
337
{
228
338
std::size_t work;
@@ -302,6 +412,7 @@ insert(
302
412
using namespace detail ;
303
413
using namespace std ::chrono;
304
414
BOOST_ASSERT (is_open ());
415
+ BOOST_ASSERT (!is_read_only ());
305
416
if (ecb_)
306
417
{
307
418
ec = ec_;
@@ -776,6 +887,9 @@ flush()
776
887
using namespace std ::chrono;
777
888
using namespace detail ;
778
889
890
+ if (is_read_only ())
891
+ return ;
892
+
779
893
#if NUDB_DEBUG_LOG
780
894
beast::unit_test::dstream dout{std::cout};
781
895
#endif
0 commit comments