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

📄 yaffs_fsx.c

📁 yaffs2 lastest sourcecode~~
💻 C
📖 第 1 页 / 共 2 页
字号:
/* * Copyright (c) 1998-2001 Apple Computer, Inc. All rights reserved. * * @APPLE_LICENSE_HEADER_START@ * * The contents of this file constitute Original Code as defined in and * are subject to the Apple Public Source License Version 1.2 (the * "License").  You may not use this file except in compliance with the * License.  Please obtain a copy of the License at * http://www.apple.com/publicsource and read it before using this file. * * This Original Code and all software distributed under the License are * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the * License for the specific language governing rights and limitations * under the License. * * @APPLE_LICENSE_HEADER_END@ * *	WARNING--WARNING--WARNING *	This is not the original fsx.c. It has been modified to run with *      yaffs direct. Seek out the original fsx.c if you want to do anything *	else. * *	 * *	File:	fsx.c *	Author:	Avadis Tevanian, Jr. * *	File system exerciser.  * *	Rewrite and enhancements 1998-2001 Conrad Minshall -- conrad@mac.com * *	Various features from Joe Sokol, Pat Dirks, and Clark Warner. * *	Small changes to work under Linux -- davej@suse.de * *	Sundry porting patches from Guy Harris 12/2001 * *	Checks for mmap last-page zero fill. * *	Modified heavily by Charles Manning to exercise via the *	yaffs direct interface. * */#include <sys/types.h>#include <sys/stat.h>#ifdef _UWIN# include <sys/param.h># include <limits.h># include <time.h># include <strings.h>#endif#include <fcntl.h>#include <sys/mman.h>#ifndef MAP_FILE# define MAP_FILE 0#endif#include <limits.h>#include <signal.h>#include <stdio.h>#include <stdlib.h>#include <string.h>#include <unistd.h>#include <stdarg.h>#include <errno.h>#include <time.h>#include "yaffsfs.h"#define NUMPRINTCOLUMNS 32	/* # columns of data to print on each line *//* *	A log entry is an operation and a bunch of arguments. */struct log_entry {	int	operation;	int	args[3];};#define	LOGSIZE	1000struct log_entry	oplog[LOGSIZE];	/* the log */int			logptr = 0;	/* current position in log */int			logcount = 0;	/* total ops *//* *	Define operations */#define	OP_READ		1#define OP_WRITE	2#define OP_TRUNCATE	3#define OP_CLOSEOPEN	4#define OP_MAPREAD	5#define OP_MAPWRITE	6#define OP_SKIPPED	7int page_size;int page_mask;char	*original_buf;			/* a pointer to the original data */char	*good_buf;			/* a pointer to the correct data */char	*temp_buf;			/* a pointer to the current data */char	*fname;				/* name of our test file */int	fd;				/* fd for our test file */off_t		file_size = 0;off_t		biggest = 0;char		state[256];unsigned long	testcalls = 0;		/* calls to function "test" */unsigned long	simulatedopcount = 0;	/* -b flag */int	closeprob = 0;			/* -c flag */int	debug = 0;			/* -d flag */unsigned long	debugstart = 0;		/* -D flag */unsigned long	maxfilelen = 256 * 1024;	/* -l flag */int	sizechecks = 1;			/* -n flag disables them */int	maxoplen = 64 * 1024;		/* -o flag */int	quiet = 0;			/* -q flag */unsigned long progressinterval = 0;	/* -p flag */int	readbdy = 1;			/* -r flag */int	style = 0;			/* -s flag */int	truncbdy = 1;			/* -t flag */int	writebdy = 1;			/* -w flag */long	monitorstart = -1;		/* -m flag */long	monitorend = -1;		/* -m flag */int	lite = 0;			/* -L flag */long	numops = /*-1 */ 10000000;			/* -N flag */int	randomoplen = 1;		/* -O flag disables it */int	seed = 1;			/* -S flag */int     mapped_writes = 0;	      /* yaffs direct does not support mmapped files */int 	mapped_reads = 0;int	fsxgoodfd = 0;FILE *	fsxlogf = NULL;int badoff = -1;int closeopen = 0;voidvwarnc(code, fmt, ap)	int code;	const char *fmt;	va_list ap;{	fprintf(stderr, "fsx: ");	if (fmt != NULL) {		vfprintf(stderr, fmt, ap);		fprintf(stderr, ": ");	}	fprintf(stderr, "%s\n", strerror(code));}voidwarn(const char * fmt, ...){	va_list ap;	va_start(ap, fmt);	vwarnc(errno, fmt, ap);	va_end(ap);}voidprt(char *fmt, ...){	va_list args;	va_start(args, fmt);	vfprintf(stdout, fmt, args);	if (fsxlogf)		vfprintf(fsxlogf, fmt, args);	va_end(args);}voidprterr(char *prefix){	prt("%s%s%s\n", prefix, prefix ? ": " : "", strerror(errno));}voidlog4(int operation, int arg0, int arg1, int arg2){	struct log_entry *le;	le = &oplog[logptr];	le->operation = operation;	if (closeopen)		le->operation = ~ le->operation;	le->args[0] = arg0;	le->args[1] = arg1;	le->args[2] = arg2;	logptr++;	logcount++;	if (logptr >= LOGSIZE)		logptr = 0;}voidlogdump(void){	int	i, count, down;	struct log_entry	*lp;	prt("LOG DUMP (%d total operations):\n", logcount);	if (logcount < LOGSIZE) {		i = 0;		count = logcount;	} else {		i = logptr;		count = LOGSIZE;	}	for ( ; count > 0; count--) {		int opnum;		opnum = i+1 + (logcount/LOGSIZE)*LOGSIZE;		prt("%d(%d mod 256): ", opnum, opnum%256);		lp = &oplog[i];		if ((closeopen = lp->operation < 0))			lp->operation = ~ lp->operation;					switch (lp->operation) {		case OP_MAPREAD:			prt("MAPREAD\t0x%x thru 0x%x\t(0x%x bytes)",			    lp->args[0], lp->args[0] + lp->args[1] - 1,			    lp->args[1]);			if (badoff >= lp->args[0] && badoff <						     lp->args[0] + lp->args[1])				prt("\t***RRRR***");			break;		case OP_MAPWRITE:			prt("MAPWRITE 0x%x thru 0x%x\t(0x%x bytes)",			    lp->args[0], lp->args[0] + lp->args[1] - 1,			    lp->args[1]);			if (badoff >= lp->args[0] && badoff <						     lp->args[0] + lp->args[1])				prt("\t******WWWW");			break;		case OP_READ:			prt("READ\t0x%x thru 0x%x\t(0x%x bytes)",			    lp->args[0], lp->args[0] + lp->args[1] - 1,			    lp->args[1]);			if (badoff >= lp->args[0] &&			    badoff < lp->args[0] + lp->args[1])				prt("\t***RRRR***");			break;		case OP_WRITE:			prt("WRITE\t0x%x thru 0x%x\t(0x%x bytes)",			    lp->args[0], lp->args[0] + lp->args[1] - 1,			    lp->args[1]);			if (lp->args[0] > lp->args[2])				prt(" HOLE");			else if (lp->args[0] + lp->args[1] > lp->args[2])				prt(" EXTEND");			if ((badoff >= lp->args[0] || badoff >=lp->args[2]) &&			    badoff < lp->args[0] + lp->args[1])				prt("\t***WWWW");			break;		case OP_TRUNCATE:			down = lp->args[0] < lp->args[1];			prt("TRUNCATE %s\tfrom 0x%x to 0x%x",			    down ? "DOWN" : "UP", lp->args[1], lp->args[0]);			if (badoff >= lp->args[!down] &&			    badoff < lp->args[!!down])				prt("\t******WWWW");			break;		case OP_SKIPPED:			prt("SKIPPED (no operation)");			break;		default:			prt("BOGUS LOG ENTRY (operation code = %d)!",			    lp->operation);		}		if (closeopen)			prt("\n\t\tCLOSE/OPEN");		prt("\n");		i++;		if (i == LOGSIZE)			i = 0;	}}voidsave_buffer(char *buffer, off_t bufferlength, int fd){	off_t ret;	ssize_t byteswritten;	if (fd <= 0 || bufferlength == 0)		return;	if (bufferlength > SSIZE_MAX) {		prt("fsx flaw: overflow in save_buffer\n");		exit(67);	}	if (lite) {		off_t size_by_seek = yaffs_lseek(fd, (off_t)0, SEEK_END);		if (size_by_seek == (off_t)-1)			prterr("save_buffer: lseek eof");		else if (bufferlength > size_by_seek) {			warn("save_buffer: .fsxgood file too short... will save 0x%llx bytes instead of 0x%llx\n", (unsigned long long)size_by_seek,			     (unsigned long long)bufferlength);			bufferlength = size_by_seek;		}	}	ret = yaffs_lseek(fd, (off_t)0, SEEK_SET);	if (ret == (off_t)-1)		prterr("save_buffer: lseek 0");		byteswritten = yaffs_write(fd, buffer, (size_t)bufferlength);	if (byteswritten != bufferlength) {		if (byteswritten == -1)			prterr("save_buffer write");		else			warn("save_buffer: short write, 0x%x bytes instead of 0x%llx\n",			     (unsigned)byteswritten,			     (unsigned long long)bufferlength);	}}voidreport_failure(int status){	logdump();		if (fsxgoodfd) {		if (good_buf) {			save_buffer(good_buf, file_size, fsxgoodfd);			prt("Correct content saved for comparison\n");			prt("(maybe hexdump \"%s\" vs \"%s.fsxgood\")\n",			    fname, fname);		}		close(fsxgoodfd);	}	prt("Exiting with %d\n",status);	exit(status);}#define short_at(cp) ((unsigned short)((*((unsigned char *)(cp)) << 8) | \					*(((unsigned char *)(cp)) + 1)))voidcheck_buffers(unsigned offset, unsigned size){	unsigned char c, t;	unsigned i = 0;	unsigned n = 0;	unsigned op = 0;	unsigned bad = 0;	if (memcmp(good_buf + offset, temp_buf, size) != 0) {		prt("READ BAD DATA: offset = 0x%x, size = 0x%x\n",		    offset, size);		prt("OFFSET\tGOOD\tBAD\tRANGE\n");		while (size > 0) {			c = good_buf[offset];			t = temp_buf[i];			if (c != t) {				if (n == 0) {					bad = short_at(&temp_buf[i]);					prt("0x%5x\t0x%04x\t0x%04x", offset,					    short_at(&good_buf[offset]), bad);					op = temp_buf[offset & 1 ? i+1 : i];				}				n++;				badoff = offset;			}			offset++;			i++;			size--;		}		if (n) {			prt("\t0x%5x\n", n);			if (bad)				prt("operation# (mod 256) for the bad data may be %u\n", ((unsigned)op & 0xff));			else				prt("operation# (mod 256) for the bad data unknown, check HOLE and EXTEND ops\n");		} else			prt("????????????????\n");		report_failure(110);	}}voidcheck_size(void){	struct yaffs_stat	statbuf;	off_t	size_by_seek;	if (yaffs_fstat(fd, &statbuf)) {		prterr("check_size: fstat");		statbuf.st_size = -1;	}	size_by_seek = yaffs_lseek(fd, (off_t)0, SEEK_END);	if (file_size != statbuf.st_size || file_size != size_by_seek) {		prt("Size error: expected 0x%llx stat 0x%llx seek 0x%llx\n",		    (unsigned long long)file_size,		    (unsigned long long)statbuf.st_size,		    (unsigned long long)size_by_seek);		report_failure(120);	}}voidcheck_trunc_hack(void){	struct yaffs_stat statbuf;	yaffs_ftruncate(fd, (off_t)0);	yaffs_ftruncate(fd, (off_t)100000);	yaffs_fstat(fd, &statbuf);	if (statbuf.st_size != (off_t)100000) {		prt("no extend on truncate! not posix!\n");		exit(130);	}	yaffs_ftruncate(fd, (off_t)0);}voiddoread(unsigned offset, unsigned size){	off_t ret;	unsigned iret;	offset -= offset % readbdy;	if (size == 0) {		if (!quiet && testcalls > simulatedopcount)			prt("skipping zero size read\n");		log4(OP_SKIPPED, OP_READ, offset, size);		return;	}	if (size + offset > file_size) {		if (!quiet && testcalls > simulatedopcount)			prt("skipping seek/read past end of file\n");		log4(OP_SKIPPED, OP_READ, offset, size);		return;	}	log4(OP_READ, offset, size, 0);	if (testcalls <= simulatedopcount)		return;	if (!quiet && ((progressinterval &&			testcalls % progressinterval == 0) ||		       (debug &&			(monitorstart == -1 ||			 (offset + size > monitorstart &&			  (monitorend == -1 || offset <= monitorend))))))		prt("%lu read\t0x%x thru\t0x%x\t(0x%x bytes)\n", testcalls,		    offset, offset + size - 1, size);	ret = yaffs_lseek(fd, (off_t)offset, SEEK_SET);	if (ret == (off_t)-1) {		prterr("doread: lseek");		report_failure(140);	}	iret = yaffs_read(fd, temp_buf, size);	if (iret != size) {		if (iret == -1)			prterr("doread: read");		else			prt("short read: 0x%x bytes instead of 0x%x\n",			    iret, size);		report_failure(141);	}	check_buffers(offset, size);}voidgendata(char *original_buf, char *good_buf, unsigned offset, unsigned size){	while (size--) {		good_buf[offset] = testcalls % 256; 		if (offset % 2)			good_buf[offset] += original_buf[offset];		offset++;	}}voiddowrite(unsigned offset, unsigned size){	off_t ret;	unsigned iret;

⌨️ 快捷键说明

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