sqlite_ubench.cc 7.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266
  1. // Copyright (C) 2012 Internet Systems Consortium, Inc. ("ISC")
  2. //
  3. // Permission to use, copy, modify, and/or distribute this software for any
  4. // purpose with or without fee is hereby granted, provided that the above
  5. // copyright notice and this permission notice appear in all copies.
  6. //
  7. // THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
  8. // REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
  9. // AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
  10. // INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
  11. // LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
  12. // OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
  13. // PERFORMANCE OF THIS SOFTWARE.
  14. #include <stdio.h>
  15. #include <stdlib.h>
  16. #include <stdint.h>
  17. #include <string.h>
  18. #include <sstream>
  19. #include <iostream>
  20. #include <sqlite3.h>
  21. #include "sqlite_ubench.h"
  22. using namespace std;
  23. SQLite_uBenchmark::SQLite_uBenchmark(const string& filename,
  24. uint32_t num_iterations,
  25. bool sync, bool verbose)
  26. :uBenchmark(num_iterations, filename, sync, verbose),
  27. db_(NULL) {
  28. }
  29. void SQLite_uBenchmark::connect() {
  30. int result = sqlite3_open(dbname_.c_str(), &db_);
  31. if (result) {
  32. sqlite3_open(dbname_.c_str(), &db_);
  33. failure("Failed to open DB file");
  34. }
  35. sqlite3_exec(db_, "DELETE FROM lease4", NULL, NULL, NULL);
  36. if (sync_) {
  37. sqlite3_exec(db_, "PRAGMA synchronous = ON", NULL, NULL, NULL);
  38. } else {
  39. sqlite3_exec(db_, "PRAGMA synchronous = OFF", NULL, NULL, NULL);
  40. }
  41. // see http://www.sqlite.org/pragma.html#pragma_journal_mode
  42. // for detailed explanation. Available modes: DELETE, TRUNCATE,
  43. // PERSIST, MEMORY, WAL, OFF
  44. sqlite3_exec(db_, "PRAGMA journal_mode = OFF", NULL, NULL, NULL);
  45. }
  46. void SQLite_uBenchmark::disconnect() {
  47. if (db_) {
  48. sqlite3_close(db_);
  49. db_ = NULL;
  50. }
  51. }
  52. void SQLite_uBenchmark::createLease4Test() {
  53. if (!db_) {
  54. throw "SQLite connection is closed.";
  55. }
  56. uint32_t addr = BASE_ADDR4; // Let's start with 1.0.0.0 address
  57. const uint8_t hwaddr_len = 20; // Not a real field
  58. char hwaddr[hwaddr_len];
  59. const uint8_t client_id_len = 128;
  60. char client_id[client_id_len];
  61. uint32_t valid_lft = 1000; // We can use the same value for all leases
  62. uint32_t recycle_time = 0; // Not supported in any foresable future,
  63. // so keep this as 0
  64. string cltt = "now"; // Timestamp
  65. uint32_t pool_id = 0; // Let's use pools 0-99
  66. bool fixed = false;
  67. string hostname("foo"); // Will generate it dynamically
  68. bool fqdn_fwd = true; // Let's pretend to do AAAA update
  69. bool fqdn_rev = true; // Let's pretend to do PTR update
  70. printf("CREATE: ");
  71. for (uint8_t i = 0; i < hwaddr_len; i++) {
  72. hwaddr[i] = 65 + i;
  73. }
  74. hwaddr[19] = 0; // workaround
  75. for (uint8_t i = 0; i < client_id_len; i++) {
  76. client_id[i] = 33 + i;
  77. }
  78. client_id[6] = 'X'; // there's apostrophe here. It would confuse
  79. // query formatting, let's get rid of it
  80. client_id[127] = 0; // workaround
  81. for (uint32_t i = 0; i < num_; i++) {
  82. stringstream cltt;
  83. cltt << "2012-07-11 15:43:" << (i % 60);
  84. addr++;
  85. char* errorMsg = NULL;
  86. // the first address is 1.0.0.0.
  87. char query[2000];
  88. /// @todo: Encode HWADDR and CLIENT-ID properly
  89. sprintf(query, "INSERT INTO lease4(addr,hwaddr,client_id,"
  90. "valid_lft,recycle_time,cltt,pool_id,fixed,hostname,"
  91. "fqdn_fwd,fqdn_rev) VALUES(%u,'%s','%s',%d,%d,'%s',%d,'%s','%s','%s','%s');",
  92. addr, hwaddr, client_id, valid_lft, recycle_time,
  93. cltt.str().c_str(), pool_id, (fixed?"true":"false"),
  94. hostname.c_str(), (fqdn_fwd?"true":"false"), (fqdn_rev?"true":"false"));
  95. // printf("QUERY=[%s]\n", query);
  96. int result = sqlite3_exec(db_, query, NULL, 0, &errorMsg);
  97. if (result != SQLITE_OK) {
  98. stringstream tmp;
  99. tmp << "INSERT error:" << errorMsg;
  100. failure(tmp.str().c_str());
  101. } else {
  102. if (verbose_) {
  103. printf(".");
  104. }
  105. };
  106. }
  107. printf("\n");
  108. }
  109. static int search_callback(void *counter, int /*argc*/, char** /*argv*/,
  110. char** /*azColName*/){
  111. int* cnt = static_cast<int*>(counter);
  112. (*cnt)++;
  113. #if 0
  114. int i;
  115. for(i=0; i<argc; i++){
  116. printf("%s=%s ", azColName[i], argv[i] ? argv[i] : "NULL");
  117. }
  118. printf("\n");
  119. #endif
  120. return 0;
  121. }
  122. void SQLite_uBenchmark::searchLease4Test() {
  123. if (!db_) {
  124. throw "SQLite connection is closed.";
  125. }
  126. printf("RETRIEVE: ");
  127. for (uint32_t i = 0; i < num_; i++) {
  128. uint32_t x = BASE_ADDR4 + random() % int(num_ / hitratio_);
  129. char* errorMsg = NULL;
  130. int cnt = 0;
  131. char query[2000];
  132. sprintf(query, "SELECT lease_id,addr,hwaddr,client_id,valid_lft,"
  133. "cltt,pool_id,fixed,hostname,fqdn_fwd,fqdn_rev "
  134. "FROM lease4 where addr=%d", x);
  135. int result = sqlite3_exec(db_, query, search_callback, &cnt, &errorMsg);
  136. if (result != SQLITE_OK) {
  137. stringstream tmp;
  138. tmp << "SELECT failed: " << errorMsg;
  139. failure(tmp.str().c_str());
  140. }
  141. if (cnt) {
  142. if (verbose_) {
  143. printf(".");
  144. }
  145. } else {
  146. if (verbose_) {
  147. printf("X");
  148. }
  149. }
  150. }
  151. printf("\n");
  152. }
  153. void SQLite_uBenchmark::updateLease4Test() {
  154. if (!db_) {
  155. throw "SQLite connection is closed.";
  156. }
  157. printf("UPDATE: ");
  158. for (uint32_t i = 0; i < num_; i++) {
  159. uint32_t x = BASE_ADDR4 + random() % num_;
  160. char* errorMsg = NULL;
  161. char query[2000];
  162. sprintf(query, "UPDATE lease4 SET valid_lft=1002, cltt='now' WHERE addr=%d", x);
  163. int result = sqlite3_exec(db_, query, NULL /* no callback here*/, 0, &errorMsg);
  164. if (result != SQLITE_OK) {
  165. stringstream tmp;
  166. tmp << "UPDATE error:" << errorMsg;
  167. failure(tmp.str().c_str());
  168. }
  169. if (verbose_) {
  170. printf(".");
  171. }
  172. }
  173. printf("\n");
  174. }
  175. void SQLite_uBenchmark::deleteLease4Test() {
  176. if (!db_) {
  177. throw "SQLite connection is closed.";
  178. }
  179. printf("DELETE: ");
  180. for (uint32_t i = 0; i < num_; i++) {
  181. uint32_t x = BASE_ADDR4 + i;
  182. char* errorMsg = NULL;
  183. char query[2000];
  184. sprintf(query, "DELETE FROM lease4 WHERE addr=%d", x);
  185. int result = sqlite3_exec(db_, query, NULL /* no callback here*/, 0, &errorMsg);
  186. if (result != SQLITE_OK) {
  187. stringstream tmp;
  188. tmp << "DELETE error:" << errorMsg;
  189. failure(tmp.str().c_str());
  190. }
  191. if (verbose_) {
  192. printf(".");
  193. }
  194. }
  195. printf("\n");
  196. }
  197. void SQLite_uBenchmark::printInfo() {
  198. cout << "SQLite version is " << sqlite3_libversion()
  199. << "sourceid version is " << sqlite3_sourceid() << endl;
  200. }
  201. int main(int argc, char* const argv[]) {
  202. const char* filename = "sqlite.db";
  203. uint32_t num = 100;
  204. bool sync = true;
  205. bool verbose = true;
  206. SQLite_uBenchmark bench(filename, num, sync, verbose);
  207. bench.parseCmdline(argc, argv);
  208. int result = bench.run();
  209. return (result);
  210. }