Skip to content

Commit 87ca34a

Browse files
committed
erofs: get rid of `struct z_erofs_collection'
It was incompletely introduced for deduplication between different logical extents backed with the same pcluster. We will have a better in-memory representation in the next release cycle for this, as well as partial memory folios support. So get rid of it instead. No logic changes. Link: https://lore.kernel.org/r/20220529055425.226363-2-xiang@kernel.org Acked-by: Chao Yu <chao@kernel.org> Signed-off-by: Gao Xiang <hsiangkao@linux.alibaba.com>
1 parent 6e95d0a commit 87ca34a

File tree

2 files changed

+65
-96
lines changed

2 files changed

+65
-96
lines changed

fs/erofs/zdata.c

Lines changed: 43 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -199,7 +199,6 @@ struct z_erofs_decompress_frontend {
199199
struct z_erofs_pagevec_ctor vector;
200200

201201
struct z_erofs_pcluster *pcl, *tailpcl;
202-
struct z_erofs_collection *cl;
203202
/* a pointer used to pick up inplace I/O pages */
204203
struct page **icpage_ptr;
205204
z_erofs_next_pcluster_t owned_head;
@@ -357,7 +356,7 @@ static bool z_erofs_try_inplace_io(struct z_erofs_decompress_frontend *fe,
357356
return false;
358357
}
359358

360-
/* callers must be with collection lock held */
359+
/* callers must be with pcluster lock held */
361360
static int z_erofs_attach_page(struct z_erofs_decompress_frontend *fe,
362361
struct page *page, enum z_erofs_page_type type,
363362
bool pvec_safereuse)
@@ -372,7 +371,7 @@ static int z_erofs_attach_page(struct z_erofs_decompress_frontend *fe,
372371

373372
ret = z_erofs_pagevec_enqueue(&fe->vector, page, type,
374373
pvec_safereuse);
375-
fe->cl->vcnt += (unsigned int)ret;
374+
fe->pcl->vcnt += (unsigned int)ret;
376375
return ret ? 0 : -EAGAIN;
377376
}
378377

@@ -405,12 +404,11 @@ static void z_erofs_try_to_claim_pcluster(struct z_erofs_decompress_frontend *f)
405404
f->mode = COLLECT_PRIMARY;
406405
}
407406

408-
static int z_erofs_lookup_collection(struct z_erofs_decompress_frontend *fe,
409-
struct inode *inode,
410-
struct erofs_map_blocks *map)
407+
static int z_erofs_lookup_pcluster(struct z_erofs_decompress_frontend *fe,
408+
struct inode *inode,
409+
struct erofs_map_blocks *map)
411410
{
412411
struct z_erofs_pcluster *pcl = fe->pcl;
413-
struct z_erofs_collection *cl;
414412
unsigned int length;
415413

416414
/* to avoid unexpected loop formed by corrupted images */
@@ -419,8 +417,7 @@ static int z_erofs_lookup_collection(struct z_erofs_decompress_frontend *fe,
419417
return -EFSCORRUPTED;
420418
}
421419

422-
cl = z_erofs_primarycollection(pcl);
423-
if (cl->pageofs != (map->m_la & ~PAGE_MASK)) {
420+
if (pcl->pageofs_out != (map->m_la & ~PAGE_MASK)) {
424421
DBG_BUGON(1);
425422
return -EFSCORRUPTED;
426423
}
@@ -443,23 +440,21 @@ static int z_erofs_lookup_collection(struct z_erofs_decompress_frontend *fe,
443440
length = READ_ONCE(pcl->length);
444441
}
445442
}
446-
mutex_lock(&cl->lock);
443+
mutex_lock(&pcl->lock);
447444
/* used to check tail merging loop due to corrupted images */
448445
if (fe->owned_head == Z_EROFS_PCLUSTER_TAIL)
449446
fe->tailpcl = pcl;
450447

451448
z_erofs_try_to_claim_pcluster(fe);
452-
fe->cl = cl;
453449
return 0;
454450
}
455451

456-
static int z_erofs_register_collection(struct z_erofs_decompress_frontend *fe,
457-
struct inode *inode,
458-
struct erofs_map_blocks *map)
452+
static int z_erofs_register_pcluster(struct z_erofs_decompress_frontend *fe,
453+
struct inode *inode,
454+
struct erofs_map_blocks *map)
459455
{
460456
bool ztailpacking = map->m_flags & EROFS_MAP_META;
461457
struct z_erofs_pcluster *pcl;
462-
struct z_erofs_collection *cl;
463458
struct erofs_workgroup *grp;
464459
int err;
465460

@@ -482,17 +477,15 @@ static int z_erofs_register_collection(struct z_erofs_decompress_frontend *fe,
482477

483478
/* new pclusters should be claimed as type 1, primary and followed */
484479
pcl->next = fe->owned_head;
480+
pcl->pageofs_out = map->m_la & ~PAGE_MASK;
485481
fe->mode = COLLECT_PRIMARY_FOLLOWED;
486482

487-
cl = z_erofs_primarycollection(pcl);
488-
cl->pageofs = map->m_la & ~PAGE_MASK;
489-
490483
/*
491484
* lock all primary followed works before visible to others
492485
* and mutex_trylock *never* fails for a new pcluster.
493486
*/
494-
mutex_init(&cl->lock);
495-
DBG_BUGON(!mutex_trylock(&cl->lock));
487+
mutex_init(&pcl->lock);
488+
DBG_BUGON(!mutex_trylock(&pcl->lock));
496489

497490
if (ztailpacking) {
498491
pcl->obj.index = 0; /* which indicates ztailpacking */
@@ -519,11 +512,10 @@ static int z_erofs_register_collection(struct z_erofs_decompress_frontend *fe,
519512
fe->tailpcl = pcl;
520513
fe->owned_head = &pcl->next;
521514
fe->pcl = pcl;
522-
fe->cl = cl;
523515
return 0;
524516

525517
err_out:
526-
mutex_unlock(&cl->lock);
518+
mutex_unlock(&pcl->lock);
527519
z_erofs_free_pcluster(pcl);
528520
return err;
529521
}
@@ -535,9 +527,9 @@ static int z_erofs_collector_begin(struct z_erofs_decompress_frontend *fe,
535527
struct erofs_workgroup *grp;
536528
int ret;
537529

538-
DBG_BUGON(fe->cl);
530+
DBG_BUGON(fe->pcl);
539531

540-
/* must be Z_EROFS_PCLUSTER_TAIL or pointed to previous collection */
532+
/* must be Z_EROFS_PCLUSTER_TAIL or pointed to previous pcluster */
541533
DBG_BUGON(fe->owned_head == Z_EROFS_PCLUSTER_NIL);
542534
DBG_BUGON(fe->owned_head == Z_EROFS_PCLUSTER_TAIL_CLOSED);
543535

@@ -554,22 +546,22 @@ static int z_erofs_collector_begin(struct z_erofs_decompress_frontend *fe,
554546
fe->pcl = container_of(grp, struct z_erofs_pcluster, obj);
555547
} else {
556548
tailpacking:
557-
ret = z_erofs_register_collection(fe, inode, map);
549+
ret = z_erofs_register_pcluster(fe, inode, map);
558550
if (!ret)
559551
goto out;
560552
if (ret != -EEXIST)
561553
return ret;
562554
}
563555

564-
ret = z_erofs_lookup_collection(fe, inode, map);
556+
ret = z_erofs_lookup_pcluster(fe, inode, map);
565557
if (ret) {
566558
erofs_workgroup_put(&fe->pcl->obj);
567559
return ret;
568560
}
569561

570562
out:
571563
z_erofs_pagevec_ctor_init(&fe->vector, Z_EROFS_NR_INLINE_PAGEVECS,
572-
fe->cl->pagevec, fe->cl->vcnt);
564+
fe->pcl->pagevec, fe->pcl->vcnt);
573565
/* since file-backed online pages are traversed in reverse order */
574566
fe->icpage_ptr = fe->pcl->compressed_pages +
575567
z_erofs_pclusterpages(fe->pcl);
@@ -582,48 +574,36 @@ static int z_erofs_collector_begin(struct z_erofs_decompress_frontend *fe,
582574
*/
583575
static void z_erofs_rcu_callback(struct rcu_head *head)
584576
{
585-
struct z_erofs_collection *const cl =
586-
container_of(head, struct z_erofs_collection, rcu);
587-
588-
z_erofs_free_pcluster(container_of(cl, struct z_erofs_pcluster,
589-
primary_collection));
577+
z_erofs_free_pcluster(container_of(head,
578+
struct z_erofs_pcluster, rcu));
590579
}
591580

592581
void erofs_workgroup_free_rcu(struct erofs_workgroup *grp)
593582
{
594583
struct z_erofs_pcluster *const pcl =
595584
container_of(grp, struct z_erofs_pcluster, obj);
596-
struct z_erofs_collection *const cl = z_erofs_primarycollection(pcl);
597585

598-
call_rcu(&cl->rcu, z_erofs_rcu_callback);
599-
}
600-
601-
static void z_erofs_collection_put(struct z_erofs_collection *cl)
602-
{
603-
struct z_erofs_pcluster *const pcl =
604-
container_of(cl, struct z_erofs_pcluster, primary_collection);
605-
606-
erofs_workgroup_put(&pcl->obj);
586+
call_rcu(&pcl->rcu, z_erofs_rcu_callback);
607587
}
608588

609589
static bool z_erofs_collector_end(struct z_erofs_decompress_frontend *fe)
610590
{
611-
struct z_erofs_collection *cl = fe->cl;
591+
struct z_erofs_pcluster *pcl = fe->pcl;
612592

613-
if (!cl)
593+
if (!pcl)
614594
return false;
615595

616596
z_erofs_pagevec_ctor_exit(&fe->vector, false);
617-
mutex_unlock(&cl->lock);
597+
mutex_unlock(&pcl->lock);
618598

619599
/*
620600
* if all pending pages are added, don't hold its reference
621601
* any longer if the pcluster isn't hosted by ourselves.
622602
*/
623603
if (fe->mode < COLLECT_PRIMARY_FOLLOWED_NOINPLACE)
624-
z_erofs_collection_put(cl);
604+
erofs_workgroup_put(&pcl->obj);
625605

626-
fe->cl = NULL;
606+
fe->pcl = NULL;
627607
return true;
628608
}
629609

@@ -666,8 +646,8 @@ static int z_erofs_do_read_page(struct z_erofs_decompress_frontend *fe,
666646
/* lucky, within the range of the current map_blocks */
667647
if (offset + cur >= map->m_la &&
668648
offset + cur < map->m_la + map->m_llen) {
669-
/* didn't get a valid collection previously (very rare) */
670-
if (!fe->cl)
649+
/* didn't get a valid pcluster previously (very rare) */
650+
if (!fe->pcl)
671651
goto restart_now;
672652
goto hitted;
673653
}
@@ -766,7 +746,7 @@ static int z_erofs_do_read_page(struct z_erofs_decompress_frontend *fe,
766746
/* bump up the number of spiltted parts of a page */
767747
++spiltted;
768748
/* also update nr_pages */
769-
fe->cl->nr_pages = max_t(pgoff_t, fe->cl->nr_pages, index + 1);
749+
fe->pcl->nr_pages = max_t(pgoff_t, fe->pcl->nr_pages, index + 1);
770750
next_part:
771751
/* can be used for verification */
772752
map->m_llen = offset + cur - map->m_la;
@@ -821,15 +801,13 @@ static int z_erofs_decompress_pcluster(struct super_block *sb,
821801

822802
enum z_erofs_page_type page_type;
823803
bool overlapped, partial;
824-
struct z_erofs_collection *cl;
825804
int err;
826805

827806
might_sleep();
828-
cl = z_erofs_primarycollection(pcl);
829-
DBG_BUGON(!READ_ONCE(cl->nr_pages));
807+
DBG_BUGON(!READ_ONCE(pcl->nr_pages));
830808

831-
mutex_lock(&cl->lock);
832-
nr_pages = cl->nr_pages;
809+
mutex_lock(&pcl->lock);
810+
nr_pages = pcl->nr_pages;
833811

834812
if (nr_pages <= Z_EROFS_VMAP_ONSTACK_PAGES) {
835813
pages = pages_onstack;
@@ -857,9 +835,9 @@ static int z_erofs_decompress_pcluster(struct super_block *sb,
857835

858836
err = 0;
859837
z_erofs_pagevec_ctor_init(&ctor, Z_EROFS_NR_INLINE_PAGEVECS,
860-
cl->pagevec, 0);
838+
pcl->pagevec, 0);
861839

862-
for (i = 0; i < cl->vcnt; ++i) {
840+
for (i = 0; i < pcl->vcnt; ++i) {
863841
unsigned int pagenr;
864842

865843
page = z_erofs_pagevec_dequeue(&ctor, &page_type);
@@ -945,11 +923,11 @@ static int z_erofs_decompress_pcluster(struct super_block *sb,
945923
goto out;
946924

947925
llen = pcl->length >> Z_EROFS_PCLUSTER_LENGTH_BIT;
948-
if (nr_pages << PAGE_SHIFT >= cl->pageofs + llen) {
926+
if (nr_pages << PAGE_SHIFT >= pcl->pageofs_out + llen) {
949927
outputsize = llen;
950928
partial = !(pcl->length & Z_EROFS_PCLUSTER_FULL_LENGTH);
951929
} else {
952-
outputsize = (nr_pages << PAGE_SHIFT) - cl->pageofs;
930+
outputsize = (nr_pages << PAGE_SHIFT) - pcl->pageofs_out;
953931
partial = true;
954932
}
955933

@@ -963,7 +941,7 @@ static int z_erofs_decompress_pcluster(struct super_block *sb,
963941
.in = compressed_pages,
964942
.out = pages,
965943
.pageofs_in = pcl->pageofs_in,
966-
.pageofs_out = cl->pageofs,
944+
.pageofs_out = pcl->pageofs_out,
967945
.inputsize = inputsize,
968946
.outputsize = outputsize,
969947
.alg = pcl->algorithmformat,
@@ -1012,16 +990,12 @@ static int z_erofs_decompress_pcluster(struct super_block *sb,
1012990
else if (pages != pages_onstack)
1013991
kvfree(pages);
1014992

1015-
cl->nr_pages = 0;
1016-
cl->vcnt = 0;
993+
pcl->nr_pages = 0;
994+
pcl->vcnt = 0;
1017995

1018-
/* all cl locks MUST be taken before the following line */
996+
/* pcluster lock MUST be taken before the following line */
1019997
WRITE_ONCE(pcl->next, Z_EROFS_PCLUSTER_NIL);
1020-
1021-
/* all cl locks SHOULD be released right now */
1022-
mutex_unlock(&cl->lock);
1023-
1024-
z_erofs_collection_put(cl);
998+
mutex_unlock(&pcl->lock);
1025999
return err;
10261000
}
10271001

@@ -1043,6 +1017,7 @@ static void z_erofs_decompress_queue(const struct z_erofs_decompressqueue *io,
10431017
owned = READ_ONCE(pcl->next);
10441018

10451019
z_erofs_decompress_pcluster(io->sb, pcl, pagepool);
1020+
erofs_workgroup_put(&pcl->obj);
10461021
}
10471022
}
10481023

fs/erofs/zdata.h

Lines changed: 22 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -12,21 +12,40 @@
1212
#define Z_EROFS_PCLUSTER_MAX_PAGES (Z_EROFS_PCLUSTER_MAX_SIZE / PAGE_SIZE)
1313
#define Z_EROFS_NR_INLINE_PAGEVECS 3
1414

15+
#define Z_EROFS_PCLUSTER_FULL_LENGTH 0x00000001
16+
#define Z_EROFS_PCLUSTER_LENGTH_BIT 1
17+
18+
/*
19+
* let's leave a type here in case of introducing
20+
* another tagged pointer later.
21+
*/
22+
typedef void *z_erofs_next_pcluster_t;
23+
1524
/*
1625
* Structure fields follow one of the following exclusion rules.
1726
*
1827
* I: Modifiable by initialization/destruction paths and read-only
1928
* for everyone else;
2029
*
21-
* L: Field should be protected by pageset lock;
30+
* L: Field should be protected by the pcluster lock;
2231
*
2332
* A: Field should be accessed / updated in atomic for parallelized code.
2433
*/
25-
struct z_erofs_collection {
34+
struct z_erofs_pcluster {
35+
struct erofs_workgroup obj;
2636
struct mutex lock;
2737

38+
/* A: point to next chained pcluster or TAILs */
39+
z_erofs_next_pcluster_t next;
40+
41+
/* A: lower limit of decompressed length and if full length or not */
42+
unsigned int length;
43+
2844
/* I: page offset of start position of decompression */
29-
unsigned short pageofs;
45+
unsigned short pageofs_out;
46+
47+
/* I: page offset of inline compressed data */
48+
unsigned short pageofs_in;
3049

3150
/* L: maximum relative page index in pagevec[] */
3251
unsigned short nr_pages;
@@ -41,29 +60,6 @@ struct z_erofs_collection {
4160
/* I: can be used to free the pcluster by RCU. */
4261
struct rcu_head rcu;
4362
};
44-
};
45-
46-
#define Z_EROFS_PCLUSTER_FULL_LENGTH 0x00000001
47-
#define Z_EROFS_PCLUSTER_LENGTH_BIT 1
48-
49-
/*
50-
* let's leave a type here in case of introducing
51-
* another tagged pointer later.
52-
*/
53-
typedef void *z_erofs_next_pcluster_t;
54-
55-
struct z_erofs_pcluster {
56-
struct erofs_workgroup obj;
57-
struct z_erofs_collection primary_collection;
58-
59-
/* A: point to next chained pcluster or TAILs */
60-
z_erofs_next_pcluster_t next;
61-
62-
/* A: lower limit of decompressed length and if full length or not */
63-
unsigned int length;
64-
65-
/* I: page offset of inline compressed data */
66-
unsigned short pageofs_in;
6763

6864
union {
6965
/* I: physical cluster size in pages */
@@ -80,8 +76,6 @@ struct z_erofs_pcluster {
8076
struct page *compressed_pages[];
8177
};
8278

83-
#define z_erofs_primarycollection(pcluster) (&(pcluster)->primary_collection)
84-
8579
/* let's avoid the valid 32-bit kernel addresses */
8680

8781
/* the chained workgroup has't submitted io (still open) */

0 commit comments

Comments
 (0)