summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorgabor@google.com <gabor@google.com@62dab493-f737-651d-591e-8d6aee1b9529>2011-08-16 01:21:01 +0000
committergabor@google.com <gabor@google.com@62dab493-f737-651d-591e-8d6aee1b9529>2011-08-16 01:21:01 +0000
commitab323f7e1ec53749653967e7d6a2fa1c922334f2 (patch)
treebc6b5343550f7fad533dabd36452544d8bfb5a14
parenta05525d13beea3ae56d979fa5fffa9de3652db61 (diff)
downloadleveldb-ab323f7e1ec53749653967e7d6a2fa1c922334f2.tar.gz
Bugfixes for iterator and documentation.
- Fix bug in Iterator::Prev where it would return the wrong key. Fixes issues 29 and 30. - Added a tweak to testharness to allow running just some tests. - Fixing two minor documentation errors based on issues 28 and 25. - Cleanup; fix namespaces of export-to-C code. Also fix one "const char*" vs "char*" mismatch. git-svn-id: https://leveldb.googlecode.com/svn/trunk@48 62dab493-f737-651d-591e-8d6aee1b9529
-rw-r--r--db/c.cc25
-rw-r--r--db/db_iter.cc3
-rw-r--r--db/db_test.cc15
-rw-r--r--doc/index.html10
-rw-r--r--util/testharness.cc12
-rw-r--r--util/testharness.h11
6 files changed, 65 insertions, 11 deletions
diff --git a/db/c.cc b/db/c.cc
index ee8a472..366dd2d 100644
--- a/db/c.cc
+++ b/db/c.cc
@@ -15,7 +15,26 @@
#include "leveldb/status.h"
#include "leveldb/write_batch.h"
-namespace leveldb {
+using leveldb::Cache;
+using leveldb::Comparator;
+using leveldb::CompressionType;
+using leveldb::DB;
+using leveldb::Env;
+using leveldb::FileLock;
+using leveldb::Iterator;
+using leveldb::Logger;
+using leveldb::NewLRUCache;
+using leveldb::Options;
+using leveldb::RandomAccessFile;
+using leveldb::Range;
+using leveldb::ReadOptions;
+using leveldb::SequentialFile;
+using leveldb::Slice;
+using leveldb::Snapshot;
+using leveldb::Status;
+using leveldb::WritableFile;
+using leveldb::WriteBatch;
+using leveldb::WriteOptions;
extern "C" {
@@ -172,7 +191,7 @@ void leveldb_release_snapshot(
delete snapshot;
}
-const char* leveldb_property_value(
+char* leveldb_property_value(
leveldb_t* db,
const char* propname) {
std::string tmp;
@@ -449,5 +468,3 @@ void leveldb_env_destroy(leveldb_env_t* env) {
}
} // end extern "C"
-
-}
diff --git a/db/db_iter.cc b/db/db_iter.cc
index 0be18ff..8849f92 100644
--- a/db/db_iter.cc
+++ b/db/db_iter.cc
@@ -216,7 +216,6 @@ void DBIter::FindPrevUserEntry() {
ValueType value_type = kTypeDeletion;
if (iter_->Valid()) {
- SaveKey(ExtractUserKey(iter_->key()), &saved_key_);
do {
ParsedInternalKey ikey;
if (ParseKey(&ikey) && ikey.sequence <= sequence_) {
@@ -227,6 +226,7 @@ void DBIter::FindPrevUserEntry() {
}
value_type = ikey.type;
if (value_type == kTypeDeletion) {
+ saved_key_.clear();
ClearSavedValue();
} else {
Slice raw_value = iter_->value();
@@ -234,6 +234,7 @@ void DBIter::FindPrevUserEntry() {
std::string empty;
swap(empty, saved_value_);
}
+ SaveKey(ExtractUserKey(iter_->key()), &saved_key_);
saved_value_.assign(raw_value.data(), raw_value.size());
}
}
diff --git a/db/db_test.cc b/db/db_test.cc
index 22fa70c..14eb44d 100644
--- a/db/db_test.cc
+++ b/db/db_test.cc
@@ -519,6 +519,21 @@ TEST(DBTest, IterSmallAndLargeMix) {
delete iter;
}
+TEST(DBTest, IterMultiWithDelete) {
+ ASSERT_OK(Put("a", "va"));
+ ASSERT_OK(Put("b", "vb"));
+ ASSERT_OK(Put("c", "vc"));
+ ASSERT_OK(Delete("b"));
+ ASSERT_EQ("NOT_FOUND", Get("b"));
+
+ Iterator* iter = db_->NewIterator(ReadOptions());
+ iter->Seek("c");
+ ASSERT_EQ(IterStatus(iter), "c->vc");
+ iter->Prev();
+ ASSERT_EQ(IterStatus(iter), "a->va");
+ delete iter;
+}
+
TEST(DBTest, Recover) {
ASSERT_OK(Put("foo", "v1"));
ASSERT_OK(Put("baz", "v5"));
diff --git a/doc/index.html b/doc/index.html
index 58442e8..8d03c45 100644
--- a/doc/index.html
+++ b/doc/index.html
@@ -23,7 +23,7 @@ creating it if necessary:
<p>
<pre>
#include &lt;assert&gt;
- #include "leveldb/include/db.h"
+ #include "leveldb/db.h"
leveldb::DB* db;
leveldb::Options options;
@@ -78,7 +78,7 @@ Such problems can be avoided by using the <code>WriteBatch</code> class to
atomically apply a set of updates:
<p>
<pre>
- #include "leveldb/include/write_batch.h"
+ #include "leveldb/write_batch.h"
...
std::string value;
leveldb::Status s = db-&gt;Get(leveldb::ReadOptions(), key1, &amp;value);
@@ -296,7 +296,7 @@ subclass of <code>leveldb::Comparator</code> that expresses these rules:
}
// Ignore the following methods for now:
- const char* Name() { return "TwoPartComparator"; }
+ const char* Name() const { return "TwoPartComparator"; }
void FindShortestSeparator(std::string*, const leveldb::Slice&amp;) const { }
void FindShortSuccessor(std::string*) const { }
};
@@ -333,7 +333,7 @@ version numbers found in the keys to decide how to interpret them.
<h1>Performance</h1>
<p>
Performance can be tuned by changing the default values of the
-types defined in <code>leveldb/include/options.h</code>.
+types defined in <code>include/leveldb/options.h</code>.
<p>
<h2>Block size</h2>
@@ -371,7 +371,7 @@ filesystem and each file stores a sequence of compressed blocks. If
uncompressed block contents.
<p>
<pre>
- #include "leveldb/include/cache.h"
+ #include "leveldb/cache.h"
leveldb::Options options;
options.cache = leveldb::NewLRUCache(100 * 1048576); // 100MB cache
diff --git a/util/testharness.cc b/util/testharness.cc
index b686ac3..6f42700 100644
--- a/util/testharness.cc
+++ b/util/testharness.cc
@@ -4,6 +4,8 @@
#include "util/testharness.h"
+#include <string>
+#include <stdlib.h>
#include <sys/stat.h>
#include <sys/types.h>
@@ -32,10 +34,20 @@ bool RegisterTest(const char* base, const char* name, void (*func)()) {
}
int RunAllTests() {
+ const char* matcher = getenv("LEVELDB_TESTS");
+
int num = 0;
if (tests != NULL) {
for (int i = 0; i < tests->size(); i++) {
const Test& t = (*tests)[i];
+ if (matcher != NULL) {
+ std::string name = t.base;
+ name.push_back('.');
+ name.append(t.name);
+ if (strstr(name.c_str(), matcher) == NULL) {
+ continue;
+ }
+ }
fprintf(stderr, "==== Test %s.%s\n", t.base, t.name);
(*t.func)();
++num;
diff --git a/util/testharness.h b/util/testharness.h
index 13ab914..6f1a9c3 100644
--- a/util/testharness.h
+++ b/util/testharness.h
@@ -15,7 +15,16 @@
namespace leveldb {
namespace test {
-// Run all tests registered by the TEST() macro.
+// Run some of the tests registered by the TEST() macro. If the
+// environment variable "LEVELDB_TESTS" is not set, runs all tests.
+// Otherwise, runs only the tests whose name contains the value of
+// "LEVELDB_TESTS" as a substring. E.g., suppose the tests are:
+// TEST(Foo, Hello) { ... }
+// TEST(Foo, World) { ... }
+// LEVELDB_TESTS=Hello will run the first test
+// LEVELDB_TESTS=o will run both tests
+// LEVELDB_TESTS=Junk will run no tests
+//
// Returns 0 if all tests pass.
// Dies or returns a non-zero value if some test fails.
extern int RunAllTests();