Skip to content

Commit 4a3a58b

Browse files
committed
riscv pmap: only need to re-read l3 when crossing the page boundary
1 parent 50c962d commit 4a3a58b

File tree

1 file changed

+56
-17
lines changed

1 file changed

+56
-17
lines changed

sys/riscv/riscv/pmap.c

+56-17
Original file line numberDiff line numberDiff line change
@@ -1201,17 +1201,21 @@ pmap_kenter(vm_offset_t sva, vm_size_t size, vm_paddr_t pa, int mode)
12011201
pn_t pn;
12021202

12031203
KASSERT((pa & L3_OFFSET) == 0,
1204-
("pmap_kenter_device: Invalid physical address"));
1204+
("%s: Invalid physical address", __func__));
12051205
KASSERT((sva & L3_OFFSET) == 0,
1206-
("pmap_kenter_device: Invalid virtual address"));
1206+
("%s: Invalid virtual address", __func__));
12071207
KASSERT((size & PAGE_MASK) == 0,
1208-
("pmap_kenter_device: Mapping is not page-sized"));
1208+
("%s: Mapping is not page-sized", __func__));
1209+
1210+
if (size == 0)
1211+
return;
12091212

12101213
memattr = pmap_memattr_bits(mode);
12111214
va = sva;
1212-
while (size != 0) {
1213-
l3 = pmap_l3(kernel_pmap, va);
1214-
KASSERT(l3 != NULL, ("Invalid page table, va: 0x%lx", va));
1215+
l3 = pmap_l3(kernel_pmap, va);
1216+
while (true) {
1217+
KASSERT(l3 != NULL, ("%s: Invalid page table, va: 0x%lx",
1218+
__func__, va));
12151219

12161220
pn = (pa / PAGE_SIZE);
12171221
entry = PTE_KERN;
@@ -1222,6 +1226,11 @@ pmap_kenter(vm_offset_t sva, vm_size_t size, vm_paddr_t pa, int mode)
12221226
va += PAGE_SIZE;
12231227
pa += PAGE_SIZE;
12241228
size -= PAGE_SIZE;
1229+
if (size == 0)
1230+
break;
1231+
/* only need to re-read l3 when crossing the page boundary */
1232+
if (__is_aligned(++l3, PAGE_SIZE))
1233+
l3 = pmap_l3(kernel_pmap, va);
12251234
}
12261235
pmap_invalidate_range(kernel_pmap, sva, va);
12271236
}
@@ -1255,18 +1264,27 @@ pmap_kremove_device(vm_offset_t sva, vm_size_t size)
12551264
vm_offset_t va;
12561265

12571266
KASSERT((sva & L3_OFFSET) == 0,
1258-
("pmap_kremove_device: Invalid virtual address"));
1267+
("%s: Invalid virtual address", __func__));
12591268
KASSERT((size & PAGE_MASK) == 0,
1260-
("pmap_kremove_device: Mapping is not page-sized"));
1269+
("%s: Mapping is not page-sized", __func__));
1270+
1271+
if (size == 0)
1272+
return;
12611273

12621274
va = sva;
1263-
while (size != 0) {
1264-
l3 = pmap_l3(kernel_pmap, va);
1265-
KASSERT(l3 != NULL, ("Invalid page table, va: 0x%lx", va));
1275+
l3 = pmap_l3(kernel_pmap, va);
1276+
while (true) {
1277+
KASSERT(l3 != NULL, ("%s: Invalid page table, va: 0x%lx",
1278+
__func__, va));
12661279
pmap_clear(l3);
12671280

12681281
va += PAGE_SIZE;
12691282
size -= PAGE_SIZE;
1283+
if (size == 0)
1284+
break;
1285+
/* only need to re-read l3 when crossing the page boundary */
1286+
if (__is_aligned(++l3, PAGE_SIZE))
1287+
l3 = pmap_l3(kernel_pmap, va);
12701288
}
12711289

12721290
pmap_invalidate_range(kernel_pmap, sva, va);
@@ -1311,19 +1329,29 @@ pmap_qenter(vm_offset_t sva, vm_page_t *ma, int count)
13111329
pn_t pn;
13121330
int i;
13131331

1332+
if (count == 0)
1333+
return;
1334+
13141335
va = sva;
1315-
for (i = 0; i < count; i++) {
1336+
l3 = pmap_l3(kernel_pmap, va);
1337+
for (i = 0; ; ) {
1338+
KASSERT(l3 != NULL, ("%s: Invalid page table, va: 0x%lx",
1339+
__func__, va));
13161340
m = ma[i];
13171341
pa = VM_PAGE_TO_PHYS(m);
13181342
pn = (pa / PAGE_SIZE);
1319-
l3 = pmap_l3(kernel_pmap, va);
13201343

13211344
entry = PTE_KERN;
13221345
entry |= pmap_memattr_bits(m->md.pv_memattr);
13231346
entry |= (pn << PTE_PPN0_S);
13241347
pmap_store(l3, entry);
13251348

1326-
va += L3_SIZE;
1349+
va += PAGE_SIZE;
1350+
if (++i >= count)
1351+
break;
1352+
/* only need to re-read l3 when crossing the page boundary */
1353+
if (__is_aligned(++l3, PAGE_SIZE))
1354+
l3 = pmap_l3(kernel_pmap, va);
13271355
}
13281356
pmap_invalidate_range(kernel_pmap, sva, va);
13291357
}
@@ -1341,10 +1369,21 @@ pmap_qremove(vm_offset_t sva, int count)
13411369

13421370
KASSERT(sva >= VM_MIN_KERNEL_ADDRESS, ("usermode va %lx", sva));
13431371

1344-
for (va = sva; count-- > 0; va += PAGE_SIZE) {
1345-
l3 = pmap_l3(kernel_pmap, va);
1346-
KASSERT(l3 != NULL, ("pmap_kremove: Invalid address"));
1372+
if (count == 0)
1373+
return;
1374+
1375+
va = sva;
1376+
l3 = pmap_l3(kernel_pmap, va);
1377+
while (true) {
1378+
KASSERT(l3 != NULL, ("%s: Invalid page table, va: 0x%lx",
1379+
__func__, va));
13471380
pmap_clear(l3);
1381+
va += PAGE_SIZE;
1382+
if (--count == 0)
1383+
break;
1384+
/* only need to re-read l3 when crossing the page boundary */
1385+
if (__is_aligned(++l3, PAGE_SIZE))
1386+
l3 = pmap_l3(kernel_pmap, va);
13481387
}
13491388
pmap_invalidate_range(kernel_pmap, sva, va);
13501389
}

0 commit comments

Comments
 (0)