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

📄 super.c

📁 Linux内核源代码 为压缩文件 是<<Linux内核>>一书中的源代码
💻 C
📖 第 1 页 / 共 3 页
字号:
		{			lastblock = last[i];			UDF_SB_ANCHOR(sb)[2] = 512 + UDF_SB_SESSION(sb);		}		else		{			if (!(bh = bread(sb->s_dev, last[i] - 256, sb->s_blocksize)))			{				ident = location = 0;			}			else			{				ident = le16_to_cpu(((tag *)bh->b_data)->tagIdent);				location = le32_to_cpu(((tag *)bh->b_data)->tagLocation);				udf_release_data(bh);			}			if (ident == TID_ANCHOR_VOL_DESC_PTR &&				location == last[i] - 256 - UDF_SB_SESSION(sb))			{				lastblock = last[i];				UDF_SB_ANCHOR(sb)[1] = last[i] - 256;			}			else			{				if (!(bh = bread(sb->s_dev, last[i] - 312 - UDF_SB_SESSION(sb),					sb->s_blocksize)))				{					ident = location = 0;				}				else				{					ident = le16_to_cpu(((tag *)bh->b_data)->tagIdent);					location = le32_to_cpu(((tag *)bh->b_data)->tagLocation);					udf_release_data(bh);				}				if (ident == TID_ANCHOR_VOL_DESC_PTR &&					location == udf_variable_to_fixed(last[i]) - 256)				{					UDF_SET_FLAG(sb, UDF_FLAG_VARCONV);					lastblock = udf_variable_to_fixed(last[i]);					UDF_SB_ANCHOR(sb)[1] = lastblock - 256;				}			}		}	}	if (!lastblock)	{		/* We havn't found the lastblock. check 312 */		if ((bh = bread(sb->s_dev, 312 + UDF_SB_SESSION(sb), sb->s_blocksize)))		{			ident = le16_to_cpu(((tag *)bh->b_data)->tagIdent);			location = le32_to_cpu(((tag *)bh->b_data)->tagLocation);			udf_release_data(bh);			if (ident == TID_ANCHOR_VOL_DESC_PTR && location == 256)				UDF_SET_FLAG(sb, UDF_FLAG_VARCONV);		}	}	for (i=0; i<sizeof(UDF_SB_ANCHOR(sb))/sizeof(int); i++)	{		if (UDF_SB_ANCHOR(sb)[i])		{			if (!(bh = udf_read_tagged(sb,				UDF_SB_ANCHOR(sb)[i], UDF_SB_ANCHOR(sb)[i], &ident)))			{				UDF_SB_ANCHOR(sb)[i] = 0;			}			else			{				udf_release_data(bh);				if ((ident != TID_ANCHOR_VOL_DESC_PTR) && (i ||					(ident != TID_FILE_ENTRY && ident != TID_EXTENDED_FILE_ENTRY)))				{					UDF_SB_ANCHOR(sb)[i] = 0;				}			}		}		else if (useranchor != 0xFFFFFFFF)		{			UDF_SB_ANCHOR(sb)[i] = useranchor;			useranchor = 0xFFFFFFFF;			i --;		}	}	return lastblock;}static int udf_find_fileset(struct super_block *sb, lb_addr *fileset, lb_addr *root){	struct buffer_head *bh = NULL;	long lastblock;	Uint16 ident;	if (fileset->logicalBlockNum != 0xFFFFFFFF ||		fileset->partitionReferenceNum != 0xFFFF)	{		bh = udf_read_ptagged(sb, *fileset, 0, &ident);		if (!bh)			return 1;		else if (ident != TID_FILE_SET_DESC)		{			udf_release_data(bh);			return 1;		}				}	if (!bh) /* Search backwards through the partitions */	{		lb_addr newfileset;		return 1;				for (newfileset.partitionReferenceNum=UDF_SB_NUMPARTS(sb)-1;			(newfileset.partitionReferenceNum != 0xFFFF &&				fileset->logicalBlockNum == 0xFFFFFFFF &&				fileset->partitionReferenceNum == 0xFFFF);			newfileset.partitionReferenceNum--)		{			lastblock = UDF_SB_PARTLEN(sb, newfileset.partitionReferenceNum);			newfileset.logicalBlockNum = 0;			do			{				bh = udf_read_ptagged(sb, newfileset, 0, &ident);				if (!bh)				{					newfileset.logicalBlockNum ++;					continue;				}				switch (ident)				{					case TID_SPACE_BITMAP_DESC:					{						struct SpaceBitmapDesc *sp;						sp = (struct SpaceBitmapDesc *)bh->b_data;						newfileset.logicalBlockNum += 1 +							((le32_to_cpu(sp->numOfBytes) + sizeof(struct SpaceBitmapDesc) - 1)								>> sb->s_blocksize_bits);						udf_release_data(bh);						break;					}					case TID_FILE_SET_DESC:					{						*fileset = newfileset;						break;					}					default:					{						newfileset.logicalBlockNum ++;						udf_release_data(bh);						bh = NULL;						break;					}				}			}			while (newfileset.logicalBlockNum < lastblock &&				fileset->logicalBlockNum == 0xFFFFFFFF &&				fileset->partitionReferenceNum == 0xFFFF);		}	}	if ((fileset->logicalBlockNum != 0xFFFFFFFF ||		fileset->partitionReferenceNum != 0xFFFF) && bh)	{		udf_debug("Fileset at block=%d, partition=%d\n",			fileset->logicalBlockNum, fileset->partitionReferenceNum);		UDF_SB_PARTITION(sb) = fileset->partitionReferenceNum;		udf_load_fileset(sb, bh, root);		udf_release_data(bh);		return 0;	}	return 1;}static void udf_load_pvoldesc(struct super_block *sb, struct buffer_head *bh){	struct PrimaryVolDesc *pvoldesc;	time_t recording;	long recording_usec;	struct ustr instr;	struct ustr outstr;	pvoldesc = (struct PrimaryVolDesc *)bh->b_data;	if ( udf_stamp_to_time(&recording, &recording_usec,		lets_to_cpu(pvoldesc->recordingDateAndTime)) )	{		timestamp ts;		ts = lets_to_cpu(pvoldesc->recordingDateAndTime);		udf_debug("recording time %ld/%ld, %04u/%02u/%02u %02u:%02u (%x)\n",			recording, recording_usec,			ts.year, ts.month, ts.day, ts.hour, ts.minute, ts.typeAndTimezone);		UDF_SB_RECORDTIME(sb) = recording;	}	if ( !udf_build_ustr(&instr, pvoldesc->volIdent, 32) )	{		if (udf_CS0toUTF8(&outstr, &instr))		{			strncpy( UDF_SB_VOLIDENT(sb), outstr.u_name,				outstr.u_len > 31 ? 31 : outstr.u_len);			udf_debug("volIdent[] = '%s'\n", UDF_SB_VOLIDENT(sb));		}	}	if ( !udf_build_ustr(&instr, pvoldesc->volSetIdent, 128) )	{		if (udf_CS0toUTF8(&outstr, &instr))			udf_debug("volSetIdent[] = '%s'\n", outstr.u_name);	}}static void udf_load_fileset(struct super_block *sb, struct buffer_head *bh, lb_addr *root){	struct FileSetDesc *fset;	fset = (struct FileSetDesc *)bh->b_data;	*root = lelb_to_cpu(fset->rootDirectoryICB.extLocation);	UDF_SB_SERIALNUM(sb) = le16_to_cpu(fset->descTag.tagSerialNum);	udf_debug("Rootdir at block=%d, partition=%d\n", 		root->logicalBlockNum, root->partitionReferenceNum);}static void udf_load_partdesc(struct super_block *sb, struct buffer_head *bh){	struct PartitionDesc *p;	int i;	p=(struct PartitionDesc *)bh->b_data;	for (i=0; i<UDF_SB_NUMPARTS(sb); i++)	{		udf_debug("Searching map: (%d == %d)\n", 			UDF_SB_PARTMAPS(sb)[i].s_partition_num, le16_to_cpu(p->partitionNumber));		if (UDF_SB_PARTMAPS(sb)[i].s_partition_num == le16_to_cpu(p->partitionNumber))		{			UDF_SB_PARTLEN(sb,i) = le32_to_cpu(p->partitionLength); /* blocks */			UDF_SB_PARTROOT(sb,i) = le32_to_cpu(p->partitionStartingLocation) + UDF_SB_SESSION(sb);			if (UDF_SB_PARTTYPE(sb,i) == UDF_SPARABLE_MAP15)				udf_fill_spartable(sb, &UDF_SB_TYPESPAR(sb,i), UDF_SB_PARTLEN(sb,i));			if (!strcmp(p->partitionContents.ident, PARTITION_CONTENTS_NSR02) ||				!strcmp(p->partitionContents.ident, PARTITION_CONTENTS_NSR03))			{				struct PartitionHeaderDesc *phd;				phd = (struct PartitionHeaderDesc *)(p->partitionContentsUse);				if (phd->unallocatedSpaceTable.extLength)					udf_debug("unallocatedSpaceTable (part %d)\n", i);				if (phd->unallocatedSpaceBitmap.extLength)				{					UDF_SB_PARTMAPS(sb)[i].s_uspace.bitmap =						le32_to_cpu(phd->unallocatedSpaceBitmap.extPosition);					UDF_SB_PARTFLAGS(sb,i) |= UDF_PART_FLAG_UNALLOC_BITMAP;					udf_debug("unallocatedSpaceBitmap (part %d) @ %d\n",						i, UDF_SB_PARTMAPS(sb)[i].s_uspace.bitmap);				}				if (phd->partitionIntegrityTable.extLength)					udf_debug("partitionIntegrityTable (part %d)\n", i);				if (phd->freedSpaceTable.extLength)					udf_debug("freedSpaceTable (part %d)\n", i);				if (phd->freedSpaceBitmap.extLength)				{					UDF_SB_PARTMAPS(sb)[i].s_fspace.bitmap =						le32_to_cpu(phd->freedSpaceBitmap.extPosition);					UDF_SB_PARTFLAGS(sb,i) |= UDF_PART_FLAG_FREED_BITMAP;					udf_debug("freedSpaceBitmap (part %d) @ %d\n",						i, UDF_SB_PARTMAPS(sb)[i].s_fspace.bitmap);				}			}			break;		}	}	if (i == UDF_SB_NUMPARTS(sb))	{		udf_debug("Partition (%d) not found in partition map\n", le16_to_cpu(p->partitionNumber));	}	else	{		udf_debug("Partition (%d:%d type %x) starts at physical %d, block length %d\n",			le16_to_cpu(p->partitionNumber), i, UDF_SB_PARTTYPE(sb,i),			UDF_SB_PARTROOT(sb,i), UDF_SB_PARTLEN(sb,i));	}}static int udf_load_logicalvol(struct super_block *sb, struct buffer_head * bh, lb_addr *fileset){	struct LogicalVolDesc *lvd;	int i, j, offset;	Uint8 type;	lvd = (struct LogicalVolDesc *)bh->b_data;	UDF_SB_NUMPARTS(sb) = le32_to_cpu(lvd->numPartitionMaps);	UDF_SB_ALLOC_PARTMAPS(sb, UDF_SB_NUMPARTS(sb));	for (i=0,offset=0;		 i<UDF_SB_NUMPARTS(sb) && offset<le32_to_cpu(lvd->mapTableLength);		 i++,offset+=((struct GenericPartitionMap *)&(lvd->partitionMaps[offset]))->partitionMapLength)	{		type = ((struct GenericPartitionMap *)&(lvd->partitionMaps[offset]))->partitionMapType;		udf_debug("Partition (%d) type %d\n", i, type);		if (type == 1)		{			struct GenericPartitionMap1 *gpm1 = (struct GenericPartitionMap1 *)&(lvd->partitionMaps[offset]);			UDF_SB_PARTTYPE(sb,i) = UDF_TYPE1_MAP15;			UDF_SB_PARTVSN(sb,i) = le16_to_cpu(gpm1->volSeqNum);			UDF_SB_PARTNUM(sb,i) = le16_to_cpu(gpm1->partitionNum);			UDF_SB_PARTFUNC(sb,i) = NULL;		}		else if (type == 2)		{			struct UdfPartitionMap2 *upm2 = (struct UdfPartitionMap2 *)&(lvd->partitionMaps[offset]);			if (!strncmp(upm2->partIdent.ident, UDF_ID_VIRTUAL, strlen(UDF_ID_VIRTUAL)))			{				if (le16_to_cpu(((Uint16 *)upm2->partIdent.identSuffix)[0]) == 0x0150)				{					UDF_SB_PARTTYPE(sb,i) = UDF_VIRTUAL_MAP15;					UDF_SB_PARTFUNC(sb,i) = udf_get_pblock_virt15;				}				else if (le16_to_cpu(((Uint16 *)upm2->partIdent.identSuffix)[0]) == 0x0200)				{					UDF_SB_PARTTYPE(sb,i) = UDF_VIRTUAL_MAP20;					UDF_SB_PARTFUNC(sb,i) = udf_get_pblock_virt20;				}			}			else if (!strncmp(upm2->partIdent.ident, UDF_ID_SPARABLE, strlen(UDF_ID_SPARABLE)))			{				int plen;				struct SparablePartitionMap *spm = (struct SparablePartitionMap *)&(lvd->partitionMaps[offset]);				UDF_SB_PARTTYPE(sb,i) = UDF_SPARABLE_MAP15;				plen = le16_to_cpu(spm->packetLength);				UDF_SB_TYPESPAR(sb,i).s_spar_pshift = 0;				while (plen >>= 1)					UDF_SB_TYPESPAR(sb,i).s_spar_pshift ++;				for (j=0; j<spm->numSparingTables; j++)					UDF_SB_TYPESPAR(sb,i).s_spar_loc[j] = le32_to_cpu(spm->locSparingTable[j]);				UDF_SB_PARTFUNC(sb,i) = udf_get_pblock_spar15;			}			else			{				udf_debug("Unknown ident: %s\n", upm2->partIdent.ident);				continue;			}			UDF_SB_PARTVSN(sb,i) = le16_to_cpu(upm2->volSeqNum);			UDF_SB_PARTNUM(sb,i) = le16_to_cpu(upm2->partitionNum);		}	}	if (fileset)	{		long_ad *la = (long_ad *)&(lvd->logicalVolContentsUse[0]);		*fileset = lelb_to_cpu(la->extLocation);		udf_debug("FileSet found in LogicalVolDesc at block=%d, partition=%d\n",			fileset->logicalBlockNum,			fileset->partitionReferenceNum);	}	if (lvd->integritySeqExt.extLength)		udf_load_logicalvolint(sb, leea_to_cpu(lvd->integritySeqExt));	return 0;}/* * udf_load_logicalvolint * */static voidudf_load_logicalvolint(struct super_block *sb, extent_ad loc){	struct buffer_head *bh = NULL;	Uint16 ident;	while ((bh = udf_read_tagged(sb, loc.extLocation, loc.extLocation, &ident)) &&		ident == TID_LOGICAL_VOL_INTEGRITY_DESC && loc.extLength > 0)	{		UDF_SB_LVIDBH(sb) = bh;				if (UDF_SB_LVID(sb)->nextIntegrityExt.extLength)			udf_load_logicalvolint(sb, leea_to_cpu(UDF_SB_LVID(sb)->nextIntegrityExt));				if (UDF_SB_LVIDBH(sb) != bh)			udf_release_data(bh);		loc.extLength -= sb->s_blocksize;		loc.extLocation ++;	}	if (UDF_SB_LVIDBH(sb) != bh)		udf_release_data(bh);}/* * udf_process_sequence * * PURPOSE *	Process a main/reserve volume descriptor sequence. * * PRE-CONDITIONS *	sb			Pointer to _locked_ superblock. *	block			First block of first extent of the sequence. *	lastblock		Lastblock of first extent of the sequence. * * HISTORY *	July 1, 1997 - Andrew E. Mileski *	Written, tested, and released. */static  intudf_process_sequence(struct super_block *sb, long block, long lastblock, lb_addr *fileset){	struct buffer_head *bh = NULL;	struct udf_vds_record vds[VDS_POS_LENGTH];	struct GenericDesc *gd;	int done=0;	int i,j;	Uint32 vdsn;	Uint16 ident;	memset(vds, 0, sizeof(struct udf_vds_record) * VDS_POS_LENGTH);	/* Read the main descriptor sequence */	for (;(!done && block <= lastblock); block++)	{		bh = udf_read_tagged(sb, block, block, &ident);		if (!bh) 			break;		/* Process each descriptor (ISO 13346 3/8.3-8.4) */		gd = (struct GenericDesc *)bh->b_data;		vdsn = le32_to_cpu(gd->volDescSeqNum);		switch (ident)		{			case TID_PRIMARY_VOL_DESC: /* ISO 13346 3/10.1 */				if (vdsn >= vds[VDS_POS_PRIMARY_VOL_DESC].volDescSeqNum)				{					vds[VDS_POS_PRIMARY_VOL_DESC].volDescSeqNum = vdsn;					vds[VDS_POS_PRIMARY_VOL_DESC].block = block;				}				break;			case TID_VOL_DESC_PTR: /* ISO 13346 3/10.3 */				if (vdsn >= vds[VDS_POS_VOL_DESC_PTR].volDescSeqNum)				{					vds[VDS_POS_VOL_DESC_PTR].volDescSeqNum = vdsn;					vds[VDS_POS_VOL_DESC_PTR].block = block;				}				break;			case TID_IMP_USE_VOL_DESC: /* ISO 13346 3/10.4 */				if (vdsn >= vds[VDS_POS_IMP_USE_VOL_DESC].volDescSeqNum)				{					vds[VDS_POS_IMP_USE_VOL_DESC].volDescSeqNum = vdsn;					vds[VDS_POS_IMP_USE_VOL_DESC].block = block;				}				break;			case TID_PARTITION_DESC: /* ISO 13346 3/10.5 */				if (!vds[VDS_POS_PARTITION_DESC].block)					vds[VDS_POS_PARTITION_DESC].block = block;				break;			case TID_LOGICAL_VOL_DESC: /* ISO 13346 3/10.6 */				if (vdsn >= vds[VDS_POS_LOGICAL_VOL_DESC].volDescSeqNum)				{					vds[VDS_POS_LOGICAL_VOL_DESC].volDescSeqNum = vdsn;					vds[VDS_POS_LOGICAL_VOL_DESC].block = block;				}				break;			case TID_UNALLOC_SPACE_DESC: /* ISO 13346 3/10.8 */				if (vdsn >= vds[VDS_POS_UNALLOC_SPACE_DESC].volDescSeqNum)				{					vds[VDS_POS_UNALLOC_SPACE_DESC].volDescSeqNum = vdsn;					vds[VDS_POS_UNALLOC_SPACE_DESC].block = block;				}				break;			case TID_TERMINATING_DESC: /* ISO 13346 3/10.9 */				vds[VDS_POS_TERMINATING_DESC].block = block;				done = 1;				break;		}		udf_release_data(bh);	}	for (i=0; i<VDS_POS_LENGTH; i++)	{		if (vds[i].block)		{			bh = udf_read_tagged(sb, vds[i].block, vds[i].block, &ident);			if (i == VDS_POS_PRIMARY_VOL_DESC)				udf_load_pvoldesc(sb, bh);			else if (i == VDS_POS_LOGICAL_VOL_DESC)				udf_load_logicalvol(sb, bh, fileset);			else if (i == VDS_POS_PARTITION_DESC)			{				struct buffer_head *bh2 = NULL;				udf_load_partdesc(sb, bh);				for (j=vds[i].block+1; j<vds[VDS_POS_TERMINATING_DESC].block; j++)				{					bh2 = udf_read_tagged(sb, j, j, &ident);					gd = (struct GenericDesc *)bh2->b_data;					if (ident == TID_PARTITION_DESC)						udf_load_partdesc(sb, bh2);					udf_release_data(bh2);				}			}			udf_release_data(bh);		}	}	return 0;}/* * udf_check_valid() */static intudf_check_valid(struct super_block *sb, int novrs, int silent){	long block;	if (novrs)	{

⌨️ 快捷键说明

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