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

📄 log_read.c

📁 在Linux内核从2.4升级到2.6时需要升级的软件包
💻 C
📖 第 1 页 / 共 2 页
字号:
/* *   Copyright (c) International Business Machines Corp., 2000-2002 * *   This program is free software;  you can redistribute it and/or modify *   it under the terms of the GNU General Public License as published by *   the Free Software Foundation; either version 2 of the License, or *   (at your option) any later version. * *   This program is distributed in the hope that it will be useful, *   but WITHOUT ANY WARRANTY;  without even the implied warranty of *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See *   the GNU General Public License for more details. * *   You should have received a copy of the GNU General Public License *   along with this program;  if not, write to the Free Software *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */#include <config.h>#include <time.h>#include <stdio.h>#include <stdlib.h>#include <memory.h>#include <string.h>#include <errno.h>#include "jfs_types.h"#include "jfs_endian.h"#include "jfs_filsys.h"#include "jfs_superblock.h"#include "jfs_dinode.h"#include "jfs_dtree.h"#include "jfs_xtree.h"#include "jfs_logmgr.h"#include "jfs_dmap.h"#include "jfs_imap.h"#include "logredo.h"#include "devices.h"#include "debug.h"#include "fsck_message.h"		/* for fsck message logging facility */ /* + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +  *  *    R E M E M B E R    M E M O R Y    A L L O C    F A I L U R E  *  */extern int32_t Insuff_memory_for_maps;extern char *available_stg_addr;extern int32_t available_stg_bytes;extern char *bmap_stg_addr;extern int32_t bmap_stg_bytes; /* + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +  *  *   L O C A L   M A C R O    D E F I N I T I O N S  *  */#define BTOLOGPN(x)  ((unsigned)(x) >> L2LOGPSIZE)#define LOGPNTOB(x)  ((x)<<L2LOGPSIZE)#define min(A,B) ((A) < (B) ? (A) : (B)) /* + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +  *  *    S T U F F    F O R    T H E    L O G  *  *       externals defined in logredo.c  */int32_t loglastp;		/* last page of log read       */int32_t lognumread;		/* number of log pages read    *//* *      open file system aggregate/lv array *     Defined in logredo.c */extern struct vopen vopen[];	/* (88) *//* *      log page buffer cache * * log has its own 4 page buffer pool. *   externals defined in logredo.c */int nextrep;			/* next log buffer pool slot to replace */int logptr[4];			/* log pages currently held in logp */struct logpage logp[4];		/* log page buffer pool  *//* * external references */extern int logError(int, int);/* * forward references */int findEndOfLog(void);int pageVal(int, int *, int *);int getLogpage(int);int setLogpage(int32_t pno, int32_t *, int32_t *, int32_t);int logRead(int32_t, struct lrd *, char *);int moveWords(int32_t, int32_t *, int32_t *, int32_t *);/* * NAME:        findEndOfLog() * * FUNCTION:    Returns the address of the end of the last record in the log. *              (i.e. the address of the byte following its descriptor). * *        Note: At the first release, log page is not written in a ping pong *              manner, so the logend is the binary search result * *              The end of the log is found by finding the page with the *              highest page number and for which h.eor == t.eor and *              h.eor > 8 (i.e. a record ends on the page). *              Page numbers are compared by comparing their difference *              with zero (necessary because page numbers are allowed to wrap.) * * RETURNS:     >0              - byte offset of last record *              REFORMAT_ERROR(-3)      - i/o error, reformat the log *              MAJOR_ERROR(-2) - other major errors other than EIO. */int findEndOfLog(){	int rc;	int32_t left, right, pmax, pval, eormax, eorval, k;	/* binary search for logend */	left = 2;		/* first page containing log records				   since page 0 is never used, page 1 is				   log superblock */	right = Log.size - 1;	/* last page containing log records */	if ((rc = pageVal(left, &eormax, &pmax)) < 0) {		fsck_send_msg(lrdo_FEOLPGV1FAIL, rc);		return (rc);	}	while ((right - left) > 1) {		k = (left + right) >> 1;		if ((rc = pageVal(k, &eorval, &pval)) < 0) {			fsck_send_msg(lrdo_FEOLPGV2FAIL, rc);			return (rc);		}		if (pval - pmax > 0) {			left = k;			pmax = pval;			eormax = eorval;		} else			right = k;	}	if ((rc = pageVal(right, &eorval, &pval)) < 0) {		fsck_send_msg(lrdo_FEOLPGV3FAIL, rc);		return (rc);	}	/*	 * the last thing to determine is whether it is the first page of	 * the last long log record and system was crashed when its second	 * page is written. If the eor of the chosen page is LOGPHDRSIZE,	 * then this page contains a partial log record, ( otherwise, the	 * the long log record's second page should be chosen ).	 * This page should be thrown away. its previous page will be	 * the real last log page.	 */	if ((pval - pmax) > 0) {		if (eorval == LOGPHDRSIZE) {			if ((rc = pageVal(right - 1, &eorval, &pval)) < 0) {				fsck_send_msg(lrdo_FEOLPGV4FAIL, rc);				return (rc);			}			return (LOGPNTOB(right - 1) + eorval);		} else			return (LOGPNTOB(right) + eorval);	} else {		if (eormax == LOGPHDRSIZE) {			left = (left == 2) ? Log.size - 1 : left - 1;			if ((rc = pageVal(left, &eormax, &pmax)) < 0) {				fsck_send_msg(lrdo_FEOLPGV4AFAIL, rc);				return (rc);			}		}		return (LOGPNTOB(left) + eormax);	}}/* * NAME:        pageVal(pno, eor, pmax) * * FUNCTION:    Read the page into the log buffer pool and call setLogpage *              to form consistent log page. * * RETURNS:     0                       - ok *              REFORMAT_ERROR(-3)      - I/O error, reformat the log *              MAJOR_ERROR(-2)         - other major errors other than EIO. */int pageVal(int pno,		/* page number in log           */	    int *eor,		/* corresponding eor value      */	    int *pmax){				/* pointer to returned page number */	int buf0;		/* logp[] buffer element number         */	/* Read the page into the log buffer pool. */	if ((buf0 = getLogpage(pno)) < 0) {		fsck_send_msg(lrdo_PVGETPGFAIL, pno, buf0);		return (buf0);	}	return (setLogpage(pno, eor, pmax, buf0));}/* * NAME:        getLogpage(pno) * * FUNCTION:    if the specified log page is in buffer pool, return its *              index. Otherwise read log page into buffer pool. * * PARAMETERS:  pno -   log page number to look for. * * RETURNS:     0 - 3   - index of the buffer pool the page located *              REFORMAT_ERROR(-3)      - I/O error, reformat the log *              MAJOR_ERROR(-2)         - other major errors other than EIO. */int getLogpage(int pno){				/* page of log */	int k, rc;	/*	 * is it in buffer pool ?	 */	for (k = 0; k <= 3; k++)		if (logptr[k] == pno)			return (k);	/*	 * read page into buffer pool into next slot	 * don't have to use llseek() here.  log dev will never be > 2 gig	 */	nextrep = (nextrep + 1) % 4;	if (Log.location & INLINELOG)		rc = ujfs_rw_diskblocks(Log.fp,					(uint64_t) (Log.xaddr + LOGPNTOB(pno)),					(unsigned) LOGPSIZE, (char *) &logp[nextrep], GET);	else		rc = ujfs_rw_diskblocks(Log.fp,					(uint64_t) LOGPNTOB(pno),					(unsigned) LOGPSIZE, (char *) &logp[nextrep], GET);	if (rc != 0) {		return (JLOG_READERROR1);	}	logptr[nextrep] = pno;

⌨️ 快捷键说明

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