ROOTANA
midasodb.cxx
Go to the documentation of this file.
1 /********************************************************************\
2 
3  Name: midasodb.cxx
4  Created by: K.Olchanski
5 
6  Contents: MIDAS implementation of MVOdb ODB interface
7 
8 \********************************************************************/
9 
10 #include <stdio.h>
11 #include <string.h> // strlen()
12 #include <assert.h>
13 #include <stdlib.h> // malloc()
14 
15 #include "mvodb.h"
16 #include "midas.h"
17 
18 static std::string toString(int value)
19 {
20  char buf[256];
21  sprintf(buf, "%d", value);
22  return buf;
23 }
24 
25 class MidasOdb: public MVOdb
26 {
27 public:
28  HNDLE fDB = 0;
29  std::string fRoot;
30  bool fPrintError = true;
31  bool fPrintWarning = false;
32 
33 public:
34  MidasOdb(HNDLE hDB, const char* root)
35  {
36  fDB = hDB;
37  fRoot = root;
38  }
39 
40  ~MidasOdb() // dtor
41  {
42  // poison the data members
43  fDB = 0;
44  }
45 
46  std::string Path(const char* varname)
47  {
48  std::string path;
49  path += fRoot;
50  path += "/";
51  path += varname;
52  return path;
53  }
54 
55  void SetPrintError(bool v)
56  {
57  fPrintError = v;
58  }
59 
60  bool GetPrintError() const
61  {
62  return fPrintError;
63  }
64 
65  bool IsReadOnly() const
66  {
67  return false;
68  }
69 
70  MVOdb* Chdir(const char* subdir, bool create, MVOdbError* error)
71  {
72  std::string path = Path(subdir);
73  HNDLE hkey;
74  int status = db_find_key(fDB, 0, path.c_str(), &hkey);
75  if (status == DB_SUCCESS) {
76  KEY key;
77  status = db_get_key(fDB, hkey, &key);
78  if (status != DB_SUCCESS) {
79  SetMidasStatus(error, fPrintError, path, "db_get_key", status);
80  return MakeNullOdb();
81  }
82  if (key.type != TID_KEY) {
83  SetError(error, fPrintError, path, "ODB path is not a directory");
84  if (create)
85  return MakeNullOdb();
86  else
87  return NULL;
88  }
89  return new MidasOdb(fDB, path.c_str());
90  } else if (!create) {
91  SetMidasStatus(error, fPrintWarning, path, "db_find_key", status);
92  return NULL;
93  } else {
94  status = db_create_key(fDB, 0, path.c_str(), TID_KEY);
95  if (status != DB_SUCCESS) {
96  SetMidasStatus(error, fPrintError, path, "db_create_key", status);
97  return MakeNullOdb();
98  }
99  return new MidasOdb(fDB, path.c_str());
100  }
101  }
102 
103  void RAInfo(const char* varname, int* num_elements, int* element_size, MVOdbError* error)
104  {
105  std::string path = Path(varname);
106 
107  if (num_elements)
108  *num_elements = 0;
109  if (element_size)
110  *element_size = 0;
111 
112  int status;
113  HNDLE hkey;
114  status = db_find_key(fDB, 0, path.c_str(), &hkey);
115  if (status != DB_SUCCESS)
116  return;
117 
118  KEY key;
119  status = db_get_key(fDB, hkey, &key);
120  if (status != DB_SUCCESS)
121  return;
122 
123  if (num_elements)
124  *num_elements = key.num_values;
125 
126  if (element_size)
127  *element_size = key.item_size;
128  }
129 
130  void ReadKey(const char* varname, int *tid, int *num_values, int *total_size, int *item_size, MVOdbError* error)
131  {
132  if (tid) *tid = 0;
133  if (num_values) *num_values = 0;
134  if (total_size) *total_size = 0;
135  if (item_size) *item_size = 0;
136 
137  std::string path = Path(varname);
138 
139  int status;
140  HNDLE hkey;
141 
142  status = db_find_key(fDB, 0, path.c_str(), &hkey);
143  if (status != DB_SUCCESS) {
144  SetMidasStatus(error, fPrintWarning, path, "db_find_key", status);
145  return;
146  }
147 
148  KEY key;
149  status = db_get_key(fDB, hkey, &key);
150  if (status != DB_SUCCESS) {
151  SetMidasStatus(error, fPrintError, path, "db_get_key", status);
152  return;
153  }
154 
155  if (tid)
156  *tid = key.type;
157 
158  if (num_values)
159  *num_values = key.num_values;
160 
161  if (total_size)
162  *total_size = key.total_size;
163 
164  if (item_size)
165  *item_size = key.item_size;
166 
167  SetOk(error);
168  }
169 
170  void ReadKeyLastWritten(const char* varname, int *last_written, MVOdbError* error)
171  {
172  if (last_written) *last_written = 0;
173 
174  std::string path = Path(varname);
175 
176  int status;
177  HNDLE hkey;
178 
179  status = db_find_key(fDB, 0, path.c_str(), &hkey);
180  if (status != DB_SUCCESS) {
181  SetMidasStatus(error, fPrintWarning, path, "db_find_key", status);
182  return;
183  }
184 
185  KEY key;
186  status = db_get_key(fDB, hkey, &key);
187  if (status != DB_SUCCESS) {
188  SetMidasStatus(error, fPrintError, path, "db_get_key", status);
189  return;
190  }
191 
192  if (last_written)
193  *last_written = key.last_written;
194 
195  SetOk(error);
196  }
197 
198  void ReadDir(std::vector<std::string>* varname, std::vector<int> *tid, std::vector<int> *num_values, std::vector<int> *total_size, std::vector<int> *item_size, MVOdbError* error)
199  {
200  // FIXME: incomplete!
201  SetOk(error);
202  }
203 
204  void ResizeArray(const char* varname, int new_size, MVOdbError* error)
205  {
206  std::string path = Path(varname);
207 
208  int status;
209  HNDLE hkey;
210 
211  status = db_find_key(fDB, 0, path.c_str(), &hkey);
212 
213  if (status != DB_SUCCESS) {
214  SetMidasStatus(error, fPrintWarning, path, "db_find_key", status);
215  return;
216  }
217 
218  status = db_set_num_values(fDB, hkey, new_size);
219  if (status != SUCCESS) {
220  SetMidasStatus(error, fPrintError, path, "db_set_num_values", status);
221  return;
222  }
223 
224  SetOk(error);
225  }
226 
227  void ResizeStringArray(const char* varname, int new_size, int new_string_length, MVOdbError* error)
228  {
229  std::string path = Path(varname);
230 
231  int status = db_resize_string(fDB, 0, path.c_str(), new_size, new_string_length);
232  if (status != SUCCESS) {
233  SetMidasStatus(error, fPrintError, path, "db_resize_string", status);
234  return;
235  }
236 
237  SetOk(error);
238  }
239 
240  bool R(const char* varname, int tid, void *value, int size, bool create, MVOdbError* error)
241  {
242  assert(value);
243  std::string path = Path(varname);
244  int status = db_get_value(fDB, 0, path.c_str(), value, &size, tid, create);
245  if (status != DB_SUCCESS) {
246  SetMidasStatus(error, fPrintError, path, "db_get_value", status);
247  return false;
248  }
249  SetOk(error);
250  return true;
251  }
252 
253  void RI(const char* varname, int *value, bool create, MVOdbError* error)
254  {
255  R(varname, TID_INT, value, sizeof(int), create, error);
256  }
257 
258  void RU16(const char* varname, uint16_t *value, bool create, MVOdbError* error)
259  {
260  R(varname, TID_WORD, value, sizeof(uint16_t), create, error);
261  }
262 
263  void RU32(const char* varname, uint32_t *value, bool create, MVOdbError* error)
264  {
265  R(varname, TID_DWORD, value, sizeof(uint32_t), create, error);
266  }
267 
268  void RD(const char* varname, double *value, bool create, MVOdbError* error)
269  {
270  bool ok = R(varname, TID_DOUBLE, value, sizeof(double), create, error);
271  if (!ok) {
272  float fvalue = *value;
273  ok = R(varname, TID_FLOAT, &fvalue, sizeof(float), create, error);
274  if (fPrintError && ok) {
275  std::string path = Path(varname);
276  fprintf(stderr, "MVOdb::RD: Sucessfully read ODB \"%s\" of type FLOAT instead of DOUBLE\n", path.c_str());
277  }
278  *value = fvalue;
279  }
280  }
281 
282  void RF(const char* varname, float *value, bool create, MVOdbError* error)
283  {
284  R(varname, TID_FLOAT, value, sizeof(float), create, error);
285  }
286 
287  void RB(const char* varname, bool *value, bool create, MVOdbError* error)
288  {
289  assert(value);
290  BOOL v = *value;
291  R(varname, TID_BOOL, &v, sizeof(BOOL), create, error);
292  *value = v;
293  }
294 
295  void RS(const char* varname, std::string* value, bool create, int create_string_length, MVOdbError* error)
296  {
297  assert(value);
298  std::string path = Path(varname);
299 
300 #ifdef HAVE_DB_GET_VALUE_STRING_CREATE_STRING_LENGTH
301  int status = db_get_value_string(fDB, 0, path.c_str(), 0, value, create, create_string_length);
302 #else
303 #warning This MIDAS has an old version of db_get_value_string() and RS() will ignore the create_string_length argument.
304  int status = db_get_value_string(fDB, 0, path.c_str(), 0, value, create);
305 #endif
306 
307  if (status != DB_SUCCESS) {
308  SetMidasStatus(error, fPrintError, path, "db_get_value_string", status);
309  return;
310  }
311 
312  SetOk(error);
313  }
314 
315  void RAI(const char* varname, int index, int tid, void *value, int size, MVOdbError* error)
316  {
317  assert(value);
318  std::string path = Path(varname);
319  path += "[";
320  path += toString(index);
321  path += "]";
322  if (index < 0) {
323  SetError(error, fPrintError, path, "RxAI() called with negative array index");
324  return;
325  }
326  int status = db_get_value(fDB, 0, path.c_str(), value, &size, tid, FALSE);
327  if (status != DB_SUCCESS) {
328  SetMidasStatus(error, fPrintError, path, "db_get_value", status);
329  return;
330  }
331  SetOk(error);
332  }
333 
334  void RIAI(const char* varname, int index, int *value, MVOdbError* error)
335  {
336  RAI(varname, index, TID_INT, value, sizeof(int), error);
337  }
338 
339  void RU16AI(const char* varname, int index, uint16_t *value, MVOdbError* error)
340  {
341  RAI(varname, index, TID_WORD, value, sizeof(uint16_t), error);
342  }
343 
344  void RU32AI(const char* varname, int index, uint32_t *value, MVOdbError* error)
345  {
346  RAI(varname, index, TID_DWORD, value, sizeof(uint32_t), error);
347  }
348 
349  void RDAI(const char* varname, int index, double *value, MVOdbError* error)
350  {
351  RAI(varname, index, TID_DOUBLE, value, sizeof(double), error);
352  }
353 
354  void RFAI(const char* varname, int index, float *value, MVOdbError* error)
355  {
356  RAI(varname, index, TID_FLOAT, value, sizeof(float), error);
357  }
358 
359  void RBAI(const char* varname, int index, bool *value, MVOdbError* error)
360  {
361  assert(value);
362  BOOL v = *value;
363  RAI(varname, index, TID_BOOL, &v, sizeof(BOOL), error);
364  *value = v;
365  }
366 
367  void RSAI(const char* varname, int index, std::string* value, MVOdbError* error)
368  {
369  assert(value);
370  std::string path = Path(varname);
371 
372  if (index < 0) {
373  SetError(error, fPrintError, path, "RSAI() called with negative array index");
374  return;
375  }
376 
377  int status = db_get_value_string(fDB, 0, path.c_str(), index, value, FALSE);
378 
379  if (status != DB_SUCCESS) {
380  SetMidasStatus(error, fPrintError, path, "db_get_value_string", status);
381  return;
382  }
383 
384  SetOk(error);
385  }
386 
387  bool RA(const std::string& path, int tid, void* buf, int size, MVOdbError* error)
388  {
389  int status = db_get_value(fDB, 0, path.c_str(), buf, &size, tid, FALSE);
390 
391  if (status != DB_SUCCESS) {
392  SetMidasStatus(error, fPrintError, path, "db_get_value", status);
393  return false;
394  }
395 
396  SetOk(error);
397  return true;
398  }
399 
400  void GetArraySize(const char* varname, int* pnum_values, int* pitem_size, MVOdbError* error)
401  {
402  int xtid = 0;
403  //int xnum_values = 0;
404  int xtotal_size = 0;
405  //int xitem_size = 0;
406 
407  ReadKey(varname, &xtid, pnum_values, &xtotal_size, pitem_size, error);
408 
409  if (xtid == TID_KEY) {
410  *pnum_values = -1;
411  *pitem_size = -1;
412  }
413 
414  if (xtid == 0) {
415  *pnum_values = -1;
416  *pitem_size = -1;
417  }
418  }
419 
420  template <class X> bool RXA(const char* varname, int tid, std::vector<X> *value, bool create, int create_size, MVOdbError* error)
421  {
422  std::string path = Path(varname);
423 
424  int num_values = 0;
425  int item_size = 0;
426 
427  GetArraySize(varname, &num_values, &item_size, error);
428 
429  if (value == NULL) {
430  if (create && create_size > 0) {
431  if (num_values < 0) {
432  // does not exist, create it
433  X v = 0;
434  W(varname, tid, &v, sizeof(X), error);
435  if (error && error->fError)
436  return false;
437  ResizeArray(varname, create_size, error);
438  } else if (num_values != create_size) {
439  // wrong size, resize it
440  ResizeArray(varname, create_size, error);
441  return true;
442  }
443  }
444  return true;
445  }
446 
447  if (num_values > 0) { // array exists
448  value->resize(num_values);
449  return RA(path, tid, &((*value)[0]), num_values*sizeof(X), error);
450  }
451 
452  // array does not exist
453 
454  if (!create)
455  return false;
456 
457  WA(varname, tid, &((*value)[0]), value->size()*sizeof(X), value->size(), error);
458 
459  if (error && error->fError)
460  return true;
461 
462  if (create_size > 0) {
463  if (create_size != (int)value->size()) {
464  ResizeArray(varname, create_size, error);
465  }
466  }
467 
468  return true;
469  }
470 
471  void RIA(const char* varname, std::vector<int> *value, bool create, int create_size, MVOdbError* error)
472  {
473  RXA<int>(varname, TID_INT, value, create, create_size, error);
474  }
475 
476  void RFA(const char* varname, std::vector<float> *value, bool create, int create_size, MVOdbError* error)
477  {
478  RXA<float>(varname, TID_FLOAT, value, create, create_size, error);
479  }
480 
481  void RDA(const char* varname, std::vector<double> *value, bool create, int create_size, MVOdbError* error)
482  {
483  bool ok = RXA<double>(varname, TID_DOUBLE, value, create, create_size, error);
484  if (!ok) {
485  std::vector<float> fvalue;
486  std::vector<float> *fvalue_ptr = NULL;
487  if (value) {
488  fvalue_ptr = &fvalue;
489  for (size_t i=0; i<value->size(); i++) {
490  fvalue.push_back((*value)[i]);
491  }
492  }
493  ok = RXA<float>(varname, TID_FLOAT, fvalue_ptr, create, create_size, error);
494  if (ok && fvalue_ptr) {
495  if (fPrintError) {
496  std::string path = Path(varname);
497  fprintf(stderr, "MVOdb::RDA: Sucessfully read ODB \"%s\" of type FLOAT instead of DOUBLE\n", path.c_str());
498  }
499  value->clear();
500  for (size_t i=0; i<fvalue.size(); i++) {
501  value->push_back(fvalue[i]);
502  }
503  }
504  }
505  }
506 
507  void RU16A(const char* varname, std::vector<uint16_t> *value, bool create, int create_size, MVOdbError* error)
508  {
509  RXA<uint16_t>(varname, TID_WORD, value, create, create_size, error);
510  }
511 
512  void RU32A(const char* varname, std::vector<uint32_t> *value, bool create, int create_size, MVOdbError* error)
513  {
514  RXA<uint32_t>(varname, TID_DWORD, value, create, create_size, error);
515  }
516 
517  void RBA(const char* varname, std::vector<bool> *value, bool create, int create_size, MVOdbError* error)
518  {
519  std::vector<BOOL> xvalue;
520  std::vector<BOOL> *xvalue_ptr = NULL;
521 
522  if (value) {
523  for (std::size_t i=0; i<value->size(); i++) {
524  if ((*value)[i])
525  xvalue.push_back(TRUE);
526  else
527  xvalue.push_back(FALSE);
528  }
529  xvalue_ptr = &xvalue;
530  }
531 
532  RXA<BOOL>(varname, TID_BOOL, xvalue_ptr, create, create_size, error);
533 
534  if (value) {
535  value->clear();
536  for (std::size_t i=0; i<xvalue.size(); i++) {
537  if (xvalue[i])
538  value->push_back(true);
539  else
540  value->push_back(false);
541  }
542  }
543  }
544 
545  void RSA(const char* varname, std::vector<std::string> *value, bool create, int create_size, int create_string_length, MVOdbError* error)
546  {
547  std::string path = Path(varname);
548 
549  int num_values = 0;
550  int item_size = 0;
551 
552  GetArraySize(varname, &num_values, &item_size, error);
553 
554  if (value == NULL) {
555  if (create && (create_size > 0) && (create_string_length > 0)) {
556  if (num_values < 0) {
557  // does not exist, create it
558  WS(varname, "", create_string_length, error);
559  if (error && error->fError)
560  return;
561  ResizeStringArray(varname, create_size, create_string_length, error);
562  } else if ((num_values != create_size) || (item_size != create_string_length)) {
563  // wrong size, resize it
564  ResizeStringArray(varname, create_size, create_string_length, error);
565  return;
566  }
567  }
568  return;
569  }
570 
571  // array exists, read it
572 
573  if (num_values > 0) {
574  value->clear();
575  int bufsize = num_values*item_size;
576  char* buf = (char*)malloc(bufsize);
577  assert(buf != NULL);
578  memset(buf, 0, bufsize);
579  RA(path, TID_STRING, buf, bufsize, error);
580  for (int i=0; i<num_values; i++) {
581  value->push_back(buf+i*item_size);
582  }
583  free(buf);
584  buf = NULL;
585  return;
586  }
587 
588  // array does not exist
589 
590  if (!create)
591  return;
592 
593  //if (!(create_string_length > 0)) {
594  // SetError(error, fPrintError, path, "RSA() with create==true must have create_string_length>0");
595  // return;
596  //}
597 
598  int string_length = 0;
599  for (size_t i = 0; i < value->size(); i++) {
600  if (((int)(*value)[i].length()) > string_length)
601  string_length = (*value)[i].length();
602  }
603  string_length += 1; // add space for string terminator NUL character '\0'
604 
605  if (create_string_length > string_length)
606  string_length = create_string_length;
607 
608  char* buf = NULL;
609 
610  int bufsize = value->size()*string_length;
611 
612  if (bufsize > 0) {
613  buf = (char*)malloc(bufsize);
614  assert(buf != NULL);
615  memset(buf, 0, bufsize);
616 
617  for (size_t i=0; i<value->size(); i++) {
618  strlcpy(buf+i*string_length, (*value)[i].c_str(), string_length);
619  }
620  }
621 
622  WA(varname, TID_STRING, buf, bufsize, value->size(), error);
623 
624  if (buf) {
625  free(buf);
626  buf = NULL;
627  }
628 
629  if (error && error->fError)
630  return;
631 
632  if ((create_size > 0) && (create_string_length > 0)) {
633  if ((((int)value->size()) != create_size) || (string_length != create_string_length)) {
634  // wrong size, resize it
635  ResizeStringArray(varname, create_size, create_string_length, error);
636  }
637  }
638  }
639 
640  void W(const char* varname, int tid, const void* v, int size, MVOdbError* error)
641  {
642  std::string path = Path(varname);
643 
644  int status = db_set_value(fDB, 0, path.c_str(), v, size, 1, tid);
645 
646  if (status == DB_TYPE_MISMATCH) {
647  if (fPrintError) {
648  fprintf(stderr, "MVOdb::W: Data type mismatch when writing to ODB \"%s\", deleting the old entry\n", path.c_str());
649  }
650 
651  Delete(varname, error);
652 
653  status = db_set_value(fDB, 0, path.c_str(), v, size, 1, tid);
654  }
655 
656  if (status != DB_SUCCESS) {
657  SetMidasStatus(error, fPrintError, path, "db_set_value", status);
658  return;
659  }
660 
661  SetOk(error);
662  return;
663  }
664 
665  void WB(const char* varname, bool v, MVOdbError* error)
666  {
667  BOOL vv = v;
668  W(varname, TID_BOOL, &vv, sizeof(BOOL), error);
669  }
670 
671  void WI(const char* varname, int v, MVOdbError* error)
672  {
673  W(varname, TID_INT, &v, sizeof(int), error);
674  }
675 
676  void WU16(const char* varname, uint16_t v, MVOdbError* error)
677  {
678  W(varname, TID_WORD, &v, sizeof(uint16_t), error);
679  }
680 
681  void WU32(const char* varname, uint32_t v, MVOdbError* error)
682  {
683  W(varname, TID_DWORD, &v, sizeof(uint32_t), error);
684  }
685 
686  void WD(const char* varname, double v, MVOdbError* error)
687  {
688  W(varname, TID_DOUBLE, &v, sizeof(double), error);
689  }
690 
691  void WF(const char* varname, float v, MVOdbError* error)
692  {
693  W(varname, TID_FLOAT, &v, sizeof(float), error);
694  }
695 
696  void WS(const char* varname, const char* v, int string_length, MVOdbError* error)
697  {
698  if (string_length > 0) {
699  char* buf = (char*)malloc(string_length);
700  assert(buf);
701  strlcpy(buf, v, string_length);
702  W(varname, TID_STRING, buf, string_length, error);
703  free(buf);
704  } else {
705  int len = strlen(v);
706  W(varname, TID_STRING, v, len+1, error);
707  }
708  }
709 
710  void WAI(const char* varname, int index, int tid, const void* v, int size, MVOdbError* error)
711  {
712  std::string path = Path(varname);
713 
714  if (index < 0) {
715  SetError(error, fPrintError, path, "WxAI() called with negative array index");
716  return;
717  }
718 
719  //printf("WAI(\"%s\", [%d], %d) path [%s], size %d\n", varname, index, tid, path.c_str(), size);
720 
721  int status;
722  HNDLE hkey;
723 
724  status = db_find_key(fDB, 0, path.c_str(), &hkey);
725 
726  if (status != DB_SUCCESS) {
727  SetMidasStatus(error, fPrintError, path, "db_find_key", status);
728  return;
729  }
730 
731  status = db_set_data_index(fDB, hkey, v, size, index, tid);
732 
733  if (status != DB_SUCCESS) {
734  SetMidasStatus(error, fPrintError, path, "db_set_value", status);
735  return;
736  }
737 
738  SetOk(error);
739  }
740 
741  void WBAI(const char* varname, int index, bool v, MVOdbError* error)
742  {
743  BOOL vv = v;
744  WAI(varname, index, TID_BOOL, &vv, sizeof(BOOL), error);
745  }
746 
747  void WIAI(const char* varname, int index, int v, MVOdbError* error)
748  {
749  WAI(varname, index, TID_INT, &v, sizeof(int), error);
750  }
751 
752  void WU16AI(const char* varname, int index, uint16_t v, MVOdbError* error)
753  {
754  WAI(varname, index, TID_WORD, &v, sizeof(uint16_t), error);
755  }
756 
757  void WU32AI(const char* varname, int index, uint32_t v, MVOdbError* error)
758  {
759  WAI(varname, index, TID_DWORD, &v, sizeof(uint32_t), error);
760  }
761 
762  void WDAI(const char* varname, int index, double v, MVOdbError* error)
763  {
764  WAI(varname, index, TID_DOUBLE, &v, sizeof(double), error);
765  }
766 
767  void WFAI(const char* varname, int index, float v, MVOdbError* error)
768  {
769  WAI(varname, index, TID_FLOAT, &v, sizeof(float), error);
770  }
771 
772  void WSAI(const char* varname, int index, const char* v, MVOdbError* error)
773  {
774  int num_elements = 0;
775  int element_size = 0;
776  RAInfo(varname, &num_elements, &element_size, error);
777  if (error && error->fError)
778  return;
779  if (element_size <= 0)
780  return;
781  char* buf = (char*)malloc(element_size);
782  assert(buf);
783  strlcpy(buf, v, element_size);
784  WAI(varname, index, TID_STRING, buf, element_size, error);
785  free(buf);
786  }
787 
788  void WA(const char* varname, int tid, const void* v, int size, int count, MVOdbError* error)
789  {
790  std::string path = Path(varname);
791 
792  //printf("WA(tid %d, size %d, count %d)\n", tid, size, count);
793 
794  if (size == 0) {
795  int status = db_create_key(fDB, 0, path.c_str(), tid);
796 
797  if (status == DB_TYPE_MISMATCH) {
798  if (fPrintError) {
799  fprintf(stderr, "MVOdb::WA: Data type mismatch when writing to ODB \"%s\", deleting the old entry\n", path.c_str());
800  }
801 
802  Delete(varname, error);
803 
804  status = db_create_key(fDB, 0, path.c_str(), tid);
805  }
806 
807  if (status != DB_SUCCESS) {
808  SetMidasStatus(error, fPrintError, path, "db_create_key", status);
809  return;
810  }
811  } else {
812  int status = db_set_value(fDB, 0, path.c_str(), v, size, count, tid);
813 
814  //printf("WA db_set_value(tid %d, size %d, count %d) status %d\n", tid, size, count, status);
815 
816  if (status == DB_TYPE_MISMATCH) {
817  if (fPrintError) {
818  fprintf(stderr, "MVOdb::WA: Data type mismatch when writing to ODB \"%s\", deleting the old entry\n", path.c_str());
819  }
820 
821  Delete(varname, error);
822 
823  status = db_set_value(fDB, 0, path.c_str(), v, size, count, tid);
824  }
825 
826  if (status != DB_SUCCESS) {
827  SetMidasStatus(error, fPrintError, path, "db_set_value", status);
828  return;
829  }
830  }
831 
832  SetOk(error);
833  }
834 
835  void WBA(const char* varname, const std::vector<bool>& v, MVOdbError* error)
836  {
837  unsigned num = v.size();
838  BOOL val[num];
839 
840  for (unsigned i=0; i<num; i++) {
841  val[i] = v[i];
842  }
843 
844  WA(varname, TID_BOOL, val, num*sizeof(BOOL), num, error);
845  }
846 
847  void WU16A(const char* varname, const std::vector<uint16_t>& v, MVOdbError* error)
848  {
849  WA(varname, TID_WORD, &v[0], v.size()*sizeof(uint16_t), v.size(), error);
850  }
851 
852  void WU32A(const char* varname, const std::vector<uint32_t>& v, MVOdbError* error)
853  {
854  WA(varname, TID_DWORD, &v[0], v.size()*sizeof(uint32_t), v.size(), error);
855  }
856 
857  void WIA(const char* varname, const std::vector<int>& v, MVOdbError* error)
858  {
859  WA(varname, TID_INT, &v[0], v.size()*sizeof(int), v.size(), error);
860  }
861 
862  void WFA(const char* varname, const std::vector<float>& v, MVOdbError* error)
863  {
864  WA(varname, TID_FLOAT, &v[0], v.size()*sizeof(float), v.size(), error);
865  }
866 
867  void WDA(const char* varname, const std::vector<double>& v, MVOdbError* error)
868  {
869  WA(varname, TID_DOUBLE, &v[0], v.size()*sizeof(double), v.size(), error);
870  }
871 
872  void WSA(const char* varname, const std::vector<std::string>& v, int odb_string_size, MVOdbError* error)
873  {
874  unsigned num = v.size();
875  unsigned length = odb_string_size;
876 
877  if (length == 0) {
878  for (unsigned i=0; i<v.size(); i++) {
879  if (v[i].length() > length)
880  length = v[i].length();
881  }
882  length += 1; // for the string terminator NUL character
883  }
884 
885  char val[length*num];
886  memset(val, 0, length*num);
887 
888  for (unsigned i=0; i<num; i++)
889  strlcpy(val+length*i, v[i].c_str(), length);
890 
891  WA(varname, TID_STRING, val, num*length, num, error);
892  }
893 
894  void Delete(const char* odbname, MVOdbError* error)
895  {
896  std::string path = Path(odbname);
897 
898  //printf("Delete(%s)\n", path.c_str());
899 
900  HNDLE hKey;
901  int status = db_find_key(fDB, 0, path.c_str(), &hKey);
902 
903  if (status == DB_NO_KEY) {
904  SetOk(error);
905  return;
906  }
907 
908  if (status != DB_SUCCESS) {
909  SetMidasStatus(error, fPrintError, path, "db_find_key", status);
910  return;
911  }
912 
913  status = db_delete_key(fDB, hKey, FALSE);
914 
915  if (status != DB_SUCCESS) {
916  SetMidasStatus(error, fPrintError, path, "db_delete_key", status);
917  return;
918  }
919 
920  SetOk(error);
921  };
922 };
923 
924 MVOdb* MakeMidasOdb(int hDB, MVOdbError* error)
925 {
926  SetOk(error);
927  return new MidasOdb(hDB, "");
928 }
929 
930 /* emacs
931  * Local Variables:
932  * tab-width: 8
933  * c-basic-offset: 3
934  * indent-tabs-mode: nil
935  * End:
936  */
bool fError
Definition: mvodb.h:190
Definition: mvodb.h:21
void RIA(const char *varname, std::vector< int > *value, bool create, int create_size, MVOdbError *error)
Definition: midasodb.cxx:471
void WU16(const char *varname, uint16_t v, MVOdbError *error)
Definition: midasodb.cxx:676
bool GetPrintError() const
Definition: midasodb.cxx:60
void SetPrintError(bool v)
Definition: midasodb.cxx:55
void WU16AI(const char *varname, int index, uint16_t v, MVOdbError *error)
Definition: midasodb.cxx:752
void RD(const char *varname, double *value, bool create, MVOdbError *error)
Definition: midasodb.cxx:268
bool R(const char *varname, int tid, void *value, int size, bool create, MVOdbError *error)
Definition: midasodb.cxx:240
void RF(const char *varname, float *value, bool create, MVOdbError *error)
Definition: midasodb.cxx:282
void WIAI(const char *varname, int index, int v, MVOdbError *error)
Definition: midasodb.cxx:747
bool fPrintError
Definition: midasodb.cxx:30
MidasOdb(HNDLE hDB, const char *root)
Definition: midasodb.cxx:34
bool fPrintWarning
Definition: midasodb.cxx:31
void W(const char *varname, int tid, const void *v, int size, MVOdbError *error)
Definition: midasodb.cxx:640
void RIAI(const char *varname, int index, int *value, MVOdbError *error)
Definition: midasodb.cxx:334
void RFAI(const char *varname, int index, float *value, MVOdbError *error)
Definition: midasodb.cxx:354
void ResizeStringArray(const char *varname, int new_size, int new_string_length, MVOdbError *error)
Definition: midasodb.cxx:227
void RSA(const char *varname, std::vector< std::string > *value, bool create, int create_size, int create_string_length, MVOdbError *error)
Definition: midasodb.cxx:545
void RAInfo(const char *varname, int *num_elements, int *element_size, MVOdbError *error)
Definition: midasodb.cxx:103
void GetArraySize(const char *varname, int *pnum_values, int *pitem_size, MVOdbError *error)
Definition: midasodb.cxx:400
void WU32(const char *varname, uint32_t v, MVOdbError *error)
Definition: midasodb.cxx:681
void RDA(const char *varname, std::vector< double > *value, bool create, int create_size, MVOdbError *error)
Definition: midasodb.cxx:481
void RB(const char *varname, bool *value, bool create, MVOdbError *error)
Definition: midasodb.cxx:287
void WDA(const char *varname, const std::vector< double > &v, MVOdbError *error)
Definition: midasodb.cxx:867
void RSAI(const char *varname, int index, std::string *value, MVOdbError *error)
Definition: midasodb.cxx:367
void WIA(const char *varname, const std::vector< int > &v, MVOdbError *error)
Definition: midasodb.cxx:857
HNDLE fDB
Definition: midasodb.cxx:28
void RU32AI(const char *varname, int index, uint32_t *value, MVOdbError *error)
Definition: midasodb.cxx:344
void RAI(const char *varname, int index, int tid, void *value, int size, MVOdbError *error)
Definition: midasodb.cxx:315
bool RXA(const char *varname, int tid, std::vector< X > *value, bool create, int create_size, MVOdbError *error)
Definition: midasodb.cxx:420
std::string Path(const char *varname)
Definition: midasodb.cxx:46
void WI(const char *varname, int v, MVOdbError *error)
Definition: midasodb.cxx:671
void WS(const char *varname, const char *v, int string_length, MVOdbError *error)
Definition: midasodb.cxx:696
void ReadKeyLastWritten(const char *varname, int *last_written, MVOdbError *error)
Definition: midasodb.cxx:170
bool IsReadOnly() const
Definition: midasodb.cxx:65
void RI(const char *varname, int *value, bool create, MVOdbError *error)
Definition: midasodb.cxx:253
void RU32A(const char *varname, std::vector< uint32_t > *value, bool create, int create_size, MVOdbError *error)
Definition: midasodb.cxx:512
void WSA(const char *varname, const std::vector< std::string > &v, int odb_string_size, MVOdbError *error)
Definition: midasodb.cxx:872
void ResizeArray(const char *varname, int new_size, MVOdbError *error)
Definition: midasodb.cxx:204
void RDAI(const char *varname, int index, double *value, MVOdbError *error)
Definition: midasodb.cxx:349
void WBAI(const char *varname, int index, bool v, MVOdbError *error)
Definition: midasodb.cxx:741
void RBA(const char *varname, std::vector< bool > *value, bool create, int create_size, MVOdbError *error)
Definition: midasodb.cxx:517
void RFA(const char *varname, std::vector< float > *value, bool create, int create_size, MVOdbError *error)
Definition: midasodb.cxx:476
void Delete(const char *odbname, MVOdbError *error)
Definition: midasodb.cxx:894
~MidasOdb()
Definition: midasodb.cxx:40
void WB(const char *varname, bool v, MVOdbError *error)
Definition: midasodb.cxx:665
void WU16A(const char *varname, const std::vector< uint16_t > &v, MVOdbError *error)
Definition: midasodb.cxx:847
void ReadKey(const char *varname, int *tid, int *num_values, int *total_size, int *item_size, MVOdbError *error)
Definition: midasodb.cxx:130
MVOdb * Chdir(const char *subdir, bool create, MVOdbError *error)
Definition: midasodb.cxx:70
void WDAI(const char *varname, int index, double v, MVOdbError *error)
Definition: midasodb.cxx:762
void WBA(const char *varname, const std::vector< bool > &v, MVOdbError *error)
Definition: midasodb.cxx:835
void ReadDir(std::vector< std::string > *varname, std::vector< int > *tid, std::vector< int > *num_values, std::vector< int > *total_size, std::vector< int > *item_size, MVOdbError *error)
Definition: midasodb.cxx:198
void RU16A(const char *varname, std::vector< uint16_t > *value, bool create, int create_size, MVOdbError *error)
Definition: midasodb.cxx:507
void RU16(const char *varname, uint16_t *value, bool create, MVOdbError *error)
Definition: midasodb.cxx:258
void WU32A(const char *varname, const std::vector< uint32_t > &v, MVOdbError *error)
Definition: midasodb.cxx:852
void WFA(const char *varname, const std::vector< float > &v, MVOdbError *error)
Definition: midasodb.cxx:862
void WD(const char *varname, double v, MVOdbError *error)
Definition: midasodb.cxx:686
void WSAI(const char *varname, int index, const char *v, MVOdbError *error)
Definition: midasodb.cxx:772
void RS(const char *varname, std::string *value, bool create, int create_string_length, MVOdbError *error)
Definition: midasodb.cxx:295
bool RA(const std::string &path, int tid, void *buf, int size, MVOdbError *error)
Definition: midasodb.cxx:387
std::string fRoot
Definition: midasodb.cxx:29
void RBAI(const char *varname, int index, bool *value, MVOdbError *error)
Definition: midasodb.cxx:359
void WU32AI(const char *varname, int index, uint32_t v, MVOdbError *error)
Definition: midasodb.cxx:757
void RU16AI(const char *varname, int index, uint16_t *value, MVOdbError *error)
Definition: midasodb.cxx:339
void WF(const char *varname, float v, MVOdbError *error)
Definition: midasodb.cxx:691
void RU32(const char *varname, uint32_t *value, bool create, MVOdbError *error)
Definition: midasodb.cxx:263
void WA(const char *varname, int tid, const void *v, int size, int count, MVOdbError *error)
Definition: midasodb.cxx:788
void WAI(const char *varname, int index, int tid, const void *v, int size, MVOdbError *error)
Definition: midasodb.cxx:710
void WFAI(const char *varname, int index, float v, MVOdbError *error)
Definition: midasodb.cxx:767
#define TID_DOUBLE
Definition: midasio.h:29
#define TID_KEY
Definition: midasio.h:35
#define TID_BOOL
Definition: midasio.h:26
#define TID_WORD
Definition: midasio.h:18
#define TID_STRING
Definition: midasio.h:32
#define TID_INT
Definition: midasio.h:24
#define TID_FLOAT
Definition: midasio.h:27
#define TID_DWORD
Definition: midasio.h:22
void SetMidasStatus(MVOdbError *error, bool print, const std::string &path, const char *midas_func_name, int status)
Definition: mvodb.cxx:41
MVOdb * MakeNullOdb()
Definition: nullodb.cxx:129
void SetError(MVOdbError *error, bool print, const std::string &path, const std::string &message)
Definition: mvodb.cxx:70
void SetOk(MVOdbError *error)
Definition: mvodb.cxx:31
MVOdb * MakeMidasOdb(int hDB, MVOdbError *error)
Definition: midasodb.cxx:924
static std::string toString(int value)
Definition: midasodb.cxx:18
#define TRUE
Definition: mxml.cxx:75
#define FALSE
Definition: mxml.cxx:76