fs/hpfs/map.c

Source file repositories/reference/linux-study-clean/fs/hpfs/map.c

File Facts

System
Linux kernel
Corpus path
fs/hpfs/map.c
Extension
.c
Size
10080 bytes
Lines
336
Domain
Core OS
Bucket
VFS And Filesystem Core
Inferred role
Core OS: implementation source
Status
source implementation candidate

Why This File Exists

Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.

Dependency Surface

Detected Declarations

Annotated Snippet

if (!d) {
			kfree(b);
			return NULL;
		}
		memcpy((char *)b + 512 * i, d, 512);
		brelse(bh);
	}
	return b;
}

void hpfs_load_hotfix_map(struct super_block *s, struct hpfs_spare_block *spareblock)
{
	struct quad_buffer_head qbh;
	__le32 *directory;
	u32 n_hotfixes, n_used_hotfixes;
	unsigned i;

	n_hotfixes = le32_to_cpu(spareblock->n_spares);
	n_used_hotfixes = le32_to_cpu(spareblock->n_spares_used);

	if (n_hotfixes > 256 || n_used_hotfixes > n_hotfixes) {
		hpfs_error(s, "invalid number of hotfixes: %u, used: %u", n_hotfixes, n_used_hotfixes);
		return;
	}
	if (!(directory = hpfs_map_4sectors(s, le32_to_cpu(spareblock->hotfix_map), &qbh, 0))) {
		hpfs_error(s, "can't load hotfix map");
		return;
	}
	for (i = 0; i < n_used_hotfixes; i++) {
		hpfs_sb(s)->hotfix_from[i] = le32_to_cpu(directory[i]);
		hpfs_sb(s)->hotfix_to[i] = le32_to_cpu(directory[n_hotfixes + i]);
	}
	hpfs_sb(s)->n_hotfixes = n_used_hotfixes;
	hpfs_brelse4(&qbh);
}

/*
 * Load fnode to memory
 */

struct fnode *hpfs_map_fnode(struct super_block *s, ino_t ino, struct buffer_head **bhp)
{
	struct fnode *fnode;
	if (hpfs_sb(s)->sb_chk) if (hpfs_chk_sectors(s, ino, 1, "fnode")) {
		return NULL;
	}
	if ((fnode = hpfs_map_sector(s, ino, bhp, FNODE_RD_AHEAD))) {
		if (hpfs_sb(s)->sb_chk) {
			struct extended_attribute *ea;
			struct extended_attribute *ea_end;
			if (le32_to_cpu(fnode->magic) != FNODE_MAGIC) {
				hpfs_error(s, "bad magic on fnode %08lx",
					(unsigned long)ino);
				goto bail;
			}
			if (!fnode_is_dir(fnode)) {
				if ((unsigned)fnode->btree.n_used_nodes + (unsigned)fnode->btree.n_free_nodes !=
				    (bp_internal(GET_BTREE_PTR(&fnode->btree)) ? 12 : 8)) {
					hpfs_error(s,
					   "bad number of nodes in fnode %08lx",
					    (unsigned long)ino);
					goto bail;
				}
				if (le16_to_cpu(fnode->btree.first_free) !=
				    8 + fnode->btree.n_used_nodes * (bp_internal(GET_BTREE_PTR(&fnode->btree)) ? 8 : 12)) {
					hpfs_error(s,
					    "bad first_free pointer in fnode %08lx",
					    (unsigned long)ino);
					goto bail;
				}
			}
			if (le16_to_cpu(fnode->ea_size_s) && (le16_to_cpu(fnode->ea_offs) < 0xc4 ||
			   le16_to_cpu(fnode->ea_offs) + le16_to_cpu(fnode->acl_size_s) + le16_to_cpu(fnode->ea_size_s) > 0x200)) {
				hpfs_error(s,
					"bad EA info in fnode %08lx: ea_offs == %04x ea_size_s == %04x",
					(unsigned long)ino,
					le16_to_cpu(fnode->ea_offs), le16_to_cpu(fnode->ea_size_s));
				goto bail;
			}
			ea = fnode_ea(fnode);
			ea_end = fnode_end_ea(fnode);
			while (ea != ea_end) {
				if (ea > ea_end) {
					hpfs_error(s, "bad EA in fnode %08lx",
						(unsigned long)ino);
					goto bail;
				}
				ea = next_ea(ea);
			}
		}

Annotation

Implementation Notes