Skip to content
This repository was archived by the owner on Oct 30, 2021. It is now read-only.

Commit 86b442f

Browse files
dennisszhouhtejun
authored andcommitted
percpu: add first_bit to keep track of the first free in the bitmap
This patch adds first_bit to keep track of the first free bit in the bitmap. This hint helps prevent scanning of fully allocated blocks. Signed-off-by: Dennis Zhou <dennisszhou@gmail.com> Reviewed-by: Josef Bacik <jbacik@fb.com> Signed-off-by: Tejun Heo <tj@kernel.org>
1 parent ca460b3 commit 86b442f

File tree

3 files changed

+17
-3
lines changed

3 files changed

+17
-3
lines changed

mm/percpu-internal.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ struct pcpu_chunk {
3636
struct pcpu_block_md *md_blocks; /* metadata blocks */
3737

3838
void *data; /* chunk data */
39-
int first_free; /* no free below this */
39+
int first_bit; /* no free below this */
4040
bool immutable; /* no [de]population allowed */
4141
int start_offset; /* the overlap with the previous
4242
region to have a page aligned

mm/percpu-stats.c

+1
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,7 @@ static void chunk_map_stats(struct seq_file *m, struct pcpu_chunk *chunk,
121121
P("nr_alloc", chunk->nr_alloc);
122122
P("max_alloc_size", chunk->max_alloc_size);
123123
P("empty_pop_pages", chunk->nr_empty_pop_pages);
124+
P("first_bit", chunk->first_bit);
124125
P("free_bytes", chunk->free_bytes);
125126
P("contig_bytes", chunk->contig_bits * PCPU_MIN_ALLOC_SIZE);
126127
P("sum_frag", sum_frag);

mm/percpu.c

+15-2
Original file line numberDiff line numberDiff line change
@@ -427,7 +427,7 @@ static void pcpu_chunk_refresh_hint(struct pcpu_chunk *chunk)
427427
chunk->contig_bits = 0;
428428

429429
bits = nr_empty_pop_pages = 0;
430-
pcpu_for_each_unpop_region(chunk->alloc_map, rs, re, 0,
430+
pcpu_for_each_unpop_region(chunk->alloc_map, rs, re, chunk->first_bit,
431431
pcpu_chunk_map_bits(chunk)) {
432432
bits = re - rs;
433433

@@ -646,7 +646,8 @@ static int pcpu_find_block_fit(struct pcpu_chunk *chunk, int alloc_bits,
646646
int bit_off, bits;
647647
int re; /* region end */
648648

649-
pcpu_for_each_unpop_region(chunk->alloc_map, bit_off, re, 0,
649+
pcpu_for_each_unpop_region(chunk->alloc_map, bit_off, re,
650+
chunk->first_bit,
650651
pcpu_chunk_map_bits(chunk)) {
651652
bits = re - bit_off;
652653

@@ -715,6 +716,13 @@ static int pcpu_alloc_area(struct pcpu_chunk *chunk, int alloc_bits,
715716

716717
chunk->free_bytes -= alloc_bits * PCPU_MIN_ALLOC_SIZE;
717718

719+
/* update first free bit */
720+
if (bit_off == chunk->first_bit)
721+
chunk->first_bit = find_next_zero_bit(
722+
chunk->alloc_map,
723+
pcpu_chunk_map_bits(chunk),
724+
bit_off + alloc_bits);
725+
718726
pcpu_block_update_hint_alloc(chunk, bit_off, alloc_bits);
719727

720728
pcpu_chunk_relocate(chunk, oslot);
@@ -750,6 +758,9 @@ static void pcpu_free_area(struct pcpu_chunk *chunk, int off)
750758
/* update metadata */
751759
chunk->free_bytes += bits * PCPU_MIN_ALLOC_SIZE;
752760

761+
/* update first free bit */
762+
chunk->first_bit = min(chunk->first_bit, bit_off);
763+
753764
pcpu_block_update_hint_free(chunk, bit_off, bits);
754765

755766
pcpu_chunk_relocate(chunk, oslot);
@@ -841,6 +852,8 @@ static struct pcpu_chunk * __init pcpu_alloc_first_chunk(unsigned long tmp_addr,
841852
set_bit(0, chunk->bound_map);
842853
set_bit(offset_bits, chunk->bound_map);
843854

855+
chunk->first_bit = offset_bits;
856+
844857
pcpu_block_update_hint_alloc(chunk, 0, offset_bits);
845858
}
846859

0 commit comments

Comments
 (0)