More for prev commit

Use the latest meta page
vmware
Howard Chu 12 years ago
parent e74d70e88e
commit ed86a086f7
  1. 72
      libraries/liblmdb/mdb.c

@ -2416,47 +2416,61 @@ mdb_env_read_header(MDB_env *env, MDB_meta *meta)
MDB_pagebuf pbuf; MDB_pagebuf pbuf;
MDB_page *p; MDB_page *p;
MDB_meta *m; MDB_meta *m;
int rc, err; int i, rc, err;
/* We don't know the page size yet, so use a minimum value. /* We don't know the page size yet, so use a minimum value.
* Read both meta pages so we can use the latest one.
*/ */
for (i=0; i<2; i++) {
#ifdef _WIN32 #ifdef _WIN32
if (!ReadFile(env->me_fd, &pbuf, MDB_PAGESIZE, (DWORD *)&rc, NULL) || rc == 0) if (!ReadFile(env->me_fd, &pbuf, MDB_PAGESIZE, (DWORD *)&rc, NULL) || rc == 0)
#else #else
if ((rc = read(env->me_fd, &pbuf, MDB_PAGESIZE)) == 0) if ((rc = read(env->me_fd, &pbuf, MDB_PAGESIZE)) == 0)
#endif #endif
{ {
return ENOENT; return ENOENT;
} }
else if (rc != MDB_PAGESIZE) { else if (rc != MDB_PAGESIZE) {
err = ErrCode(); err = ErrCode();
if (rc > 0) if (rc > 0)
err = MDB_INVALID; err = MDB_INVALID;
DPRINTF("read: %s", strerror(err)); DPRINTF("read: %s", strerror(err));
return err; return err;
} }
p = (MDB_page *)&pbuf; p = (MDB_page *)&pbuf;
if (!F_ISSET(p->mp_flags, P_META)) { if (!F_ISSET(p->mp_flags, P_META)) {
DPRINTF("page %zu not a meta page", p->mp_pgno); DPRINTF("page %zu not a meta page", p->mp_pgno);
return MDB_INVALID; return MDB_INVALID;
} }
m = METADATA(p); m = METADATA(p);
if (m->mm_magic != MDB_MAGIC) { if (m->mm_magic != MDB_MAGIC) {
DPUTS("meta has invalid magic"); DPUTS("meta has invalid magic");
return MDB_INVALID; return MDB_INVALID;
} }
if (m->mm_version != MDB_VERSION) { if (m->mm_version != MDB_VERSION) {
DPRINTF("database is version %u, expected version %u", DPRINTF("database is version %u, expected version %u",
m->mm_version, MDB_VERSION); m->mm_version, MDB_VERSION);
return MDB_VERSION_MISMATCH; return MDB_VERSION_MISMATCH;
} }
memcpy(meta, m, sizeof(*m)); if (i) {
if (m->mm_txnid > meta->mm_txnid)
memcpy(meta, m, sizeof(*m));
} else {
memcpy(meta, m, sizeof(*m));
#ifdef _WIN32
if (SetFilePointer(env->me_fd, meta->mm_psize, NULL, FILE_BEGIN) != meta->mm_psize)
#else
if (lseek(env->me_fd, meta->mm_psize, SEEK_SET) != meta->mm_psize)
#endif
return ErrCode();
}
}
return 0; return 0;
} }

Loading…
Cancel
Save