Forum Stats

  • 3,825,929 Users
  • 2,260,581 Discussions
  • 7,896,738 Comments

Discussions

Oracle Berkeley DB "heap" access method misscounts records in "db.stat()"

Jesús Cea
Jesús Cea Member Posts: 56 Blue Ribbon
edited Dec 6, 2020 3:02AM in Berkeley DB

I am working in supporting HEAP access method in "berkeleydb" bindings for Python and I have found a bug affecting BDB 6.2 and 18.1. BDB 5.3 works fine.

Steps to reproduce:

  1. Create a HEAP database.
  2. Add a record.
  3. Delete that record.
  4. Do a "stat()" on that database and observe field "nrecs" (number of record in the database).

If you use "DB_FAST_STAT", a Zero is returned. That value is correct. If if you request a full database scan, ONE is returned. That value is incorrect. Moreover, that faulty result will be stored in the cache, so future "stat" with "DB_FAST_STAT" will be wrong.

Scanning the database with a cursor will show that the database is empty, as it should.

For some reason, a "stat" scanning a HEAP database will wrongly count deleted records.

The test sourcecode is: (Python using an unreleased version of "berkeleydb" bindings)

"""

self.env = db.DBEnv()

self.env.open(self.homeDir, db.DB_CREATE | db.DB_INIT_MPOOL |

                                   db.DB_INIT_LOG | db.DB_INIT_TXN)

self.db = db.DB(self.env)

self.db.open(flags=db.DB_CREATE, dbtype=db.DB_HEAP)

key = self.db.append(data=b'value')

self.db.delete(key)

print(self.db.stat(db.DB_FAST_STAT))

print(self.db.stat())

print(self.db.stat(db.DB_FAST_STAT))

"""

The values printed in my environment are: (notice the wrong number in "nrecs"):

"""

{'magic': 476546, 'metaflags': 0, 'ext_files': 0, 'nrecs': 0, 'pagecnt': 3, 'pagesize': 8192, 'nregions': 1, 'regionsize': 32664, 'version': 2}

{'magic': 476546, 'metaflags': 0, 'ext_files': 0, 'nrecs': 1, 'pagecnt': 3, 'pagesize': 8192, 'nregions': 1, 'regionsize': 32664, 'version': 2}

{'magic': 476546, 'metaflags': 0, 'ext_files': 0, 'nrecs': 1, 'pagecnt': 3, 'pagesize': 8192, 'nregions': 1, 'regionsize': 32664, 'version': 2}

"""

Answers

  • Jesús Cea
    Jesús Cea Member Posts: 56 Blue Ribbon

    More checks. "DB_FAST_STAT" doesn't give a correct count either. Storing a record and doing "db.stat(db.DB_FAST_STAT)" gives a count of zero for 'nrecs' field. BDB 5.3 works fine. BDB 6.2 and 18.1 gives back incorrect stats.