0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025 #include "ext2.h"
0026 #include <linux/buffer_head.h>
0027 #include <linux/pagemap.h>
0028 #include <linux/swap.h>
0029 #include <linux/iversion.h>
0030
0031 typedef struct ext2_dir_entry_2 ext2_dirent;
0032
0033
0034
0035
0036
0037
0038 static inline unsigned ext2_rec_len_from_disk(__le16 dlen)
0039 {
0040 unsigned len = le16_to_cpu(dlen);
0041
0042 #if (PAGE_SIZE >= 65536)
0043 if (len == EXT2_MAX_REC_LEN)
0044 return 1 << 16;
0045 #endif
0046 return len;
0047 }
0048
0049 static inline __le16 ext2_rec_len_to_disk(unsigned len)
0050 {
0051 #if (PAGE_SIZE >= 65536)
0052 if (len == (1 << 16))
0053 return cpu_to_le16(EXT2_MAX_REC_LEN);
0054 else
0055 BUG_ON(len > (1 << 16));
0056 #endif
0057 return cpu_to_le16(len);
0058 }
0059
0060
0061
0062
0063
0064 static inline unsigned ext2_chunk_size(struct inode *inode)
0065 {
0066 return inode->i_sb->s_blocksize;
0067 }
0068
0069
0070
0071
0072
0073 static unsigned
0074 ext2_last_byte(struct inode *inode, unsigned long page_nr)
0075 {
0076 unsigned last_byte = inode->i_size;
0077
0078 last_byte -= page_nr << PAGE_SHIFT;
0079 if (last_byte > PAGE_SIZE)
0080 last_byte = PAGE_SIZE;
0081 return last_byte;
0082 }
0083
0084 static int ext2_commit_chunk(struct page *page, loff_t pos, unsigned len)
0085 {
0086 struct address_space *mapping = page->mapping;
0087 struct inode *dir = mapping->host;
0088 int err = 0;
0089
0090 inode_inc_iversion(dir);
0091 block_write_end(NULL, mapping, pos, len, len, page, NULL);
0092
0093 if (pos+len > dir->i_size) {
0094 i_size_write(dir, pos+len);
0095 mark_inode_dirty(dir);
0096 }
0097
0098 if (IS_DIRSYNC(dir)) {
0099 err = write_one_page(page);
0100 if (!err)
0101 err = sync_inode_metadata(dir, 1);
0102 } else {
0103 unlock_page(page);
0104 }
0105
0106 return err;
0107 }
0108
0109 static bool ext2_check_page(struct page *page, int quiet, char *kaddr)
0110 {
0111 struct inode *dir = page->mapping->host;
0112 struct super_block *sb = dir->i_sb;
0113 unsigned chunk_size = ext2_chunk_size(dir);
0114 u32 max_inumber = le32_to_cpu(EXT2_SB(sb)->s_es->s_inodes_count);
0115 unsigned offs, rec_len;
0116 unsigned limit = PAGE_SIZE;
0117 ext2_dirent *p;
0118 char *error;
0119
0120 if ((dir->i_size >> PAGE_SHIFT) == page->index) {
0121 limit = dir->i_size & ~PAGE_MASK;
0122 if (limit & (chunk_size - 1))
0123 goto Ebadsize;
0124 if (!limit)
0125 goto out;
0126 }
0127 for (offs = 0; offs <= limit - EXT2_DIR_REC_LEN(1); offs += rec_len) {
0128 p = (ext2_dirent *)(kaddr + offs);
0129 rec_len = ext2_rec_len_from_disk(p->rec_len);
0130
0131 if (unlikely(rec_len < EXT2_DIR_REC_LEN(1)))
0132 goto Eshort;
0133 if (unlikely(rec_len & 3))
0134 goto Ealign;
0135 if (unlikely(rec_len < EXT2_DIR_REC_LEN(p->name_len)))
0136 goto Enamelen;
0137 if (unlikely(((offs + rec_len - 1) ^ offs) & ~(chunk_size-1)))
0138 goto Espan;
0139 if (unlikely(le32_to_cpu(p->inode) > max_inumber))
0140 goto Einumber;
0141 }
0142 if (offs != limit)
0143 goto Eend;
0144 out:
0145 SetPageChecked(page);
0146 return true;
0147
0148
0149
0150 Ebadsize:
0151 if (!quiet)
0152 ext2_error(sb, __func__,
0153 "size of directory #%lu is not a multiple "
0154 "of chunk size", dir->i_ino);
0155 goto fail;
0156 Eshort:
0157 error = "rec_len is smaller than minimal";
0158 goto bad_entry;
0159 Ealign:
0160 error = "unaligned directory entry";
0161 goto bad_entry;
0162 Enamelen:
0163 error = "rec_len is too small for name_len";
0164 goto bad_entry;
0165 Espan:
0166 error = "directory entry across blocks";
0167 goto bad_entry;
0168 Einumber:
0169 error = "inode out of bounds";
0170 bad_entry:
0171 if (!quiet)
0172 ext2_error(sb, __func__, "bad entry in directory #%lu: : %s - "
0173 "offset=%lu, inode=%lu, rec_len=%d, name_len=%d",
0174 dir->i_ino, error, (page->index<<PAGE_SHIFT)+offs,
0175 (unsigned long) le32_to_cpu(p->inode),
0176 rec_len, p->name_len);
0177 goto fail;
0178 Eend:
0179 if (!quiet) {
0180 p = (ext2_dirent *)(kaddr + offs);
0181 ext2_error(sb, "ext2_check_page",
0182 "entry in directory #%lu spans the page boundary"
0183 "offset=%lu, inode=%lu",
0184 dir->i_ino, (page->index<<PAGE_SHIFT)+offs,
0185 (unsigned long) le32_to_cpu(p->inode));
0186 }
0187 fail:
0188 SetPageError(page);
0189 return false;
0190 }
0191
0192
0193
0194
0195
0196
0197
0198
0199 static struct page * ext2_get_page(struct inode *dir, unsigned long n,
0200 int quiet, void **page_addr)
0201 {
0202 struct address_space *mapping = dir->i_mapping;
0203 struct folio *folio = read_mapping_folio(mapping, n, NULL);
0204
0205 if (IS_ERR(folio))
0206 return &folio->page;
0207 *page_addr = kmap_local_folio(folio, n & (folio_nr_pages(folio) - 1));
0208 if (unlikely(!folio_test_checked(folio))) {
0209 if (!ext2_check_page(&folio->page, quiet, *page_addr))
0210 goto fail;
0211 }
0212 return &folio->page;
0213
0214 fail:
0215 ext2_put_page(&folio->page, *page_addr);
0216 return ERR_PTR(-EIO);
0217 }
0218
0219
0220
0221
0222
0223
0224 static inline int ext2_match (int len, const char * const name,
0225 struct ext2_dir_entry_2 * de)
0226 {
0227 if (len != de->name_len)
0228 return 0;
0229 if (!de->inode)
0230 return 0;
0231 return !memcmp(name, de->name, len);
0232 }
0233
0234
0235
0236
0237 static inline ext2_dirent *ext2_next_entry(ext2_dirent *p)
0238 {
0239 return (ext2_dirent *)((char *)p +
0240 ext2_rec_len_from_disk(p->rec_len));
0241 }
0242
0243 static inline unsigned
0244 ext2_validate_entry(char *base, unsigned offset, unsigned mask)
0245 {
0246 ext2_dirent *de = (ext2_dirent*)(base + offset);
0247 ext2_dirent *p = (ext2_dirent*)(base + (offset&mask));
0248 while ((char*)p < (char*)de) {
0249 if (p->rec_len == 0)
0250 break;
0251 p = ext2_next_entry(p);
0252 }
0253 return (char *)p - base;
0254 }
0255
0256 static inline void ext2_set_de_type(ext2_dirent *de, struct inode *inode)
0257 {
0258 if (EXT2_HAS_INCOMPAT_FEATURE(inode->i_sb, EXT2_FEATURE_INCOMPAT_FILETYPE))
0259 de->file_type = fs_umode_to_ftype(inode->i_mode);
0260 else
0261 de->file_type = 0;
0262 }
0263
0264 static int
0265 ext2_readdir(struct file *file, struct dir_context *ctx)
0266 {
0267 loff_t pos = ctx->pos;
0268 struct inode *inode = file_inode(file);
0269 struct super_block *sb = inode->i_sb;
0270 unsigned int offset = pos & ~PAGE_MASK;
0271 unsigned long n = pos >> PAGE_SHIFT;
0272 unsigned long npages = dir_pages(inode);
0273 unsigned chunk_mask = ~(ext2_chunk_size(inode)-1);
0274 bool need_revalidate = !inode_eq_iversion(inode, file->f_version);
0275 bool has_filetype;
0276
0277 if (pos > inode->i_size - EXT2_DIR_REC_LEN(1))
0278 return 0;
0279
0280 has_filetype =
0281 EXT2_HAS_INCOMPAT_FEATURE(sb, EXT2_FEATURE_INCOMPAT_FILETYPE);
0282
0283 for ( ; n < npages; n++, offset = 0) {
0284 char *kaddr, *limit;
0285 ext2_dirent *de;
0286 struct page *page = ext2_get_page(inode, n, 0, (void **)&kaddr);
0287
0288 if (IS_ERR(page)) {
0289 ext2_error(sb, __func__,
0290 "bad page in #%lu",
0291 inode->i_ino);
0292 ctx->pos += PAGE_SIZE - offset;
0293 return PTR_ERR(page);
0294 }
0295 if (unlikely(need_revalidate)) {
0296 if (offset) {
0297 offset = ext2_validate_entry(kaddr, offset, chunk_mask);
0298 ctx->pos = (n<<PAGE_SHIFT) + offset;
0299 }
0300 file->f_version = inode_query_iversion(inode);
0301 need_revalidate = false;
0302 }
0303 de = (ext2_dirent *)(kaddr+offset);
0304 limit = kaddr + ext2_last_byte(inode, n) - EXT2_DIR_REC_LEN(1);
0305 for ( ;(char*)de <= limit; de = ext2_next_entry(de)) {
0306 if (de->rec_len == 0) {
0307 ext2_error(sb, __func__,
0308 "zero-length directory entry");
0309 ext2_put_page(page, kaddr);
0310 return -EIO;
0311 }
0312 if (de->inode) {
0313 unsigned char d_type = DT_UNKNOWN;
0314
0315 if (has_filetype)
0316 d_type = fs_ftype_to_dtype(de->file_type);
0317
0318 if (!dir_emit(ctx, de->name, de->name_len,
0319 le32_to_cpu(de->inode),
0320 d_type)) {
0321 ext2_put_page(page, kaddr);
0322 return 0;
0323 }
0324 }
0325 ctx->pos += ext2_rec_len_from_disk(de->rec_len);
0326 }
0327 ext2_put_page(page, kaddr);
0328 }
0329 return 0;
0330 }
0331
0332
0333
0334
0335
0336
0337
0338
0339
0340
0341
0342
0343
0344
0345
0346
0347
0348 struct ext2_dir_entry_2 *ext2_find_entry (struct inode *dir,
0349 const struct qstr *child, struct page **res_page,
0350 void **res_page_addr)
0351 {
0352 const char *name = child->name;
0353 int namelen = child->len;
0354 unsigned reclen = EXT2_DIR_REC_LEN(namelen);
0355 unsigned long start, n;
0356 unsigned long npages = dir_pages(dir);
0357 struct page *page = NULL;
0358 struct ext2_inode_info *ei = EXT2_I(dir);
0359 ext2_dirent * de;
0360 void *page_addr;
0361
0362 if (npages == 0)
0363 goto out;
0364
0365
0366 *res_page = NULL;
0367 *res_page_addr = NULL;
0368
0369 start = ei->i_dir_start_lookup;
0370 if (start >= npages)
0371 start = 0;
0372 n = start;
0373 do {
0374 char *kaddr;
0375 page = ext2_get_page(dir, n, 0, &page_addr);
0376 if (IS_ERR(page))
0377 return ERR_CAST(page);
0378
0379 kaddr = page_addr;
0380 de = (ext2_dirent *) kaddr;
0381 kaddr += ext2_last_byte(dir, n) - reclen;
0382 while ((char *) de <= kaddr) {
0383 if (de->rec_len == 0) {
0384 ext2_error(dir->i_sb, __func__,
0385 "zero-length directory entry");
0386 ext2_put_page(page, page_addr);
0387 goto out;
0388 }
0389 if (ext2_match(namelen, name, de))
0390 goto found;
0391 de = ext2_next_entry(de);
0392 }
0393 ext2_put_page(page, page_addr);
0394
0395 if (++n >= npages)
0396 n = 0;
0397
0398 if (unlikely(n > (dir->i_blocks >> (PAGE_SHIFT - 9)))) {
0399 ext2_error(dir->i_sb, __func__,
0400 "dir %lu size %lld exceeds block count %llu",
0401 dir->i_ino, dir->i_size,
0402 (unsigned long long)dir->i_blocks);
0403 goto out;
0404 }
0405 } while (n != start);
0406 out:
0407 return ERR_PTR(-ENOENT);
0408
0409 found:
0410 *res_page = page;
0411 *res_page_addr = page_addr;
0412 ei->i_dir_start_lookup = n;
0413 return de;
0414 }
0415
0416
0417
0418
0419
0420
0421
0422
0423
0424
0425
0426
0427
0428 struct ext2_dir_entry_2 *ext2_dotdot(struct inode *dir, struct page **p,
0429 void **pa)
0430 {
0431 void *page_addr;
0432 struct page *page = ext2_get_page(dir, 0, 0, &page_addr);
0433 ext2_dirent *de = NULL;
0434
0435 if (!IS_ERR(page)) {
0436 de = ext2_next_entry((ext2_dirent *) page_addr);
0437 *p = page;
0438 *pa = page_addr;
0439 }
0440 return de;
0441 }
0442
0443 int ext2_inode_by_name(struct inode *dir, const struct qstr *child, ino_t *ino)
0444 {
0445 struct ext2_dir_entry_2 *de;
0446 struct page *page;
0447 void *page_addr;
0448
0449 de = ext2_find_entry(dir, child, &page, &page_addr);
0450 if (IS_ERR(de))
0451 return PTR_ERR(de);
0452
0453 *ino = le32_to_cpu(de->inode);
0454 ext2_put_page(page, page_addr);
0455 return 0;
0456 }
0457
0458 static int ext2_prepare_chunk(struct page *page, loff_t pos, unsigned len)
0459 {
0460 return __block_write_begin(page, pos, len, ext2_get_block);
0461 }
0462
0463 void ext2_set_link(struct inode *dir, struct ext2_dir_entry_2 *de,
0464 struct page *page, void *page_addr, struct inode *inode,
0465 int update_times)
0466 {
0467 loff_t pos = page_offset(page) +
0468 (char *) de - (char *) page_addr;
0469 unsigned len = ext2_rec_len_from_disk(de->rec_len);
0470 int err;
0471
0472 lock_page(page);
0473 err = ext2_prepare_chunk(page, pos, len);
0474 BUG_ON(err);
0475 de->inode = cpu_to_le32(inode->i_ino);
0476 ext2_set_de_type(de, inode);
0477 err = ext2_commit_chunk(page, pos, len);
0478 if (update_times)
0479 dir->i_mtime = dir->i_ctime = current_time(dir);
0480 EXT2_I(dir)->i_flags &= ~EXT2_BTREE_FL;
0481 mark_inode_dirty(dir);
0482 }
0483
0484
0485
0486
0487 int ext2_add_link (struct dentry *dentry, struct inode *inode)
0488 {
0489 struct inode *dir = d_inode(dentry->d_parent);
0490 const char *name = dentry->d_name.name;
0491 int namelen = dentry->d_name.len;
0492 unsigned chunk_size = ext2_chunk_size(dir);
0493 unsigned reclen = EXT2_DIR_REC_LEN(namelen);
0494 unsigned short rec_len, name_len;
0495 struct page *page = NULL;
0496 void *page_addr = NULL;
0497 ext2_dirent * de;
0498 unsigned long npages = dir_pages(dir);
0499 unsigned long n;
0500 loff_t pos;
0501 int err;
0502
0503
0504
0505
0506
0507
0508 for (n = 0; n <= npages; n++) {
0509 char *kaddr;
0510 char *dir_end;
0511
0512 page = ext2_get_page(dir, n, 0, &page_addr);
0513 err = PTR_ERR(page);
0514 if (IS_ERR(page))
0515 goto out;
0516 lock_page(page);
0517 kaddr = page_addr;
0518 dir_end = kaddr + ext2_last_byte(dir, n);
0519 de = (ext2_dirent *)kaddr;
0520 kaddr += PAGE_SIZE - reclen;
0521 while ((char *)de <= kaddr) {
0522 if ((char *)de == dir_end) {
0523
0524 name_len = 0;
0525 rec_len = chunk_size;
0526 de->rec_len = ext2_rec_len_to_disk(chunk_size);
0527 de->inode = 0;
0528 goto got_it;
0529 }
0530 if (de->rec_len == 0) {
0531 ext2_error(dir->i_sb, __func__,
0532 "zero-length directory entry");
0533 err = -EIO;
0534 goto out_unlock;
0535 }
0536 err = -EEXIST;
0537 if (ext2_match (namelen, name, de))
0538 goto out_unlock;
0539 name_len = EXT2_DIR_REC_LEN(de->name_len);
0540 rec_len = ext2_rec_len_from_disk(de->rec_len);
0541 if (!de->inode && rec_len >= reclen)
0542 goto got_it;
0543 if (rec_len >= name_len + reclen)
0544 goto got_it;
0545 de = (ext2_dirent *) ((char *) de + rec_len);
0546 }
0547 unlock_page(page);
0548 ext2_put_page(page, page_addr);
0549 }
0550 BUG();
0551 return -EINVAL;
0552
0553 got_it:
0554 pos = page_offset(page) +
0555 (char *)de - (char *)page_addr;
0556 err = ext2_prepare_chunk(page, pos, rec_len);
0557 if (err)
0558 goto out_unlock;
0559 if (de->inode) {
0560 ext2_dirent *de1 = (ext2_dirent *) ((char *) de + name_len);
0561 de1->rec_len = ext2_rec_len_to_disk(rec_len - name_len);
0562 de->rec_len = ext2_rec_len_to_disk(name_len);
0563 de = de1;
0564 }
0565 de->name_len = namelen;
0566 memcpy(de->name, name, namelen);
0567 de->inode = cpu_to_le32(inode->i_ino);
0568 ext2_set_de_type (de, inode);
0569 err = ext2_commit_chunk(page, pos, rec_len);
0570 dir->i_mtime = dir->i_ctime = current_time(dir);
0571 EXT2_I(dir)->i_flags &= ~EXT2_BTREE_FL;
0572 mark_inode_dirty(dir);
0573
0574 out_put:
0575 ext2_put_page(page, page_addr);
0576 out:
0577 return err;
0578 out_unlock:
0579 unlock_page(page);
0580 goto out_put;
0581 }
0582
0583
0584
0585
0586
0587 int ext2_delete_entry (struct ext2_dir_entry_2 *dir, struct page *page,
0588 char *kaddr)
0589 {
0590 struct inode *inode = page->mapping->host;
0591 unsigned from = ((char*)dir - kaddr) & ~(ext2_chunk_size(inode)-1);
0592 unsigned to = ((char *)dir - kaddr) +
0593 ext2_rec_len_from_disk(dir->rec_len);
0594 loff_t pos;
0595 ext2_dirent * pde = NULL;
0596 ext2_dirent * de = (ext2_dirent *) (kaddr + from);
0597 int err;
0598
0599 while ((char*)de < (char*)dir) {
0600 if (de->rec_len == 0) {
0601 ext2_error(inode->i_sb, __func__,
0602 "zero-length directory entry");
0603 err = -EIO;
0604 goto out;
0605 }
0606 pde = de;
0607 de = ext2_next_entry(de);
0608 }
0609 if (pde)
0610 from = (char *)pde - kaddr;
0611 pos = page_offset(page) + from;
0612 lock_page(page);
0613 err = ext2_prepare_chunk(page, pos, to - from);
0614 BUG_ON(err);
0615 if (pde)
0616 pde->rec_len = ext2_rec_len_to_disk(to - from);
0617 dir->inode = 0;
0618 err = ext2_commit_chunk(page, pos, to - from);
0619 inode->i_ctime = inode->i_mtime = current_time(inode);
0620 EXT2_I(inode)->i_flags &= ~EXT2_BTREE_FL;
0621 mark_inode_dirty(inode);
0622 out:
0623 return err;
0624 }
0625
0626
0627
0628
0629 int ext2_make_empty(struct inode *inode, struct inode *parent)
0630 {
0631 struct page *page = grab_cache_page(inode->i_mapping, 0);
0632 unsigned chunk_size = ext2_chunk_size(inode);
0633 struct ext2_dir_entry_2 * de;
0634 int err;
0635 void *kaddr;
0636
0637 if (!page)
0638 return -ENOMEM;
0639
0640 err = ext2_prepare_chunk(page, 0, chunk_size);
0641 if (err) {
0642 unlock_page(page);
0643 goto fail;
0644 }
0645 kaddr = kmap_atomic(page);
0646 memset(kaddr, 0, chunk_size);
0647 de = (struct ext2_dir_entry_2 *)kaddr;
0648 de->name_len = 1;
0649 de->rec_len = ext2_rec_len_to_disk(EXT2_DIR_REC_LEN(1));
0650 memcpy (de->name, ".\0\0", 4);
0651 de->inode = cpu_to_le32(inode->i_ino);
0652 ext2_set_de_type (de, inode);
0653
0654 de = (struct ext2_dir_entry_2 *)(kaddr + EXT2_DIR_REC_LEN(1));
0655 de->name_len = 2;
0656 de->rec_len = ext2_rec_len_to_disk(chunk_size - EXT2_DIR_REC_LEN(1));
0657 de->inode = cpu_to_le32(parent->i_ino);
0658 memcpy (de->name, "..\0", 4);
0659 ext2_set_de_type (de, inode);
0660 kunmap_atomic(kaddr);
0661 err = ext2_commit_chunk(page, 0, chunk_size);
0662 fail:
0663 put_page(page);
0664 return err;
0665 }
0666
0667
0668
0669
0670 int ext2_empty_dir (struct inode * inode)
0671 {
0672 void *page_addr = NULL;
0673 struct page *page = NULL;
0674 unsigned long i, npages = dir_pages(inode);
0675
0676 for (i = 0; i < npages; i++) {
0677 char *kaddr;
0678 ext2_dirent * de;
0679 page = ext2_get_page(inode, i, 0, &page_addr);
0680
0681 if (IS_ERR(page))
0682 goto not_empty;
0683
0684 kaddr = page_addr;
0685 de = (ext2_dirent *)kaddr;
0686 kaddr += ext2_last_byte(inode, i) - EXT2_DIR_REC_LEN(1);
0687
0688 while ((char *)de <= kaddr) {
0689 if (de->rec_len == 0) {
0690 ext2_error(inode->i_sb, __func__,
0691 "zero-length directory entry");
0692 printk("kaddr=%p, de=%p\n", kaddr, de);
0693 goto not_empty;
0694 }
0695 if (de->inode != 0) {
0696
0697 if (de->name[0] != '.')
0698 goto not_empty;
0699 if (de->name_len > 2)
0700 goto not_empty;
0701 if (de->name_len < 2) {
0702 if (de->inode !=
0703 cpu_to_le32(inode->i_ino))
0704 goto not_empty;
0705 } else if (de->name[1] != '.')
0706 goto not_empty;
0707 }
0708 de = ext2_next_entry(de);
0709 }
0710 ext2_put_page(page, page_addr);
0711 }
0712 return 1;
0713
0714 not_empty:
0715 ext2_put_page(page, page_addr);
0716 return 0;
0717 }
0718
0719 const struct file_operations ext2_dir_operations = {
0720 .llseek = generic_file_llseek,
0721 .read = generic_read_dir,
0722 .iterate_shared = ext2_readdir,
0723 .unlocked_ioctl = ext2_ioctl,
0724 #ifdef CONFIG_COMPAT
0725 .compat_ioctl = ext2_compat_ioctl,
0726 #endif
0727 .fsync = ext2_fsync,
0728 };