Skip site navigation (1)Skip section navigation (2)
Date:      22 Nov 1996 06:11 EST 
From:      "barry (b.a.) scott" <tsbarry@nortel.ca>
To:        akiyama@kme.mei.co.jp
Cc:        freebsd-scsi@freebsd.org, hackers@freebsd.org, joerg_wunsch@uriah.heep.sax.de, peter@taronga.com
Subject:   Re: Drive with 1024 byte logical blocks 
Message-ID:  <199611221847.KAA09486@freefall.freebsd.org>

next in thread | raw e-mail | index | archive | help
	The changes that John Gumb and I came up with modify
	far less code then this patch. Is this patch fixing
	extra problems that we missed?

	Further you have not patched fdisk or newfs that seem to
	be critical to getting a ufs file system onto a disk.

	For reference here is our patches to sbin/... and sys/...

		BArry

*** sys.orig/kern/subr_diskslice.c	Sun Nov 17 19:55:47 1996
--- sys/kern/subr_diskslice.c	Tue Nov 19 20:09:26 1996
***************
*** 210,220 ****
--- 210,224 ----
  		ic->ic_prev_iodone_chain = bp->b_iodone_chain;
  		ic->ic_args[0].ia_long = (LABELSECTOR + labelsect - blkno)
  					 << DEV_BSHIFT;
+ 		/* if we have a label then scale the offset to the disklabel */
+ 		if( lp )
+ 			ic->ic_args[0].ia_long *= lp->d_secsize / DEV_BSIZE;
  		ic->ic_args[1].ia_ptr = sp;
  		bp->b_flags |= B_CALL;
  		bp->b_iodone = dsiodone;
  		bp->b_iodone_chain = ic;
  		if (!(bp->b_flags & B_READ)) {
+ 
  			/*
  			 * XXX even disklabel(8) writes directly so we need
  			 * to adjust writes.  Perhaps we should drop support
*** sys.orig/msdosfs/msdosfs_fat.c	Sun Nov 17 19:54:36 1996
--- sys/msdosfs/msdosfs_fat.c	Tue Nov 19 20:09:34 1996
***************
*** 116,122 ****
  	    * pmp->pm_BytesPerSec;
  	bn += pmp->pm_fatblk;
  	if (bnp)
! 		*bnp = bn;
  	if (sizep)
  		*sizep = size;
  	if (bop)
--- 116,122 ----
  	    * pmp->pm_BytesPerSec;
  	bn += pmp->pm_fatblk;
  	if (bnp)
! 		*bnp = bn * pmp->pm_SecBlkRatio;
  	if (sizep)
  		*sizep = size;
  	if (bop)
***************
*** 185,191 ****
  				return E2BIG;
  			}
  			if (bnp)
! 				*bnp = pmp->pm_rootdirblk + (findcn * pmp->pm_SectPerClust);
  			if (cnp)
  				*cnp = MSDOSFSROOT;
  			return 0;
--- 185,191 ----
  				return E2BIG;
  			}
  			if (bnp)
! 				*bnp = (pmp->pm_rootdirblk + (findcn * pmp->pm_SectPerClust)) * pmp->pm_SecBlkRatio;
  			if (cnp)
  				*cnp = MSDOSFSROOT;
  			return 0;
***************
*** 340,346 ****
  	 * bwrite()'s and really slow things down.
  	 */
  	for (i = 1; i < pmp->pm_FATs; i++) {
! 		fatbn += pmp->pm_FATsecs;
  		/* getblk() never fails */
  		bpn = getblk(pmp->pm_devvp, fatbn, bp->b_bcount, 0, 0);
  		bcopy(bp->b_data, bpn->b_data, bp->b_bcount);
--- 340,346 ----
  	 * bwrite()'s and really slow things down.
  	 */
  	for (i = 1; i < pmp->pm_FATs; i++) {
! 		fatbn += pmp->pm_FATsecs * pmp->pm_SecBlkRatio;
  		/* getblk() never fails */
  		bpn = getblk(pmp->pm_devvp, fatbn, bp->b_bcount, 0, 0);
  		bcopy(bp->b_data, bpn->b_data, bp->b_bcount);
*** sys.orig/msdosfs/msdosfs_vfsops.c	Sun Nov 17 19:54:37 1996
--- sys/msdosfs/msdosfs_vfsops.c	Tue Nov 19 20:09:40 1996
***************
*** 273,278 ****
--- 273,279 ----
  	struct buf *bp0 = NULL;
  	struct byte_bpb33 *b33;
  	struct byte_bpb50 *b50;
+ 	int secsize;
  #ifdef	PC98
  	u_int	pc98_wrk;
  	u_int	Phy_Sector_Size;
***************
*** 319,325 ****
  	devvp->v_flag &= 0xffff; 
  	error = bread(devvp, 0, 1024, NOCRED, &bp0);
  #else
! 	error = bread(devvp, 0, 512, NOCRED, &bp0);
  #endif
  	if (error)
  		goto error_exit;
--- 320,337 ----
  	devvp->v_flag &= 0xffff; 
  	error = bread(devvp, 0, 1024, NOCRED, &bp0);
  #else
! 	/* hunt for the sector size that works */
! 	for( secsize=DEV_BSIZE; secsize<=2048; secsize <<= 1 )
! 		{
! 		if( bp0 )
! 			{
! 			brelse( bp0 );
! 			bp0 = NULL;
! 			}
! 		error = bread(devvp, 0, secsize, NOCRED, &bp0);
! 		if( error == 0 )
! 			break;
! 		}
  #endif
  	if (error)
  		goto error_exit;
***************
*** 349,354 ****
--- 361,369 ----
  	pmp = malloc(sizeof *pmp, M_MSDOSFSMNT, M_WAITOK);
  	bzero((caddr_t)pmp, sizeof *pmp);
  	pmp->pm_mountp = mp;
+ 
+ 	/* calculate the ratio of sector size to DEV_BSIZE */
+ 	pmp->pm_SecBlkRatio = secsize/DEV_BSIZE;
  
  	/*
  	 * Compute several useful quantities from the bpb in the
*** sys.orig/msdosfs/msdosfsmount.h	Sun Nov 17 19:54:36 1996
--- sys/msdosfs/msdosfsmount.h	Tue Nov 19 20:09:43 1996
***************
*** 60,65 ****
--- 60,66 ----
  	mode_t pm_mask;		/* mask to and with file protection bits */
  	struct vnode *pm_devvp;	/* vnode for block device mntd */
  	struct bpb50 pm_bpb;	/* BIOS parameter blk for this fs */
+ 	int pm_SecBlkRatio;	/* How many DEV_BSIZE blocks fit inside a physical sector */
  	u_long pm_fatblk;	/* block # of first FAT */
  	u_long pm_rootdirblk;	/* block # of root directory */
  	u_long pm_rootdirsize;	/* size in blocks (not clusters) */
***************
*** 124,143 ****
   * Map a cluster number into a filesystem relative block number.
   */
  #define	cntobn(pmp, cn) \
! 	((((cn)-CLUST_FIRST) * (pmp)->pm_SectPerClust) + (pmp)->pm_firstcluster)
  
  /*
   * Map a filesystem relative block number back into a cluster number.
   */
  #define	bntocn(pmp, bn) \
! 	((((bn) - pmp->pm_firstcluster)/ (pmp)->pm_SectPerClust) + CLUST_FIRST)
  
  /*
   * Calculate block number for directory entry in root dir, offset dirofs
   */
  #define	roottobn(pmp, dirofs) \
! 	(((dirofs) / (pmp)->pm_depclust) * (pmp)->pm_SectPerClust \
! 	+ (pmp)->pm_rootdirblk)
  
  /*
   * Calculate block number for directory entry at cluster dirclu, offset
--- 125,144 ----
   * Map a cluster number into a filesystem relative block number.
   */
  #define	cntobn(pmp, cn) \
! 	(((((cn)-CLUST_FIRST) * (pmp)->pm_SectPerClust) + (pmp)->pm_firstcluster)*(pmp)->pm_SecBlkRatio)
  
  /*
   * Map a filesystem relative block number back into a cluster number.
   */
  #define	bntocn(pmp, bn) \
! 	(((((bn)/((pmp)->pm_SecBlkRatio) - pmp->pm_firstcluster)/ (pmp)->pm_SectPerClust) + CLUST_FIRST)
  
  /*
   * Calculate block number for directory entry in root dir, offset dirofs
   */
  #define	roottobn(pmp, dirofs) \
! 	((((dirofs) / (pmp)->pm_depclust) * (pmp)->pm_SectPerClust \
! 	+ (pmp)->pm_rootdirblk) * (pmp)->pm_SecBlkRatio)
  
  /*
   * Calculate block number for directory entry at cluster dirclu, offset
*** sys.orig/scsi/od.c	Sun Nov 17 19:57:06 1996
--- sys/scsi/od.c	Tue Nov 19 20:09:46 1996
***************
*** 361,369 ****
  	switch (od->params.secsiz) {
  	case SECSIZE :
  	case 1024 :
- #ifdef notyet
  	case 2048 :
- #endif
  		break;
  	default :
  		printf("od%ld: Can't deal with %d bytes logical blocks\n",
--- 361,367 ----
***************
*** 448,453 ****
--- 446,452 ----
  	u_int32_t opri;
  	struct scsi_data *od;
  	u_int32_t unit;
+ 	int secsize;
  
  	odstrats++;
  	unit = ODUNIT((bp->b_dev));
***************
*** 464,478 ****
  	/*
  	 * Odd number of bytes or negative offset
  	 */
! 	if (bp->b_blkno < 0 || bp->b_bcount % DEV_BSIZE != 0) {
  		bp->b_error = EINVAL;
  		goto bad;
  	}
  	/*
  	 * Do bounds checking, adjust transfer, set b_cylin and b_pbklno.
  	 */
! 	if (dscheck(bp, od->dk_slices) <= 0)
  		goto done;	/* XXX check b_resid */
  
  	opri = SPLOD();
  
--- 463,520 ----
  	/*
  	 * Odd number of bytes or negative offset
  	 */
! 	if (bp->b_blkno < 0 ) {
! 		bp->b_error = EINVAL;
! 		printf("od_strategy: Negative block number: 0x%x\n", bp->b_blkno);
! 		goto bad;
! 	}
! 
! 	
! 	secsize = od->params.secsiz;
! 
! 	/* make sure the blkno is scalable */
! 	if( (bp->b_blkno % (secsize/DEV_BSIZE)) != 0 ) {
  		bp->b_error = EINVAL;
+ 		printf("od_strategy: Block number is not multiple of sector size (2): 0x%x\n", bp->b_blkno);
  		goto bad;
  	}
+ 
+ 	/* make sure that the tranasfer size is a multiple of the sector size */
+ 	if( (bp->b_bcount % secsize) != 0 ) {
+ 		bp->b_error = EINVAL;
+ 		printf("od_strategy: Invalid b_bcount %d at block number: 0x%x\n", bp->b_bcount, bp->b_blkno);
+ 		goto bad;
+ 	}
+ 
  	/*
  	 * Do bounds checking, adjust transfer, set b_cylin and b_pbklno.
  	 */
! 	{
! 	int status;
! 	int sec_blk_ratio = secsize/DEV_BSIZE;
! 	/* save original block number and size */
! 	int b_blkno = bp->b_blkno;
! 	int b_bcount = bp->b_bcount;
! 
! 	/* replace with scaled values */
! 	bp->b_blkno /= sec_blk_ratio;
! 	bp->b_bcount /= sec_blk_ratio;
! 	
! 	/* have dscheck enforce limits and map to physical block number */
! 	status = dscheck(bp, od->dk_slices);
! 
! 	/* restore original values to prevent bad side effects in block system */
! 	bp->b_blkno = b_blkno;
! 	bp->b_bcount = b_bcount;
! 	/* scale resid */
! 	bp->b_resid *= sec_blk_ratio;
! 
! 	/* see if the mapping failed */
! 	if (status <= 0)
! 		{
  		goto done;	/* XXX check b_resid */
+ 		}
+ 	}
  
  	opri = SPLOD();
  
***************
*** 581,592 ****
  		 * With this thing..
  		 */
  		secsize = od->params.secsiz;
! 		blkno = bp->b_pblkno / (secsize / DEV_BSIZE);
  		if (bp->b_bcount & (secsize - 1))
  		{
  		    goto bad;
  		}
! 		nblk = (bp->b_bcount + (secsize - 1)) / secsize;
  
  		/*
  		 *  Fill out the scsi command
--- 623,634 ----
  		 * With this thing..
  		 */
  		secsize = od->params.secsiz;
! 		blkno = bp->b_pblkno;
  		if (bp->b_bcount & (secsize - 1))
  		{
  		    goto bad;
  		}
! 		nblk = bp->b_bcount / secsize;
  
  		/*
  		 *  Fill out the scsi command
*** sys.orig/ufs/ufs/ufs_disksubr.c	Sun Nov 17 19:56:09 1996
--- sys/ufs/ufs/ufs_disksubr.c	Tue Nov 19 20:09:52 1996
***************
*** 182,188 ****
  
  	bp = geteblk((int)lp->d_secsize);
  	bp->b_dev = dev;
! 	bp->b_blkno = LABELSECTOR;
  	bp->b_bcount = lp->d_secsize;
  	bp->b_flags &= ~B_INVAL;
  	bp->b_flags |= B_BUSY | B_READ;
--- 182,188 ----
  
  	bp = geteblk((int)lp->d_secsize);
  	bp->b_dev = dev;
! 	bp->b_blkno = LABELSECTOR * ((int)lp->d_secsize/DEV_BSIZE);
  	bp->b_bcount = lp->d_secsize;
  	bp->b_flags &= ~B_INVAL;
  	bp->b_flags |= B_BUSY | B_READ;
***************
*** 284,290 ****
  	}
  	bp = geteblk((int)lp->d_secsize);
  	bp->b_dev = dkmodpart(dev, labelpart);
! 	bp->b_blkno = LABELSECTOR;
  	bp->b_bcount = lp->d_secsize;
  #if 1
  	/*
--- 284,290 ----
  	}
  	bp = geteblk((int)lp->d_secsize);
  	bp->b_dev = dkmodpart(dev, labelpart);
! 	bp->b_blkno = LABELSECTOR * ((int)lp->d_secsize / DEV_BSIZE);
  	bp->b_bcount = lp->d_secsize;
  #if 1
  	/*

*** sbin.orig/i386/fdisk/fdisk.c	Wed Nov 20 11:18:24 1996
--- sbin/i386/fdisk/fdisk.c	Wed Nov 20 11:28:23 1996
***************
*** 54,60 ****
  
  #define RoundCyl(x) ((((x) + cylsecs - 1) / cylsecs) * cylsecs)
  
! #define SECSIZE 512
  
  const char *disk;
  const char *disks[] =
--- 54,62 ----
  
  #define RoundCyl(x) ((((x) + cylsecs - 1) / cylsecs) * cylsecs)
  
! #define MAX_SEC_SIZE 2048	/* maximum section size that is supported */
! #define MIN_SEC_SIZE 512	/* the sector size to start sensing at */
! int secsize = 0;		/* the sensed sector size */
  
  const char *disk;
  const char *disks[] =
***************
*** 74,79 ****
--- 76,83 ----
  	unsigned char bootinst[DOSPARTOFF];
  	struct	dos_partition parts[4];
  	unsigned short int	signature;
+ 	/* room to read in MBRs that are bigger then DEV_BSIZE */
+ 	unsigned char large_sector_overflow[MAX_SEC_SIZE-MIN_SEC_SIZE];
  };
  struct mboot mboot;
  
***************
*** 292,297 ****
--- 296,302 ----
  	if (read_s0())
  		init_sector0(1);
  
+ 	printf("Media sector size is %d\n", secsize );
  	printf("Warning: BIOS sector numbering starts with sector 1\n");
  	printf("Information from DOS bootblock is:\n");
  	if (partition == -1)
***************
*** 347,353 ****
  	printf("sysid %d,(%s)\n", partp->dp_typ, get_type(partp->dp_typ));
  	printf("    start %ld, size %ld (%ld Meg), flag %x\n",
  		partp->dp_start,
! 		partp->dp_size, partp->dp_size * 512 / (1024 * 1024),
  		partp->dp_flag);
  	printf("\tbeg: cyl %d/ sector %d/ head %d;\n\tend: cyl %d/ sector %d/ head %d\n"
  		,DPCYL(partp->dp_scyl, partp->dp_ssect)
--- 352,358 ----
  	printf("sysid %d,(%s)\n", partp->dp_typ, get_type(partp->dp_typ));
  	printf("    start %ld, size %ld (%ld Meg), flag %x\n",
  		partp->dp_start,
! 		partp->dp_size, partp->dp_size * secsize / (1024 * 1024),
  		partp->dp_flag);
  	printf("\tbeg: cyl %d/ sector %d/ head %d;\n\tend: cyl %d/ sector %d/ head %d\n"
  		,DPCYL(partp->dp_scyl, partp->dp_ssect)
***************
*** 549,562 ****
  read_disk(off_t sector, void *buf)
  {
  	lseek(fd,(sector * 512), 0);
! 	return read(fd, buf, 512);
  }
  
  static ssize_t
  write_disk(off_t sector, void *buf)
  {
  	lseek(fd,(sector * 512), 0);
! 	return write(fd, buf, 512);
  }
  
  static int
--- 554,582 ----
  read_disk(off_t sector, void *buf)
  {
  	lseek(fd,(sector * 512), 0);
! 
! 	if( secsize == 0 )
! 		for( secsize = MIN_SEC_SIZE; secsize <= MAX_SEC_SIZE; secsize *= 2 )
! 			{
! 			/* try the read */
! 			int size = read(fd, buf, secsize);
! 			if( size == secsize )
! 				/* it worked so return */
! 				return secsize;
! 			}
! 	else
! 		return read( fd, buf, secsize );
! 
! 	/* we failed to read at any of the sizes */
! 	return -1;
  }
  
  static ssize_t
  write_disk(off_t sector, void *buf)
  {
  	lseek(fd,(sector * 512), 0);
! 	/* write out in the size that the read_disk found worked */
! 	return write(fd, buf, secsize);
  }
  
  static int
*** sbin.orig/newfs/mkfs.c	Wed Nov 20 11:20:40 1996
--- sbin/newfs/mkfs.c	Wed Nov 20 11:25:46 1996
***************
*** 82,90 ****
  extern int	nphyssectors;	/* # sectors/track including spares */
  extern int	secpercyl;	/* sectors per cylinder */
  extern int	sectorsize;	/* bytes/sector */
- #if defined( tahoe )
  extern int	realsectorsize;	/* bytes/sector in hardware */
- #endif
  extern int	rpm;		/* revolutions/minute of drive */
  extern int	interleave;	/* hardware sector interleave */
  extern int	trackskew;	/* sector 0 skew, per track */
--- 82,88 ----
***************
*** 212,218 ****
  	 */
  	if (fssize <= 0)
  		printf("preposterous size %d\n", fssize), exit(13);
! 	wtfs(fssize-1, DEV_BSIZE, (char *)&sblock);
  	/*
  	 * collect and verify the sector and track info
  	 */
--- 210,217 ----
  	 */
  	if (fssize <= 0)
  		printf("preposterous size %d\n", fssize), exit(13);
! 	/* the last block transfer must be in real sector size byte */
! 	wtfs(fssize-(realsectorsize/512), realsectorsize, (char *)&sblock);
  	/*
  	 * collect and verify the sector and track info
  	 */
*** sbin.orig/newfs/newfs.c	Wed Nov 20 11:18:55 1996
--- sbin/newfs/newfs.c	Wed Nov 20 11:24:39 1996
***************
*** 167,175 ****
  int	trackspares = -1;	/* spare sectors per track */
  int	cylspares = -1;		/* spare sectors per cylinder */
  int	sectorsize;		/* bytes/sector */
- #ifdef tahoe
  int	realsectorsize;		/* bytes/sector in hardware */
- #endif
  int	rpm;			/* revolutions/minute of drive */
  int	interleave;		/* hardware sector interleave */
  int	trackskew = -1;		/* sector 0 skew, per track */
--- 167,173 ----
***************
*** 530,540 ****
--- 528,553 ----
  		fssize /= secperblk;
  		pp->p_size /= secperblk;
  	}
+ #else
+ 	realsectorsize = sectorsize;
+ 	if (sectorsize != DEV_BSIZE) {		/* XXX */
+ 		int secperblk = sectorsize / DEV_BSIZE;
+ 
+ 		sectorsize = DEV_BSIZE;
+ 		nsectors *= secperblk;
+ 		nphyssectors *= secperblk;
+ 		secpercyl *= secperblk;
+ 		fssize *= secperblk;
+ 		pp->p_size *= secperblk;
+ 	}
  #endif
  	mkfs(pp, special, fsi, fso);
  #ifdef tahoe
  	if (realsectorsize != DEV_BSIZE)
  		pp->p_size *= DEV_BSIZE / realsectorsize;
+ #else
+ 	if (realsectorsize != DEV_BSIZE)
+ 		pp->p_size /= real
sectorsize/DEV_BSIZE;
  #endif
  	if (!Nflag)
  		close(fso);
***************
*** 676,679 ****
  	fprintf(stderr, "\t-x spare sectors per cylinder\n");
  	exit(1);
  }
- 
--- 689,691 ----




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199611221847.KAA09486>