00001
00002
00003
00004
00005
00006
00007
00008
00018
00019 #ifndef __Bank_AMOS_HH
00020 #define __Bank_AMOS_HH 1
00021
00022 #include "utility_AMOS.hh"
00023 #include "IDMap_AMOS.hh"
00024 #include <cstdlib>
00025 #include <string>
00026 #include <fstream>
00027 #include <vector>
00028 #include <deque>
00029
00030
00031
00032 namespace AMOS {
00033
00034 typedef uint8_t BankMode_t;
00035 const BankMode_t B_READ = 0x1;
00036 const BankMode_t B_WRITE = 0x2;
00037 const BankMode_t B_SPY = 0x4;
00039
00040
00041
00042
00055
00056 class IBankable_t
00057 {
00058 friend class Bank_t;
00059 friend class BankStream_t;
00060
00061
00062 protected:
00063
00064 ID_t iid_m;
00065
00066 std::string eid_m;
00067
00068 BankFlags_t flags_m;
00069
00070
00071
00088 virtual void readRecord (std::istream & fix, std::istream & var) = 0;
00089
00090
00091
00106 virtual void readRecordFix(std::istream & fix) = 0;
00107
00108
00109
00124 virtual void writeRecord (std::ostream & fix, std::ostream & var) const = 0;
00125
00126
00127 public:
00128
00129
00134 IBankable_t ( )
00135 {
00136 iid_m = NULL_ID;
00137 }
00138
00139
00140
00143 IBankable_t (const IBankable_t & source)
00144 {
00145 *this = source;
00146 }
00147
00148
00149
00152 virtual ~IBankable_t ( )
00153 {
00154
00155 }
00156
00157
00158
00161 virtual void clear ( )
00162 {
00163 iid_m = NULL_ID;
00164 eid_m . erase( );
00165 flags_m . clear( );
00166 }
00167
00168
00169
00174 const std::string & getEID ( ) const
00175 {
00176 return eid_m;
00177 }
00178
00179
00180
00185 ID_t getIID ( ) const
00186 {
00187 return iid_m;
00188 }
00189
00190
00191
00196 virtual NCode_t getNCode ( ) const = 0;
00197
00198
00199
00206 bool isRemoved ( ) const
00207 {
00208 return flags_m . is_removed;
00209 }
00210
00211
00212
00217 bool isModified ( ) const
00218 {
00219 return flags_m . is_modified;
00220 }
00221
00222
00223
00228 bool isFlagA ( ) const
00229 {
00230 return flags_m . is_flagA;
00231 }
00232
00233
00234
00239 bool isFlagB ( ) const
00240 {
00241 return flags_m . is_flagB;
00242 }
00243
00244
00245
00252 void setEID (const std::string & eid)
00253 {
00254 std::string::size_type s = eid . find (NL_CHAR);
00255 if (s == std::string::npos )
00256 eid_m = eid;
00257 else
00258 eid_m . assign (eid, 0, s);
00259 }
00260
00261
00262
00272 void setFlagA (bool flag)
00273 {
00274 flags_m . is_flagA = flag;
00275 }
00276
00277
00278
00288 void setFlagB (bool flag)
00289 {
00290 flags_m . is_flagB = flag;
00291 }
00292
00293
00294
00300 void setIID (ID_t iid)
00301 {
00302 iid_m = iid;
00303 }
00304
00305 };
00306
00307
00308
00309
00310
00332
00333 class Bank_t
00334 {
00335
00336 protected:
00337
00338 static const Size_t DEFAULT_BUFFER_SIZE;
00339 static const Size_t DEFAULT_PARTITION_SIZE;
00340 static const Size_t MAX_OPEN_PARTITIONS;
00341
00342 enum IFOMode_t
00343 {
00344 I_OPEN,
00345 I_CREATE,
00346 I_CLOSE
00347 };
00348
00349
00350
00356
00357 class BankPartition_t
00358 {
00359
00360 private:
00361
00362 char * fix_buff;
00363 char * var_buff;
00364
00365
00366 public:
00367
00368 std::string fix_name;
00369 std::string var_name;
00370 std::fstream fix;
00371 std::fstream var;
00372
00373
00376 BankPartition_t (Size_t buffer_size);
00377
00378
00379
00382 ~BankPartition_t ( );
00383
00384 };
00385
00386
00387
00401 void addPartition (bool create);
00402
00403
00404
00407 void appendBID (IBankable_t & obj);
00408
00409
00410
00413 void fetchBID (ID_t bid, IBankable_t & obj);
00414
00415
00416
00419 void fetchBIDFix(ID_t iid, IBankable_t & obj);
00420
00421
00422
00436 BankPartition_t * getPartition (ID_t id)
00437 {
00438 if ( partitions_m [id] -> fix . is_open( ) )
00439 {
00440 partitions_m [id]->fix.clear();
00441 partitions_m [id]->var.clear();
00442 return partitions_m [id];
00443 }
00444 else
00445 return openPartition (id);
00446 }
00447
00448
00449
00452 BankPartition_t * getLastPartition ( )
00453 {
00454 return getPartition (npartitions_m - 1);
00455 }
00456
00457
00458
00461 void init ( );
00462
00463
00464
00472 BankPartition_t * localizeBID (ID_t & bid)
00473 {
00474 ID_t pid = (-- bid) / partition_size_m;
00475 bid -= pid * partition_size_m;
00476 return getPartition (pid);
00477 }
00478
00479
00480
00492 void lockIFO ( );
00493
00494
00495
00498 BankPartition_t * openPartition (ID_t id);
00499
00500
00501
00504 void removeBID (ID_t bid);
00505
00506
00507
00510 void replaceBID (ID_t bid, IBankable_t & obj);
00511
00512
00513
00521 void setMode (BankMode_t mode)
00522 {
00523 if ( mode & ~(B_READ | B_WRITE | B_SPY) )
00524 AMOS_THROW_ARGUMENT ("Invalid BankMode: unknown mode");
00525
00526 if ( ! mode & (B_READ | B_WRITE | B_SPY) )
00527 AMOS_THROW_ARGUMENT ("Invalid BankMode: mode not specified");
00528
00529 if ( mode & B_SPY )
00530 mode = B_SPY | B_READ;
00531
00532 mode_m = mode;
00533 }
00534
00535
00536
00551 void syncIFO (IFOMode_t mode);
00552
00553
00554
00557 void touchFile (const std::string & path, int mode, bool create);
00558
00559
00560
00572 void unlockIFO ( );
00573
00574
00575
00580 Bank_t (const Bank_t & source);
00581
00582
00583
00588 Bank_t & operator= (const Bank_t & source);
00589
00590
00591 NCode_t banktype_m;
00592
00593 Size_t buffer_size_m;
00594 Size_t max_partitions_m;
00595
00596 bool is_open_m;
00597 signed char status_m;
00598 BankMode_t mode_m;
00599
00600 std::string store_dir_m;
00601 std::string store_pfx_m;
00602 Size_t fix_size_m;
00603 Size_t partition_size_m;
00604
00605 ID_t last_bid_m;
00606 ID_t max_bid_m;
00607 ID_t nbids_m;
00608 Size_t npartitions_m;
00609 std::deque <BankPartition_t *> opened_m;
00610 std::vector<BankPartition_t *> partitions_m;
00611
00612 IDMap_t idmap_m;
00613
00614
00615 public:
00616
00617 typedef int64_t bankstreamoff;
00618
00619 static const std::string BANK_VERSION;
00620
00621 static const std::string IFO_STORE_SUFFIX;
00622 static const std::string MAP_STORE_SUFFIX;
00623 static const std::string LCK_STORE_SUFFIX;
00624
00625 static const std::string FIX_STORE_SUFFIX;
00626 static const std::string VAR_STORE_SUFFIX;
00627
00628 static const std::string TMP_STORE_SUFFIX;
00629
00630 static const char WRITE_LOCK_CHAR;
00631 static const char READ_LOCK_CHAR;
00632
00633
00634
00649 Bank_t (NCode_t type)
00650 : banktype_m (type)
00651 {
00652 init( );
00653 status_m = 0;
00654 buffer_size_m = DEFAULT_BUFFER_SIZE;
00655 max_partitions_m = MAX_OPEN_PARTITIONS;
00656 }
00657
00658
00659
00660 Bank_t (const std::string & type)
00661 : banktype_m (Encode(type))
00662 {
00663 init( );
00664 status_m = 0;
00665 buffer_size_m = DEFAULT_BUFFER_SIZE;
00666 max_partitions_m = MAX_OPEN_PARTITIONS;
00667 }
00668
00669
00670
00675 ~Bank_t ( )
00676 {
00677 if ( is_open_m )
00678 close( );
00679 }
00680
00681
00682
00702 void append (IBankable_t & obj);
00703
00704
00705
00721 void assignEID (ID_t iid, const std::string & eid);
00722
00723
00724
00740 void assignIID (const std::string & eid, ID_t iid);
00741
00742
00743
00754 void clean ( );
00755
00756
00757
00769 void clear ( );
00770
00771
00772
00781 void close ( );
00782
00783
00784
00805 void concat (Bank_t & source);
00806
00807
00808
00825 void create (const std::string & dir, BankMode_t mode = B_READ | B_WRITE);
00826
00827
00828
00839 void destroy ( );
00840
00841
00842
00845 bool empty ( ) const
00846 {
00847 return ( getSize( ) == 0 );
00848 }
00849
00850
00851
00861 bool exists (const std::string & dir) const;
00862
00863
00864
00867 bool existsEID (const std::string & eid) const
00868 {
00869 return (idmap_m . exists (eid));
00870 }
00871
00872
00873
00876 bool existsIID (ID_t iid) const
00877 {
00878 return (idmap_m . exists (iid));
00879 }
00880
00881
00882
00898 void fetch (ID_t iid, IBankable_t & obj)
00899 {
00900 fetchBID (lookupBID (iid), obj);
00901 obj . iid_m = iid;
00902 obj . eid_m . assign (idmap_m . lookupEID (iid));
00903 }
00904
00905
00906
00909 void fetch (const std::string & eid, IBankable_t & obj)
00910 {
00911 fetchBID (lookupBID (eid), obj);
00912 obj . iid_m = idmap_m . lookupIID (eid);
00913 obj . eid_m . assign (eid);
00914 }
00915
00916
00917
00920 void fetchFix(ID_t iid, IBankable_t & obj)
00921 {
00922 fetchBIDFix (lookupBID (iid), obj);
00923 obj . iid_m = iid;
00924 obj . eid_m . assign (idmap_m . lookupEID (iid));
00925 }
00926
00927
00928
00931 void fetchFix(const std::string & eid, IBankable_t & obj)
00932 {
00933 fetchBIDFix (lookupBID (eid), obj);
00934 obj . iid_m = idmap_m . lookupIID (eid);
00935 obj . eid_m . assign (eid);
00936 }
00937
00938
00939
00949 const IDMap_t & getIDMap ( ) const
00950 {
00951 return idmap_m;
00952 }
00953
00954
00955
00964 Size_t getIDMapSize ( ) const
00965 {
00966 return idmap_m . getSize( );
00967 }
00968
00969
00970
00986 Size_t getIndexSize ( ) const
00987 {
00988 return last_bid_m;
00989 }
00990
00991
00992
00999 ID_t getMaxIID ( ) const;
01000
01001
01008 ID_t getMaxBID ( ) const;
01009
01010
01011
01012
01013
01021 Size_t getSize ( ) const
01022 {
01023 return nbids_m;
01024 }
01025
01026
01027
01036 signed char getStatus ( ) const
01037 {
01038 return status_m;
01039 }
01040
01041
01042
01049 NCode_t getType ( ) const
01050 {
01051 return banktype_m;
01052 }
01053
01054
01055
01060 bool isOpen ( ) const
01061 {
01062 return is_open_m;
01063 }
01064
01065
01066
01072 ID_t lookupBID (ID_t iid) const;
01073
01074
01075
01081 ID_t lookupBID (const std::string & eid) const;
01082
01083
01084
01089 const std::string & lookupEID (ID_t iid) const
01090 {
01091 return idmap_m . lookupEID (iid);
01092 }
01093
01094
01095
01100 ID_t lookupIID (const std::string & eid) const
01101 {
01102 return idmap_m . lookupIID (eid);
01103 }
01104
01105
01106
01125 void open (const std::string & dir, BankMode_t mode = B_READ | B_WRITE);
01126
01127
01128
01145 void remove (ID_t iid)
01146 {
01147 removeBID (lookupBID (iid));
01148 idmap_m . remove (iid);
01149 }
01150
01151
01152
01155 void remove (const std::string & eid)
01156 {
01157 removeBID (lookupBID (eid));
01158 idmap_m . remove (eid);
01159 }
01160
01161
01162
01185 void replace (ID_t iid, IBankable_t & obj);
01186
01187
01188
01191 void replace (const std::string & eid, IBankable_t & obj);
01192
01193
01194
01202 void setStatus (signed char status)
01203 {
01204 status_m = status;
01205 }
01206
01207 };
01208
01209
01210
01220 bool BankExists (NCode_t ncode, const std::string & dir);
01221
01222
01223
01229 void PrintBankVersion (const char * s);
01230
01231 }
01232
01233 #endif // #ifndef __Bank_AMOS_HH