VisionFive2 Linux kernel

StarFive Tech Linux Kernel for VisionFive (JH7110) boards (mirror)

More than 9999 Commits   32 Branches   54 Tags
b24413180f560 (Greg Kroah-Hartman 2017-11-01 15:07:57 +0100   1) // SPDX-License-Identifier: GPL-2.0
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   2) /*
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   3)  *  linux/fs/isofs/dir.c
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   4)  *
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   5)  *  (C) 1992, 1993, 1994  Eric Youngdale Modified for ISO 9660 filesystem.
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   6)  *
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   7)  *  (C) 1991  Linus Torvalds - minix filesystem
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   8)  *
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700   9)  *  Steve Beynon		       : Missing last directory entries fixed
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  10)  *  (stephen@askone.demon.co.uk)      : 21st June 1996
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  11)  *
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  12)  *  isofs directory handling functions
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  13)  */
5a0e3ad6af866 (Tejun Heo          2010-03-24 17:04:11 +0900  14) #include <linux/gfp.h>
94f2f715771d0 (Al Viro            2005-04-25 18:32:12 -0700  15) #include "isofs.h"
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  16) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  17) int isofs_name_translate(struct iso_directory_record *de, char *new, struct inode *inode)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  18) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  19) 	char * old = de->name;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  20) 	int len = de->name_len[0];
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  21) 	int i;
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  22) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  23) 	for (i = 0; i < len; i++) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  24) 		unsigned char c = old[i];
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  25) 		if (!c)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  26) 			break;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  27) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  28) 		if (c >= 'A' && c <= 'Z')
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  29) 			c |= 0x20;	/* lower case */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  30) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  31) 		/* Drop trailing '.;1' (ISO 9660:1988 7.5.1 requires period) */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  32) 		if (c == '.' && i == len - 3 && old[i + 1] == ';' && old[i + 2] == '1')
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  33) 			break;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  34) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  35) 		/* Drop trailing ';1' */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  36) 		if (c == ';' && i == len - 2 && old[i + 1] == '1')
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  37) 			break;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  38) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  39) 		/* Convert remaining ';' to '.' */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  40) 		/* Also '/' to '.' (broken Acorn-generated ISO9660 images) */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  41) 		if (c == ';' || c == '/')
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  42) 			c = '.';
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  43) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  44) 		new[i] = c;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  45) 	}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  46) 	return i;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  47) }
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  48) 
3d0186bb068e6 (Matthew Wilcox     2018-06-16 17:32:07 -0400  49) /* Acorn extensions written by Matthew Wilcox <willy@infradead.org> 1998 */
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  50) int get_acorn_filename(struct iso_directory_record *de,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  51) 			    char *retname, struct inode *inode)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  52) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  53) 	int std;
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  54) 	unsigned char *chr;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  55) 	int retnamlen = isofs_name_translate(de, retname, inode);
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  56) 
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  57) 	if (retnamlen == 0)
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  58) 		return 0;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  59) 	std = sizeof(struct iso_directory_record) + de->name_len[0];
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  60) 	if (std & 1)
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  61) 		std++;
e17a21d3bb067 (Al Viro            2016-05-05 10:48:47 -0400  62) 	if (de->length[0] - std != 32)
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  63) 		return retnamlen;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  64) 	chr = ((unsigned char *) de) + std;
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  65) 	if (strncmp(chr, "ARCHIMEDES", 10))
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  66) 		return retnamlen;
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  67) 	if ((*retname == '_') && ((chr[19] & 1) == 1))
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  68) 		*retname = '!';
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  69) 	if (((de->flags[0] & 2) == 0) && (chr[13] == 0xff)
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  70) 		&& ((chr[12] & 0xf0) == 0xf0)) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  71) 		retname[retnamlen] = ',';
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  72) 		sprintf(retname+retnamlen+1, "%3.3x",
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  73) 			((chr[12] & 0xf) << 8) | chr[11]);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  74) 		retnamlen += 4;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  75) 	}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  76) 	return retnamlen;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  77) }
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  78) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  79) /*
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  80)  * This should _really_ be cleaned up some day..
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  81)  */
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400  82) static int do_isofs_readdir(struct inode *inode, struct file *file,
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400  83) 		struct dir_context *ctx,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700  84) 		char *tmpname, struct iso_directory_record *tmpde)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  85) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  86) 	unsigned long bufsize = ISOFS_BUFFER_SIZE(inode);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  87) 	unsigned char bufbits = ISOFS_BUFFER_BITS(inode);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  88) 	unsigned long block, offset, block_saved, offset_saved;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  89) 	unsigned long inode_number = 0;	/* Quiet GCC */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  90) 	struct buffer_head *bh = NULL;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  91) 	int len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  92) 	int map;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  93) 	int first_de = 1;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  94) 	char *p = NULL;		/* Quiet GCC */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  95) 	struct iso_directory_record *de;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  96) 	struct isofs_sb_info *sbi = ISOFS_SB(inode->i_sb);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700  97) 
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400  98) 	offset = ctx->pos & (bufsize - 1);
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400  99) 	block = ctx->pos >> bufbits;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 100) 
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 101) 	while (ctx->pos < inode->i_size) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 102) 		int de_len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 103) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 104) 		if (!bh) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 105) 			bh = isofs_bread(inode, block);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 106) 			if (!bh)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 107) 				return 0;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 108) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 109) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 110) 		de = (struct iso_directory_record *) (bh->b_data + offset);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 111) 
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 112) 		de_len = *(unsigned char *)de;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 113) 
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 114) 		/*
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 115) 		 * If the length byte is zero, we should move on to the next
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 116) 		 * CDROM sector.  If we are at the end of the directory, we
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 117) 		 * kick out of the while loop.
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 118) 		 */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 119) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 120) 		if (de_len == 0) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 121) 			brelse(bh);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 122) 			bh = NULL;
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 123) 			ctx->pos = (ctx->pos + ISOFS_BLOCK_SIZE) & ~(ISOFS_BLOCK_SIZE - 1);
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 124) 			block = ctx->pos >> bufbits;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 125) 			offset = 0;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 126) 			continue;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 127) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 128) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 129) 		block_saved = block;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 130) 		offset_saved = offset;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 131) 		offset += de_len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 132) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 133) 		/* Make sure we have a full directory entry */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 134) 		if (offset >= bufsize) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 135) 			int slop = bufsize - offset + de_len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 136) 			memcpy(tmpde, de, slop);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 137) 			offset &= bufsize - 1;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 138) 			block++;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 139) 			brelse(bh);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 140) 			bh = NULL;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 141) 			if (offset) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 142) 				bh = isofs_bread(inode, block);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 143) 				if (!bh)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 144) 					return 0;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 145) 				memcpy((void *) tmpde + slop, bh->b_data, offset);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 146) 			}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 147) 			de = tmpde;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 148) 		}
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 149) 		/* Basic sanity check, whether name doesn't exceed dir entry */
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 150) 		if (de_len < de->name_len[0] +
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 151) 					sizeof(struct iso_directory_record)) {
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 152) 			printk(KERN_NOTICE "iso9660: Corrupted directory entry"
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 153) 			       " in block %lu of inode %lu\n", block,
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 154) 			       inode->i_ino);
0a6dc67a6aa45 (Pan Bian           2021-01-18 04:04:55 -0800 155) 			brelse(bh);
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 156) 			return -EIO;
2deb1acc653cb (Jan Kara           2008-04-30 00:52:33 -0700 157) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 158) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 159) 		if (first_de) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 160) 			isofs_normalize_block_and_offset(de,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 161) 							&block_saved,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 162) 							&offset_saved);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 163) 			inode_number = isofs_get_ino(block_saved,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 164) 							offset_saved, bufbits);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 165) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 166) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 167) 		if (de->flags[-sbi->s_high_sierra] & 0x80) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 168) 			first_de = 0;
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 169) 			ctx->pos += de_len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 170) 			continue;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 171) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 172) 		first_de = 1;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 173) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 174) 		/* Handle the case of the '.' directory */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 175) 		if (de->name_len[0] == 1 && de->name[0] == 0) {
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 176) 			if (!dir_emit_dot(file, ctx))
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 177) 				break;
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 178) 			ctx->pos += de_len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 179) 			continue;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 180) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 181) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 182) 		len = 0;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 183) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 184) 		/* Handle the case of the '..' directory */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 185) 		if (de->name_len[0] == 1 && de->name[0] == 1) {
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 186) 			if (!dir_emit_dotdot(file, ctx))
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 187) 				break;
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 188) 			ctx->pos += de_len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 189) 			continue;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 190) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 191) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 192) 		/* Handle everything else.  Do name translation if there
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 193) 		   is no Rock Ridge NM field. */
9769f4eb3fad2 (Jeremy White       2005-06-21 17:16:53 -0700 194) 
9769f4eb3fad2 (Jeremy White       2005-06-21 17:16:53 -0700 195) 		/*
9769f4eb3fad2 (Jeremy White       2005-06-21 17:16:53 -0700 196) 		 * Do not report hidden files if so instructed, or associated
9769f4eb3fad2 (Jeremy White       2005-06-21 17:16:53 -0700 197) 		 * files unless instructed to do so
9769f4eb3fad2 (Jeremy White       2005-06-21 17:16:53 -0700 198) 		 */
5404ac8e4418a (Jan Kara           2009-06-17 16:26:27 -0700 199) 		if ((sbi->s_hide && (de->flags[-sbi->s_high_sierra] & 1)) ||
5404ac8e4418a (Jan Kara           2009-06-17 16:26:27 -0700 200) 		    (!sbi->s_showassoc &&
9769f4eb3fad2 (Jeremy White       2005-06-21 17:16:53 -0700 201) 				(de->flags[-sbi->s_high_sierra] & 4))) {
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 202) 			ctx->pos += de_len;
9769f4eb3fad2 (Jeremy White       2005-06-21 17:16:53 -0700 203) 			continue;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 204) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 205) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 206) 		map = 1;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 207) 		if (sbi->s_rock) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 208) 			len = get_rock_ridge_filename(de, tmpname, inode);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 209) 			if (len != 0) {		/* may be -1 */
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 210) 				p = tmpname;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 211) 				map = 0;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 212) 			}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 213) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 214) 		if (map) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 215) #ifdef CONFIG_JOLIET
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 216) 			if (sbi->s_joliet_level) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 217) 				len = get_joliet_filename(de, tmpname, inode);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 218) 				p = tmpname;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 219) 			} else
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 220) #endif
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 221) 			if (sbi->s_mapping == 'a') {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 222) 				len = get_acorn_filename(de, tmpname, inode);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 223) 				p = tmpname;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 224) 			} else
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 225) 			if (sbi->s_mapping == 'n') {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 226) 				len = isofs_name_translate(de, tmpname, inode);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 227) 				p = tmpname;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 228) 			} else {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 229) 				p = de->name;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 230) 				len = de->name_len[0];
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 231) 			}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 232) 		}
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 233) 		if (len > 0) {
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 234) 			if (!dir_emit(ctx, p, len, inode_number, DT_UNKNOWN))
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 235) 				break;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 236) 		}
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 237) 		ctx->pos += de_len;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 238) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 239) 		continue;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 240) 	}
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 241) 	if (bh)
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 242) 		brelse(bh);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 243) 	return 0;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 244) }
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 245) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 246) /*
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 247)  * Handle allocation of temporary space for name translation and
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 248)  * handling split directory entries.. The real work is done by
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 249)  * "do_isofs_readdir()".
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 250)  */
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 251) static int isofs_readdir(struct file *file, struct dir_context *ctx)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 252) {
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 253) 	int result;
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 254) 	char *tmpname;
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 255) 	struct iso_directory_record *tmpde;
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 256) 	struct inode *inode = file_inode(file);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 257) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 258) 	tmpname = (char *)__get_free_page(GFP_KERNEL);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 259) 	if (tmpname == NULL)
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 260) 		return -ENOMEM;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 261) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 262) 	tmpde = (struct iso_directory_record *) (tmpname+1024);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 263) 
bfee7169c0210 (Al Viro            2013-05-17 21:11:59 -0400 264) 	result = do_isofs_readdir(inode, file, ctx, tmpname, tmpde);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 265) 
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 266) 	free_page((unsigned long) tmpname);
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 267) 	return result;
^1da177e4c3f4 (Linus Torvalds     2005-04-16 15:20:36 -0700 268) }
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 269) 
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 270) const struct file_operations isofs_dir_operations =
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 271) {
ca572727dbb94 (jan Blunck         2010-05-26 14:44:53 -0700 272) 	.llseek = generic_file_llseek,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 273) 	.read = generic_read_dir,
e899108994540 (Al Viro            2016-05-09 12:53:03 -0400 274) 	.iterate_shared = isofs_readdir,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 275) };
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 276) 
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 277) /*
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 278)  * directories can handle most operations...
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 279)  */
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 280) const struct inode_operations isofs_dir_inode_operations =
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 281) {
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 282) 	.lookup = isofs_lookup,
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 283) };
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 284) 
c3ed85a36ff5b (Dave Jones         2007-07-15 23:40:03 -0700 285)