Commit 5add2ee198723c3fec3ce4a7d77de298344f6ba8

Authored by Al Viro
1 parent 5ded75ec4c

[readdir] convert udf

Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>

Showing 1 changed file with 26 additions and 37 deletions Side-by-side Diff

... ... @@ -35,14 +35,16 @@
35 35 #include "udf_i.h"
36 36 #include "udf_sb.h"
37 37  
38   -static int do_udf_readdir(struct inode *dir, struct file *filp,
39   - filldir_t filldir, void *dirent)
  38 +
  39 +static int udf_readdir(struct file *file, struct dir_context *ctx)
40 40 {
  41 + struct inode *dir = file_inode(file);
  42 + struct udf_inode_info *iinfo = UDF_I(dir);
41 43 struct udf_fileident_bh fibh = { .sbh = NULL, .ebh = NULL};
42 44 struct fileIdentDesc *fi = NULL;
43 45 struct fileIdentDesc cfi;
44 46 int block, iblock;
45   - loff_t nf_pos = (filp->f_pos - 1) << 2;
  47 + loff_t nf_pos;
46 48 int flen;
47 49 unsigned char *fname = NULL;
48 50 unsigned char *nameptr;
49 51  
50 52  
... ... @@ -54,10 +56,14 @@
54 56 uint32_t elen;
55 57 sector_t offset;
56 58 int i, num, ret = 0;
57   - unsigned int dt_type;
58 59 struct extent_position epos = { NULL, 0, {0, 0} };
59   - struct udf_inode_info *iinfo;
60 60  
  61 + if (ctx->pos == 0) {
  62 + if (!dir_emit_dot(file, ctx))
  63 + return 0;
  64 + ctx->pos = 1;
  65 + }
  66 + nf_pos = (ctx->pos - 1) << 2;
61 67 if (nf_pos >= size)
62 68 goto out;
63 69  
... ... @@ -71,7 +77,6 @@
71 77 nf_pos = udf_ext0_offset(dir);
72 78  
73 79 fibh.soffset = fibh.eoffset = nf_pos & (dir->i_sb->s_blocksize - 1);
74   - iinfo = UDF_I(dir);
75 80 if (iinfo->i_alloc_type != ICBTAG_FLAG_AD_IN_ICB) {
76 81 if (inode_bmap(dir, nf_pos >> dir->i_sb->s_blocksize_bits,
77 82 &epos, &eloc, &elen, &offset)
78 83  
... ... @@ -116,8 +121,10 @@
116 121 }
117 122  
118 123 while (nf_pos < size) {
119   - filp->f_pos = (nf_pos >> 2) + 1;
  124 + struct kernel_lb_addr tloc;
120 125  
  126 + ctx->pos = (nf_pos >> 2) + 1;
  127 +
121 128 fi = udf_fileident_read(dir, &nf_pos, &fibh, &cfi, &epos, &eloc,
122 129 &elen, &offset);
123 130 if (!fi)
124 131  
125 132  
... ... @@ -155,24 +162,22 @@
155 162 }
156 163  
157 164 if (cfi.fileCharacteristics & FID_FILE_CHAR_PARENT) {
158   - iblock = parent_ino(filp->f_path.dentry);
159   - flen = 2;
160   - memcpy(fname, "..", flen);
161   - dt_type = DT_DIR;
162   - } else {
163   - struct kernel_lb_addr tloc = lelb_to_cpu(cfi.icb.extLocation);
164   -
165   - iblock = udf_get_lb_pblock(dir->i_sb, &tloc, 0);
166   - flen = udf_get_filename(dir->i_sb, nameptr, fname, lfi);
167   - dt_type = DT_UNKNOWN;
  165 + if (!dir_emit_dotdot(file, ctx))
  166 + goto out;
  167 + continue;
168 168 }
169 169  
170   - if (flen && filldir(dirent, fname, flen, filp->f_pos,
171   - iblock, dt_type) < 0)
  170 + flen = udf_get_filename(dir->i_sb, nameptr, fname, lfi);
  171 + if (!flen)
  172 + continue;
  173 +
  174 + tloc = lelb_to_cpu(cfi.icb.extLocation);
  175 + iblock = udf_get_lb_pblock(dir->i_sb, &tloc, 0);
  176 + if (!dir_emit(ctx, fname, flen, iblock, DT_UNKNOWN))
172 177 goto out;
173 178 } /* end while */
174 179  
175   - filp->f_pos = (nf_pos >> 2) + 1;
  180 + ctx->pos = (nf_pos >> 2) + 1;
176 181  
177 182 out:
178 183 if (fibh.sbh != fibh.ebh)
179 184  
... ... @@ -184,27 +189,11 @@
184 189 return ret;
185 190 }
186 191  
187   -static int udf_readdir(struct file *filp, void *dirent, filldir_t filldir)
188   -{
189   - struct inode *dir = file_inode(filp);
190   - int result;
191   -
192   - if (filp->f_pos == 0) {
193   - if (filldir(dirent, ".", 1, filp->f_pos, dir->i_ino, DT_DIR) < 0) {
194   - return 0;
195   - }
196   - filp->f_pos++;
197   - }
198   -
199   - result = do_udf_readdir(dir, filp, filldir, dirent);
200   - return result;
201   -}
202   -
203 192 /* readdir and lookup functions */
204 193 const struct file_operations udf_dir_operations = {
205 194 .llseek = generic_file_llseek,
206 195 .read = generic_read_dir,
207   - .readdir = udf_readdir,
  196 + .iterate = udf_readdir,
208 197 .unlocked_ioctl = udf_ioctl,
209 198 .fsync = generic_file_fsync,
210 199 };