⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 db_vrfy.c

📁 这是linux下运行的mysql软件包,可用于linux 下安装 php + mysql + apach 的网络配置
💻 C
📖 第 1 页 / 共 5 页
字号:
	switch (pip->type) {	case P_IBTREE:	case P_LDUP:		if (!LF_ISSET(ST_DUPSORT)) {			EPRINT((dbenv,	    "Page %lu: sorted duplicate set in unsorted-dup database",			    (u_long)pgno));			isbad = 1;		}		break;	case P_IRECNO:	case P_LRECNO:		if (LF_ISSET(ST_DUPSORT)) {			EPRINT((dbenv,	    "Page %lu: unsorted duplicate set in sorted-dup database",			    (u_long)pgno));			isbad = 1;		}		break;	default:		/*		 * If the page is entirely zeroed, its pip->type will be a lie		 * (we assumed it was a hash page, as they're allowed to be		 * zeroed);  handle this case specially.		 */		if (F_ISSET(pip, VRFY_IS_ALLZEROES))			ZEROPG_ERR_PRINT(dbenv, pgno, "duplicate page");		else			EPRINT((dbenv,		    "Page %lu: duplicate page of inappropriate type %lu",			    (u_long)pgno, (u_long)pip->type));		isbad = 1;		break;	}	if ((ret = __db_vrfy_putpageinfo(dbenv, vdp, pip)) != 0)		return (ret);	return (isbad == 1 ? DB_VERIFY_BAD : 0);}/* * __db_salvage_duptree -- *	Attempt to salvage a given duplicate tree, given its alleged root. * *	The key that corresponds to this dup set has been passed to us *	in DBT *key.  Because data items follow keys, though, it has been *	printed once already. * *	The basic idea here is that pgno ought to be a P_LDUP, a P_LRECNO, a *	P_IBTREE, or a P_IRECNO.  If it's an internal page, use the verifier *	functions to make sure it's safe;  if it's not, we simply bail and the *	data will have to be printed with no key later on.  if it is safe, *	recurse on each of its children. * *	Whether or not it's safe, if it's a leaf page, __bam_salvage it. * *	At all times, use the DB hanging off vdp to mark and check what we've *	done, so each page gets printed exactly once and we don't get caught *	in any cycles. * * PUBLIC: int __db_salvage_duptree __P((DB *, VRFY_DBINFO *, db_pgno_t, * PUBLIC:     DBT *, void *, int (*)(void *, const void *), u_int32_t)); */int__db_salvage_duptree(dbp, vdp, pgno, key, handle, callback, flags)	DB *dbp;	VRFY_DBINFO *vdp;	db_pgno_t pgno;	DBT *key;	void *handle;	int (*callback) __P((void *, const void *));	u_int32_t flags;{	DB_MPOOLFILE *mpf;	PAGE *h;	int ret, t_ret;	mpf = dbp->mpf;	if (pgno == PGNO_INVALID || !IS_VALID_PGNO(pgno))		return (DB_VERIFY_BAD);	/* We have a plausible page.  Try it. */	if ((ret = mpf->get(mpf, &pgno, 0, &h)) != 0)		return (ret);	switch (TYPE(h)) {	case P_IBTREE:	case P_IRECNO:		if ((ret = __db_vrfy_common(dbp, vdp, h, pgno, flags)) != 0)			goto err;		if ((ret = __bam_vrfy(dbp,		    vdp, h, pgno, flags | DB_NOORDERCHK)) != 0 ||		    (ret = __db_salvage_markdone(vdp, pgno)) != 0)			goto err;		/*		 * We have a known-healthy internal page.  Walk it.		 */		if ((ret = __bam_salvage_walkdupint(dbp, vdp, h, key,		    handle, callback, flags)) != 0)			goto err;		break;	case P_LRECNO:	case P_LDUP:		if ((ret = __bam_salvage(dbp,		    vdp, pgno, TYPE(h), h, handle, callback, key, flags)) != 0)			goto err;		break;	default:		ret = DB_VERIFY_BAD;		goto err;		/* NOTREACHED */	}err:	if ((t_ret = mpf->put(mpf, h, 0)) != 0 && ret == 0)		ret = t_ret;	return (ret);}/* * __db_salvage_subdbs -- *	Check and see if this database has subdbs;  if so, try to salvage *	them independently. */static int__db_salvage_subdbs(dbp, vdp, handle, callback, flags, hassubsp)	DB *dbp;	VRFY_DBINFO *vdp;	void *handle;	int (*callback) __P((void *, const void *));	u_int32_t flags;	int *hassubsp;{	BTMETA *btmeta;	DB *pgset;	DBC *pgsc;	DB_MPOOLFILE *mpf;	PAGE *h;	db_pgno_t p, meta_pgno;	int ret, err_ret;	pgset = NULL;	pgsc = NULL;	mpf = dbp->mpf;	err_ret = 0;	meta_pgno = PGNO_BASE_MD;	if ((ret = mpf->get(mpf, &meta_pgno, 0, &h)) != 0)		return (ret);	if (TYPE(h) == P_BTREEMETA)		btmeta = (BTMETA *)h;	else {		/* Not a btree metadata, ergo no subdbs, so just return. */		ret = 0;		goto err;	}	/* If it's not a safe page, bail on the attempt. */	if ((ret = __db_vrfy_common(dbp, vdp, h, PGNO_BASE_MD, flags)) != 0 ||	   (ret = __bam_vrfy_meta(dbp, vdp, btmeta, PGNO_BASE_MD, flags)) != 0)		goto err;	if (!F_ISSET(&btmeta->dbmeta, BTM_SUBDB)) {		/* No subdbs, just return. */		ret = 0;		goto err;	}	/* We think we've got subdbs.  Mark it so. */	*hassubsp = 1;	if ((ret = mpf->put(mpf, h, 0)) != 0)		return (ret);	/*	 * We have subdbs.  Try to crack them.	 *	 * To do so, get a set of leaf pages in the master	 * database, and then walk each of the valid ones, salvaging	 * subdbs as we go.  If any prove invalid, just drop them;  we'll	 * pick them up on a later pass.	 */	if ((ret = __db_vrfy_pgset(dbp->dbenv, dbp->pgsize, &pgset)) != 0)		return (ret);	if ((ret =	    __db_meta2pgset(dbp, vdp, PGNO_BASE_MD, flags, pgset)) != 0)		goto err;	if ((ret = pgset->cursor(pgset, NULL, &pgsc, 0)) != 0)		goto err;	while ((ret = __db_vrfy_pgset_next(pgsc, &p)) == 0) {		if ((ret = mpf->get(mpf, &p, 0, &h)) != 0) {			err_ret = ret;			continue;		}		if ((ret = __db_vrfy_common(dbp, vdp, h, p, flags)) != 0 ||		    (ret = __bam_vrfy(dbp,		    vdp, h, p, flags | DB_NOORDERCHK)) != 0)			goto nextpg;		if (TYPE(h) != P_LBTREE)			goto nextpg;		else if ((ret = __db_salvage_subdbpg(		    dbp, vdp, h, handle, callback, flags)) != 0)			err_ret = ret;nextpg:		if ((ret = mpf->put(mpf, h, 0)) != 0)			err_ret = ret;	}	if (ret != DB_NOTFOUND)		goto err;	if ((ret = pgsc->c_close(pgsc)) != 0)		goto err;	ret = pgset->close(pgset, 0);	return ((ret == 0 && err_ret != 0) ? err_ret : ret);	/* NOTREACHED */err:	if (pgsc != NULL)		(void)pgsc->c_close(pgsc);	if (pgset != NULL)		(void)pgset->close(pgset, 0);	(void)mpf->put(mpf, h, 0);	return (ret);}/* * __db_salvage_subdbpg -- *	Given a known-good leaf page in the master database, salvage all *	leaf pages corresponding to each subdb. */static int__db_salvage_subdbpg(dbp, vdp, master, handle, callback, flags)	DB *dbp;	VRFY_DBINFO *vdp;	PAGE *master;	void *handle;	int (*callback) __P((void *, const void *));	u_int32_t flags;{	BKEYDATA *bkkey, *bkdata;	BOVERFLOW *bo;	DB *pgset;	DBC *pgsc;	DBT key;	DB_ENV *dbenv;	DB_MPOOLFILE *mpf;	PAGE *subpg;	db_indx_t i;	db_pgno_t meta_pgno, p;	int ret, err_ret, t_ret;	char *subdbname;	dbenv = dbp->dbenv;	mpf = dbp->mpf;	ret = err_ret = 0;	subdbname = NULL;	if ((ret = __db_vrfy_pgset(dbenv, dbp->pgsize, &pgset)) != 0)		return (ret);	/*	 * For each entry, get and salvage the set of pages	 * corresponding to that entry.	 */	for (i = 0; i < NUM_ENT(master); i += P_INDX) {		bkkey = GET_BKEYDATA(dbp, master, i);		bkdata = GET_BKEYDATA(dbp, master, i + O_INDX);		/* Get the subdatabase name. */		if (B_TYPE(bkkey->type) == B_OVERFLOW) {			/*			 * We can, in principle anyway, have a subdb			 * name so long it overflows.  Ick.			 */			bo = (BOVERFLOW *)bkkey;			if ((ret = __db_safe_goff(dbp, vdp, bo->pgno, &key,			    (void **)&subdbname, flags)) != 0) {				err_ret = DB_VERIFY_BAD;				continue;			}			/* Nul-terminate it. */			if ((ret = __os_realloc(dbenv,			    key.size + 1, &subdbname)) != 0)				goto err;			subdbname[key.size] = '\0';		} else if (B_TYPE(bkkey->type == B_KEYDATA)) {			if ((ret = __os_realloc(dbenv,			    bkkey->len + 1, &subdbname)) != 0)				goto err;			memcpy(subdbname, bkkey->data, bkkey->len);			subdbname[bkkey->len] = '\0';		}		/* Get the corresponding pgno. */		if (bkdata->len != sizeof(db_pgno_t)) {			err_ret = DB_VERIFY_BAD;			continue;		}		memcpy(&meta_pgno, bkdata->data, sizeof(db_pgno_t));		/*		 * Subdatabase meta pgnos are stored in network byte		 * order for cross-endian compatibility.  Swap if appropriate.		 */		DB_NTOHL(&meta_pgno);		/* If we can't get the subdb meta page, just skip the subdb. */		if (!IS_VALID_PGNO(meta_pgno) ||		    (ret = mpf->get(mpf, &meta_pgno, 0, &subpg)) != 0) {			err_ret = ret;			continue;		}		/*		 * Verify the subdatabase meta page.  This has two functions.		 * First, if it's bad, we have no choice but to skip the subdb		 * and let the pages just get printed on a later pass.  Second,		 * the access-method-specific meta verification routines record		 * the various state info (such as the presence of dups)		 * that we need for __db_prheader().		 */		if ((ret =		    __db_vrfy_common(dbp, vdp, subpg, meta_pgno, flags)) != 0) {			err_ret = ret;			(void)mpf->put(mpf, subpg, 0);			continue;		}		switch (TYPE(subpg)) {		case P_BTREEMETA:			if ((ret = __bam_vrfy_meta(dbp,			    vdp, (BTMETA *)subpg, meta_pgno, flags)) != 0) {				err_ret = ret;				(void)mpf->put(mpf, subpg, 0);				continue;			}			break;		case P_HASHMETA:			if ((ret = __ham_vrfy_meta(dbp,			    vdp, (HMETA *)subpg, meta_pgno, flags)) != 0) {				err_ret = ret;				(void)mpf->put(mpf, subpg, 0);				continue;			}			break;		default:			/* This isn't an appropriate page;  skip this subdb. */			err_ret = DB_VERIFY_BAD;			continue;			/* NOTREACHED */		}		if ((ret = mpf->put(mpf, subpg, 0)) != 0) {			err_ret = ret;			continue;		}		/* Print a subdatabase header. */		if ((ret = __db_prheader(dbp,		    subdbname, 0, 0, handle, callback, vdp, meta_pgno)) != 0)			goto err;		if ((ret = __db_meta2pgset(dbp, vdp, meta_pgno,		    flags, pgset)) != 0) {			err_ret = ret;			continue;		}		if ((ret = pgset->cursor(pgset, NULL, &pgsc, 0)) != 0)			goto err;		while ((ret = __db_vrfy_pgset_next(pgsc, &p)) == 0) {			if ((ret = mpf->get(mpf, &p, 0, &subpg)) != 0) {				err_ret = ret;				continue;			}			if ((ret = __db_salvage(dbp, vdp, p, subpg,			    handle, callback, flags)) != 0)				err_ret = ret;			if ((ret = mpf->put(mpf, subpg, 0)) != 0)				err_ret = ret;		}		if (ret != DB_NOTFOUND)			goto err;		if ((ret = pgsc->c_close(pgsc)) != 0)			goto err;		if ((ret = __db_prfooter(handle, callback)) != 0)			goto err;	}err:	if (subdbname)		__os_free(dbenv, subdbname);	if ((t_ret = pgset->close(pgset, 0)) != 0)		ret = t_ret;	if ((t_ret = __db_salvage_markdone(vdp, PGNO(master))) != 0)		return (t_ret);	return ((err_ret != 0) ? err_ret : ret);}/* * __db_meta2pgset -- *	Given a known-safe meta page number, return the set of pages *	corresponding to the database it represents.  Return DB_VERIFY_BAD if *	it's not a suitable meta page or is invalid. */static int__db_meta2pgset(dbp, vdp, pgno, flags, pgset)	DB *dbp;	VRFY_DBINFO *vdp;	db_pgno_t pgno;	u_int32_t flags;	DB *pgset;{	DB_MPOOLFILE *mpf;	PAGE *h;	int ret, t_ret;	mpf = dbp->mpf;	if ((ret = mpf->get(mpf, &pgno, 0, &h)) != 0)		return (ret);	switch (TYPE(h)) {	case P_BTREEMETA:		ret = __bam_meta2pgset(dbp, vdp, (BTMETA *)h, flags, pgset);		break;	case P_HASHMETA:		ret = __ham_meta2pgset(dbp, vdp, (HMETA *)h, flags, pgset);		break;	default:		ret = DB_VERIFY_BAD;		break;	}	if ((t_ret = mpf->put(mpf, h, 0)) != 0)		return (t_ret);	return (ret);}/* * __db_guesspgsize -- *	Try to guess what the pagesize is if the one on the meta page *	and the one in the db are invalid. */static int__db_guesspgsize(dbenv, fhp)	DB_ENV *dbenv;	DB_FH *fhp;{	db_pgno_t i;	size_t nr;	u_int32_t guess;	u_int8_t type;	for (guess = DB_MAX_PGSIZE; guess >= DB_MIN_PGSIZE; guess >>= 1) {		/*		 * We try to read three pages ahead after the first one		 * and make sure we have plausible types for all of them.		 * If the seeks fail, continue with a smaller size;		 * we're probably just looking past the end of the database.		 * If they succeed and the types are reasonable, also continue		 * with a size smaller;  we may be looking at pages N,		 * 2N, and 3N for some N > 1.		 *		 * As soon as we hit an invalid type, we stop and return		 * our previous guess; that last one was probably the page size.		 */		for (i = 1; i <= 3; i++) {			if (__os_seek(dbenv, fhp, guess,			    i, SSZ(DBMETA, type), 0, DB_OS_SEEK_SET) != 0)				break;			if (__os_read(dbenv,			    fhp, &type, 1, &nr) != 0 || nr == 0)				break;			if (type == P_INVALID || type >= P_PAGETYPE_MAX)				return (guess << 1);		}	}	/*	 * If we're just totally confused--the corruption takes up most of the	 * beginning pages of the database--go with the default size.	 */	return (DB_DEF_IOSIZE);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -