00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include <BerkeleyDbDatastore.h>
00026 #include <Vector.h>
00027 #include <Matrix.h>
00028 #include <ID.h>
00029
00030 #include <errno.h>
00031 #include <unistd.h>
00032 #include <sys/stat.h>
00033
00034 BerkeleyDbDatastore::BerkeleyDbDatastore(const char *projectName,
00035 Domain &theDomain,
00036 FEM_ObjectBroker &theObjectBroker,
00037 char *dbType)
00038 :FE_Datastore(theDomain, theObjectBroker), dbTag(0),
00039 connection(true)
00040 {
00041
00042 project = new char[strlen(projectName) + 1];
00043 strcpy(project, projectName);
00044
00045
00046 struct stat sb;
00047 if (stat(project, &sb) != 0) {
00048
00049
00050 if (mkdir(project, S_IRWXU) != 0) {
00051 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed mkdir: ";
00052 opserr << project << " " << strerror(errno);
00053 connection = false;
00054 return;
00055 }
00056 }
00057
00058
00059 int ret = 0;
00060 if ((ret = db_env_create(&dbenv, 0)) != 0) {
00061 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed db_env_create: ";
00062 opserr << db_strerror(ret) << endln;
00063 connection = false;
00064 }
00065
00066
00067 dbenv->set_errpfx(dbenv, project);
00068
00069
00070 if ((ret = dbenv->open(dbenv, project,
00071 DB_CREATE | DB_INIT_LOG | DB_PRIVATE | DB_INIT_MPOOL,
00072 S_IRUSR | S_IWUSR)) != 0) {
00073
00074 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed db_env_create: ";
00075 opserr << db_strerror(ret) << endln;
00076 connection = false;
00077 return;
00078 }
00079
00080
00081
00082 int result;
00083 if ((result = db_create(&dbMatrix, dbenv, 0)) != 0) {
00084 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed to init dbMatrix";
00085 opserr << db_strerror(result) << endln;
00086 connection = false;
00087 return;
00088 }
00089 if ((result = db_create(&dbVector, dbenv, 0)) != 0) {
00090 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed to init dbVector";
00091 opserr << db_strerror(result) << endln;
00092 connection = false;
00093 return;
00094 }
00095 if ((result = db_create(&dbID, dbenv, 0)) != 0) {
00096 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed to init dbID";
00097 opserr << db_strerror(result) << endln;
00098 connection = false;
00099 return;
00100 }
00101
00102
00103
00104 DBTYPE type = DB_HASH;
00105 if (dbType != NULL) {
00106 if ((strcmp(dbType, "hash") == 0) || (strcmp(dbType, "HASH") == 0))
00107 type = DB_HASH;
00108 else if ((strcmp(dbType, "queue") == 0) || (strcmp(dbType, "QUEUE") == 0))
00109 type = DB_QUEUE;
00110 else if ((strcmp(dbType, "btree") == 0) || (strcmp(dbType, "BTREE") == 0))
00111 type = DB_BTREE;
00112 else if ((strcmp(dbType, "recno") == 0) || (strcmp(dbType, "RECNO") == 0))
00113 type = DB_RECNO;
00114 }
00115
00116
00117 #ifdef _BerkeleyDB41orGreater
00118
00119 if ((result = dbMatrix->open(dbMatrix, NULL, "Matrices.db", NULL, type,
00120 DB_CREATE | DB_EXCL, 0664)) != 0) {
00121
00122 if ((result = dbMatrix->open(dbMatrix, NULL, "Matrices.db", NULL, type,
00123 DB_CREATE, 0664)) != 0) {
00124 #else
00125 if ((result = dbMatrix->open(dbMatrix, "Matrices.db", NULL, type,
00126 DB_CREATE | DB_EXCL, 0664)) != 0) {
00127
00128 if ((result = dbMatrix->open(dbMatrix, "Matrices.db", NULL, type,
00129 DB_CREATE, 0664)) != 0) {
00130 #endif
00131
00132 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed to open dbMatrix\n";
00133 opserr << db_strerror(result) << endln;
00134 connection = false;
00135 return;
00136 }
00137 }
00138
00139
00140 #ifdef _BerkeleyDB41orGreater
00141
00142 if ((result = dbVector->open(dbVector, NULL, "Vectors.db", NULL, type,
00143 DB_CREATE | DB_EXCL, 0664)) != 0) {
00144
00145 if ((result = dbVector->open(dbVector, NULL, "Vectors.db", NULL, type,
00146 DB_CREATE, 0664)) != 0) {
00147
00148 #else
00149
00150 if ((result = dbVector->open(dbVector, "Vectors.db", NULL, type,
00151 DB_CREATE | DB_EXCL, 0664)) != 0) {
00152
00153 if ((result = dbVector->open(dbVector, "Vectors.db", NULL, type,
00154 DB_CREATE, 0664)) != 0) {
00155
00156 #endif
00157 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed to open dbVector\n";
00158 opserr << db_strerror(result) << endln;
00159 connection = false;
00160 return;
00161 }
00162 }
00163
00164 #ifdef _BerkeleyDB41orGreater
00165 if ((result = dbID->open(dbID, NULL, "IDs.db", NULL, type,
00166 DB_CREATE | DB_EXCL, 0664)) != 0) {
00167 type = DB_UNKNOWN;
00168 if ((result = dbID->open(dbID, NULL, "IDs.db", NULL, type,
00169 0, 0664)) != 0) {
00170 #else
00171 if ((result = dbID->open(dbID, "IDs.db", NULL, type,
00172 DB_CREATE | DB_EXCL, 0664)) != 0) {
00173 type = DB_UNKNOWN;
00174 if ((result = dbID->open(dbID, "IDs.db", NULL, type,
00175 0, 0664)) != 0) {
00176 #endif
00177
00178 opserr << "BerkeleyDbDatastore::BerkeleyDbDatastore - failed to open dbID\n";
00179 opserr << db_strerror(result) << endln;
00180 connection = false;
00181 return;
00182 } else
00183 result = dbID->get_type(dbID, &type);
00184 }
00185 }
00186
00187
00188 BerkeleyDbDatastore::~BerkeleyDbDatastore()
00189 {
00190 opserr << "CLOSING DATABASE\n";
00191
00192 if (connection == true)
00193 dbMatrix->close(dbMatrix, 0);
00194 if (connection == true)
00195 dbVector->close(dbVector, 0);
00196 if (connection == true)
00197 dbID->close(dbID, 0);
00198 if (connection == true)
00199 dbenv->close(dbenv, 0);
00200
00201 if (project != 0)
00202 delete [] project;
00203 }
00204
00205
00206 int
00207 BerkeleyDbDatastore::getDbTag(void)
00208 {
00209 dbTag++;
00210 return dbTag;
00211 }
00212
00213
00214 int
00215 BerkeleyDbDatastore::sendMsg(int dataTag, int commitTag,
00216 const Message &,
00217 ChannelAddress *theAddress)
00218 {
00219 opserr << "BerkeleyDbDatastore::sendMsg() - not yet implemented\n";
00220 return -1;
00221 }
00222
00223 int
00224 BerkeleyDbDatastore::recvMsg(int dataTag, int commitTag,
00225 Message &,
00226 ChannelAddress *theAddress)
00227 {
00228 opserr << "BerkeleyDbDatastore::recvMsg() - not yet implemented\n";
00229 return -1;
00230 }
00231
00232 int
00233 BerkeleyDbDatastore::sendMatrix(int dbTag, int commitTag,
00234 const Matrix &theMatrix,
00235 ChannelAddress *theAddress)
00236 {
00237
00238 if (connection == false)
00239 return -1;
00240
00241
00242 sprintf(query,"%d-%d-%d", dbTag, commitTag, theMatrix.dataSize);
00243 key.data = query;
00244 key.size = strlen(query);
00245 key.ulen = key.size;
00246 key.doff = 0;
00247 key.flags = DB_DBT_USERMEM;
00248
00249
00250 data.data = (void *)theMatrix.data;
00251 data.size = theMatrix.dataSize * sizeof(double);
00252 data.ulen = data.size;
00253 data.doff = 0;
00254 data.flags = DB_DBT_USERMEM;
00255
00256 int ret;
00257 if ((ret = dbMatrix->put(dbMatrix, NULL, &key, &data, 0)) != 0) {
00258 opserr << "BerkeleyDbDatastore::sendMatrix() - failed to send the Matrix to database\n";
00259 dbMatrix->err(dbMatrix, ret, "DB->put");
00260 return -2;
00261 }
00262
00263 return 0;
00264 }
00265
00266
00267 int
00268 BerkeleyDbDatastore::recvMatrix(int dbTag, int commitTag,
00269 Matrix &theMatrix,
00270 ChannelAddress *theAddress)
00271 {
00272
00273 if (connection == false)
00274 return -1;
00275
00276
00277 sprintf(query,"%d-%d-%d", dbTag, commitTag, theMatrix.dataSize);
00278 key.data = query;
00279 key.size = strlen(query);
00280 key.ulen = key.size;
00281 key.doff = 0;
00282 key.flags = DB_DBT_USERMEM;
00283
00284
00285 data.data = (void *)theMatrix.data;
00286 data.size = theMatrix.dataSize * sizeof(double);
00287 data.ulen = data.size;
00288 data.doff = 0;
00289 data.flags = DB_DBT_USERMEM;
00290
00291 int ret;
00292 if ((ret = dbMatrix->get(dbMatrix, NULL, &key, &data, 0)) != 0) {
00293 opserr << "BerkeleyDbDatastore::recvMatrix() - failed to get the Matrix from database\n";
00294 dbMatrix->err(dbMatrix, ret, "DB->get");
00295 return -2;
00296 }
00297
00298 return 0;
00299 }
00300
00301
00302 int
00303 BerkeleyDbDatastore::sendVector(int dbTag, int commitTag,
00304 const Vector &theVector,
00305 ChannelAddress *theAddress)
00306 {
00307
00308 if (connection == false)
00309 return -1;
00310
00311
00312 sprintf(query,"%d-%d-%d", dbTag, commitTag, theVector.sz);
00313 key.data = query;
00314 key.size = strlen(query);
00315 key.ulen = key.size;
00316 key.doff = 0;
00317 key.flags = DB_DBT_USERMEM;
00318
00319
00320 data.data = (void *)theVector.theData;
00321 data.size = theVector.sz * sizeof(double);
00322 data.ulen = data.size;
00323 data.doff = 0;
00324 data.flags = DB_DBT_USERMEM;
00325
00326 int ret;
00327 if ((ret = dbVector->put(dbVector, NULL, &key, &data, 0)) != 0) {
00328 opserr << "BerkeleyDbDatastore::sendVector() - failed to send the Vector to database\n";
00329 dbVector->err(dbVector, ret, "DB->put");
00330 return -2;
00331 }
00332
00333 return 0;
00334 }
00335
00336
00337 int
00338 BerkeleyDbDatastore::recvVector(int dbTag, int commitTag,
00339 Vector &theVector,
00340 ChannelAddress *theAddress)
00341 {
00342
00343 if (connection == false)
00344 return -1;
00345
00346
00347 sprintf(query,"%d-%d-%d", dbTag, commitTag, theVector.sz);
00348 key.data = query;
00349 key.size = strlen(query);
00350 key.ulen = key.size;
00351 key.doff = 0;
00352 key.flags = DB_DBT_USERMEM;
00353
00354
00355 data.data = (void *)theVector.theData;
00356 data.size = theVector.sz * sizeof(double);
00357 data.ulen = data.size;
00358 data.doff = 0;
00359 data.flags = DB_DBT_USERMEM;
00360
00361 int ret;
00362 if ((ret = dbVector->get(dbVector, NULL, &key, &data, 0)) != 0) {
00363 opserr << "BerkeleyDbDatastore::recvVector() - failed to get the Vector from database\n";
00364 dbVector->err(dbVector, ret, "DB->get");
00365 return -2;
00366 }
00367
00368 return 0;
00369 }
00370
00371
00372 int
00373 BerkeleyDbDatastore::sendID(int dbTag, int commitTag,
00374 const ID &theID,
00375 ChannelAddress *theAddress)
00376 {
00377 int ret = 0;
00378
00379
00380 if (connection == false)
00381 return -1;
00382
00383
00384 sprintf(query,"%d-%d-%d", dbTag, commitTag, theID.sz);
00385 key.data = query;
00386 key.size = strlen(query);
00387 key.ulen = key.size;
00388 key.doff = 0;
00389 key.flags = DB_DBT_USERMEM;
00390
00391
00392 data.data = (void *)theID.data;
00393 data.size = theID.sz * sizeof(int);
00394 data.ulen = data.size;
00395 data.doff = 0;
00396 data.flags = DB_DBT_USERMEM;
00397
00398 if ((ret = dbID->put(dbID, 0, &key, &data, 0)) != 0) {
00399 opserr << "BerkeleyDbDatastore::sendID() - failed to send the ID to database\n";
00400 dbID->err(dbID, ret, "DB->put");
00401 return -2;
00402
00403 }
00404 opserr << dbTag << " " << commitTag << " " << theID.Size() << " " << query << endln;
00405
00406 return 0;
00407 }
00408
00409
00410 int
00411 BerkeleyDbDatastore::recvID(int dbTag, int commitTag,
00412 ID &theID,
00413 ChannelAddress *theAddress)
00414 {
00415
00416 if (connection == false)
00417 return -1;
00418
00419
00420 sprintf(query,"%d-%d-%d", dbTag, commitTag, theID.sz);
00421 key.data = query;
00422 key.size = strlen(query);
00423 key.ulen = key.size;
00424 key.doff = 0;
00425 key.flags = DB_DBT_USERMEM;
00426
00427 opserr << dbTag << " " << commitTag << " " << theID.Size() << " " << query << endln;
00428
00429
00430
00431
00432 data.data = (void *)theID.data;
00433 data.size = theID.sz * sizeof(int);
00434 data.ulen = data.size;
00435 data.doff = 0;
00436 data.flags = DB_DBT_USERMEM;
00437
00438 int ret;
00439 if ((ret = dbID->get(dbID, NULL, &key, &data, 0)) != 0) {
00440 opserr << "BerkeleyDbDatastore::recvID() - failed to get the ID from database\n";
00441 dbID->err(dbID, ret, "DB->get");
00442 return -2;
00443 }
00444
00445 return 0;
00446 }