Changeset 6f4495f5 in mainline for kernel/generic/src/mm/as.c
- Timestamp:
- 2007-01-27T17:32:13Z (18 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- 1ba41c5
- Parents:
- 51baa8a
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
kernel/generic/src/mm/as.c
r51baa8a r6f4495f5 94 94 static slab_cache_t *as_slab; 95 95 96 /** This lock protects inactive_as_with_asid_head list. It must be acquired before as_t mutex. */ 96 /** 97 * This lock protects inactive_as_with_asid_head list. It must be acquired 98 * before as_t mutex. 99 */ 97 100 SPINLOCK_INITIALIZE(inactive_as_with_asid_lock); 98 101 … … 108 111 static int area_flags_to_page_flags(int aflags); 109 112 static as_area_t *find_area_and_lock(as_t *as, uintptr_t va); 110 static bool check_area_conflicts(as_t *as, uintptr_t va, size_t size, as_area_t *avoid_area); 113 static bool check_area_conflicts(as_t *as, uintptr_t va, size_t size, 114 as_area_t *avoid_area); 111 115 static void sh_info_remove_reference(share_info_t *sh_info); 112 116 … … 137 141 138 142 as_slab = slab_cache_create("as_slab", sizeof(as_t), 0, 139 143 as_constructor, as_destructor, SLAB_CACHE_MAGDEFERRED); 140 144 141 145 AS_KERNEL = as_create(FLAG_AS_KERNEL); … … 172 176 /** Destroy adress space. 173 177 * 174 * When there are no tasks referencing this address space (i.e. its refcount is zero),175 * the address space can be destroyed.178 * When there are no tasks referencing this address space (i.e. its refcount is 179 * zero), the address space can be destroyed. 176 180 */ 177 181 void as_destroy(as_t *as) … … 204 208 205 209 ASSERT(!list_empty(&as->as_area_btree.leaf_head)); 206 node = list_get_instance(as->as_area_btree.leaf_head.next, btree_node_t, leaf_link); 210 node = list_get_instance(as->as_area_btree.leaf_head.next, 211 btree_node_t, leaf_link); 207 212 208 213 if ((cond = node->keys)) { … … 273 278 a->backend_data = *backend_data; 274 279 else 275 memsetb((uintptr_t) &a->backend_data, sizeof(a->backend_data), 0); 280 memsetb((uintptr_t) &a->backend_data, sizeof(a->backend_data), 281 0); 276 282 277 283 btree_create(&a->used_space); … … 288 294 * 289 295 * @param as Address space. 290 * @param address Virtual address belonging to the area to be changed. Must be page-aligned. 296 * @param address Virtual address belonging to the area to be changed. Must be 297 * page-aligned. 291 298 * @param size New size of the virtual memory block starting at address. 292 299 * @param flags Flags influencing the remap operation. Currently unused. … … 357 364 * Start TLB shootdown sequence. 358 365 */ 359 tlb_shootdown_start(TLB_INVL_PAGES, AS->asid, area->base + pages*PAGE_SIZE, area->pages - pages); 366 tlb_shootdown_start(TLB_INVL_PAGES, AS->asid, area->base + 367 pages * PAGE_SIZE, area->pages - pages); 360 368 361 369 /* … … 370 378 371 379 ASSERT(!list_empty(&area->used_space.leaf_head)); 372 node = list_get_instance(area->used_space.leaf_head.prev, btree_node_t, leaf_link); 380 node = 381 list_get_instance(area->used_space.leaf_head.prev, 382 btree_node_t, leaf_link); 373 383 if ((cond = (bool) node->keys)) { 374 384 uintptr_t b = node->key[node->keys - 1]; 375 count_t c = (count_t) node->value[node->keys - 1]; 385 count_t c = 386 (count_t) node->value[node->keys - 1]; 376 387 int i = 0; 377 388 378 if (overlaps(b, c*PAGE_SIZE, area->base, pages*PAGE_SIZE)) { 389 if (overlaps(b, c * PAGE_SIZE, area->base, 390 pages*PAGE_SIZE)) { 379 391 380 if (b + c *PAGE_SIZE <= start_free) {392 if (b + c * PAGE_SIZE <= start_free) { 381 393 /* 382 * The whole interval fits completely 383 * in the resized address space area. 394 * The whole interval fits 395 * completely in the resized 396 * address space area. 384 397 */ 385 398 break; … … 387 400 388 401 /* 389 * Part of the interval corresponding to b and c 390 * overlaps with the resized address space area. 402 * Part of the interval corresponding 403 * to b and c overlaps with the resized 404 * address space area. 391 405 */ 392 406 393 407 cond = false; /* we are almost done */ 394 408 i = (start_free - b) >> PAGE_WIDTH; 395 if (!used_space_remove(area, start_free, c - i)) 396 panic("Could not remove used space.\n"); 409 if (!used_space_remove(area, start_free, 410 c - i)) 411 panic("Could not remove used " 412 "space.\n"); 397 413 } else { 398 414 /* 399 * The interval of used space can be completely removed. 415 * The interval of used space can be 416 * completely removed. 400 417 */ 401 418 if (!used_space_remove(area, b, c)) 402 panic("Could not remove used space.\n"); 419 panic("Could not remove used " 420 "space.\n"); 403 421 } 404 422 … … 407 425 408 426 page_table_lock(as, false); 409 pte = page_mapping_find(as, b + i*PAGE_SIZE); 410 ASSERT(pte && PTE_VALID(pte) && PTE_PRESENT(pte)); 411 if (area->backend && area->backend->frame_free) { 427 pte = page_mapping_find(as, b + 428 i * PAGE_SIZE); 429 ASSERT(pte && PTE_VALID(pte) && 430 PTE_PRESENT(pte)); 431 if (area->backend && 432 area->backend->frame_free) { 412 433 area->backend->frame_free(area, 413 b + i*PAGE_SIZE, PTE_GET_FRAME(pte)); 434 b + i * PAGE_SIZE, 435 PTE_GET_FRAME(pte)); 414 436 } 415 page_mapping_remove(as, b + i*PAGE_SIZE); 437 page_mapping_remove(as, b + 438 i * PAGE_SIZE); 416 439 page_table_unlock(as, false); 417 440 } … … 422 445 * Finish TLB shootdown sequence. 423 446 */ 424 tlb_invalidate_pages(as->asid, area->base + pages*PAGE_SIZE, area->pages - pages); 447 tlb_invalidate_pages(as->asid, area->base + pages * PAGE_SIZE, 448 area->pages - pages); 425 449 tlb_shootdown_finalize(); 426 450 … … 428 452 * Invalidate software translation caches (e.g. TSB on sparc64). 429 453 */ 430 as_invalidate_translation_cache(as, area->base + pages*PAGE_SIZE, area->pages - pages); 454 as_invalidate_translation_cache(as, area->base + 455 pages * PAGE_SIZE, area->pages - pages); 431 456 } else { 432 457 /* … … 434 459 * Check for overlaps with other address space areas. 435 460 */ 436 if (!check_area_conflicts(as, address, pages * PAGE_SIZE, area)) { 461 if (!check_area_conflicts(as, address, pages * PAGE_SIZE, 462 area)) { 437 463 mutex_unlock(&area->lock); 438 464 mutex_unlock(&as->lock); … … 485 511 * Visit only the pages mapped by used_space B+tree. 486 512 */ 487 for (cur = area->used_space.leaf_head.next; cur != &area->used_space.leaf_head; cur = cur->next) { 513 for (cur = area->used_space.leaf_head.next; 514 cur != &area->used_space.leaf_head; cur = cur->next) { 488 515 btree_node_t *node; 489 516 int i; … … 497 524 for (j = 0; j < (count_t) node->value[i]; j++) { 498 525 page_table_lock(as, false); 499 pte = page_mapping_find(as, b + j*PAGE_SIZE); 500 ASSERT(pte && PTE_VALID(pte) && PTE_PRESENT(pte)); 501 if (area->backend && area->backend->frame_free) { 502 area->backend->frame_free(area, 503 b + j*PAGE_SIZE, PTE_GET_FRAME(pte)); 526 pte = page_mapping_find(as, b + j * PAGE_SIZE); 527 ASSERT(pte && PTE_VALID(pte) && 528 PTE_PRESENT(pte)); 529 if (area->backend && 530 area->backend->frame_free) { 531 area->backend->frame_free(area, b + 532 j * PAGE_SIZE, PTE_GET_FRAME(pte)); 504 533 } 505 page_mapping_remove(as, b + j *PAGE_SIZE);534 page_mapping_remove(as, b + j * PAGE_SIZE); 506 535 page_table_unlock(as, false); 507 536 } … … 516 545 517 546 /* 518 * Invalidate potential software translation caches (e.g. TSB on sparc64). 547 * Invalidate potential software translation caches (e.g. TSB on 548 * sparc64). 519 549 */ 520 550 as_invalidate_translation_cache(as, area->base, area->pages); … … 606 636 dst_flags_mask |= AS_AREA_CACHEABLE; 607 637 608 if (src_size != acc_size || (src_flags & dst_flags_mask) != dst_flags_mask) { 638 if (src_size != acc_size || 639 (src_flags & dst_flags_mask) != dst_flags_mask) { 609 640 mutex_unlock(&src_area->lock); 610 641 mutex_unlock(&src_as->lock); … … 659 690 */ 660 691 dst_area = as_area_create(dst_as, dst_flags_mask, src_size, dst_base, 661 692 AS_AREA_ATTR_PARTIAL, src_backend, &src_backend_data); 662 693 if (!dst_area) { 663 694 /* … … 777 808 if (PTE_PRESENT(pte)) { 778 809 if (((access == PF_ACCESS_READ) && PTE_READABLE(pte)) || 779 780 810 (access == PF_ACCESS_WRITE && PTE_WRITABLE(pte)) || 811 (access == PF_ACCESS_EXEC && PTE_EXECUTABLE(pte))) { 781 812 page_table_unlock(AS, false); 782 813 mutex_unlock(&area->lock); … … 805 836 if (THREAD->in_copy_from_uspace) { 806 837 THREAD->in_copy_from_uspace = false; 807 istate_set_retaddr(istate, (uintptr_t) &memcpy_from_uspace_failover_address); 838 istate_set_retaddr(istate, 839 (uintptr_t) &memcpy_from_uspace_failover_address); 808 840 } else if (THREAD->in_copy_to_uspace) { 809 841 THREAD->in_copy_to_uspace = false; 810 istate_set_retaddr(istate, (uintptr_t) &memcpy_to_uspace_failover_address); 842 istate_set_retaddr(istate, 843 (uintptr_t) &memcpy_to_uspace_failover_address); 811 844 } else { 812 845 return AS_PF_FAULT; … … 846 879 */ 847 880 ASSERT(old->asid != ASID_INVALID); 848 list_append(&old->inactive_as_with_asid_link, &inactive_as_with_asid_head); 881 list_append(&old->inactive_as_with_asid_link, 882 &inactive_as_with_asid_head); 849 883 } 850 884 mutex_unlock(&old->lock); … … 862 896 mutex_lock_active(&new->lock); 863 897 if ((new->cpu_refcount++ == 0) && (new != AS_KERNEL)) { 864 if (new->asid != ASID_INVALID) 898 if (new->asid != ASID_INVALID) { 865 899 list_remove(&new->inactive_as_with_asid_link); 866 else 867 needs_asid = true; /* defer call to asid_get() until new->lock is released */ 900 } else { 901 /* 902 * Defer call to asid_get() until new->lock is released. 903 */ 904 needs_asid = true; 905 } 868 906 } 869 907 SET_PTL0_ADDRESS(new->page_table); … … 1007 1045 * @param va Virtual address. 1008 1046 * 1009 * @return Locked address space area containing va on success or NULL on failure. 1047 * @return Locked address space area containing va on success or NULL on 1048 * failure. 1010 1049 */ 1011 1050 as_area_t *find_area_and_lock(as_t *as, uintptr_t va) … … 1042 1081 * Because of its position in the B+tree, it must have base < va. 1043 1082 */ 1044 if ((lnode = btree_leaf_node_left_neighbour(&as->as_area_btree, leaf))) { 1083 lnode = btree_leaf_node_left_neighbour(&as->as_area_btree, leaf); 1084 if (lnode) { 1045 1085 a = (as_area_t *) lnode->value[lnode->keys - 1]; 1046 1086 mutex_lock(&a->lock); … … 1065 1105 * @return True if there is no conflict, false otherwise. 1066 1106 */ 1067 bool check_area_conflicts(as_t *as, uintptr_t va, size_t size, as_area_t *avoid_area) 1107 bool check_area_conflicts(as_t *as, uintptr_t va, size_t size, 1108 as_area_t *avoid_area) 1068 1109 { 1069 1110 as_area_t *a; … … 1100 1141 mutex_unlock(&a->lock); 1101 1142 } 1102 if ((node = btree_leaf_node_right_neighbour(&as->as_area_btree, leaf))) { 1143 node = btree_leaf_node_right_neighbour(&as->as_area_btree, leaf); 1144 if (node) { 1103 1145 a = (as_area_t *) node->value[0]; 1104 1146 mutex_lock(&a->lock); … … 1131 1173 if (!KERNEL_ADDRESS_SPACE_SHADOWED) { 1132 1174 return !overlaps(va, size, 1133 KERNEL_ADDRESS_SPACE_START, KERNEL_ADDRESS_SPACE_END-KERNEL_ADDRESS_SPACE_START); 1175 KERNEL_ADDRESS_SPACE_START, 1176 KERNEL_ADDRESS_SPACE_END - KERNEL_ADDRESS_SPACE_START); 1134 1177 } 1135 1178 … … 1190 1233 node = btree_leaf_node_left_neighbour(&a->used_space, leaf); 1191 1234 if (node) { 1192 uintptr_t left_pg = node->key[node->keys - 1], right_pg = leaf->key[0]; 1193 count_t left_cnt = (count_t) node->value[node->keys - 1], right_cnt = (count_t) leaf->value[0]; 1235 uintptr_t left_pg = node->key[node->keys - 1]; 1236 uintptr_t right_pg = leaf->key[0]; 1237 count_t left_cnt = (count_t) node->value[node->keys - 1]; 1238 count_t right_cnt = (count_t) leaf->value[0]; 1194 1239 1195 1240 /* … … 1201 1246 if (page >= right_pg) { 1202 1247 /* Do nothing. */ 1203 } else if (overlaps(page, count*PAGE_SIZE, left_pg, left_cnt*PAGE_SIZE)) { 1248 } else if (overlaps(page, count * PAGE_SIZE, left_pg, 1249 left_cnt * PAGE_SIZE)) { 1204 1250 /* The interval intersects with the left interval. */ 1205 1251 return 0; 1206 } else if (overlaps(page, count*PAGE_SIZE, right_pg, right_cnt*PAGE_SIZE)) { 1252 } else if (overlaps(page, count * PAGE_SIZE, right_pg, 1253 right_cnt * PAGE_SIZE)) { 1207 1254 /* The interval intersects with the right interval. */ 1208 1255 return 0; 1209 } else if ((page == left_pg + left_cnt*PAGE_SIZE) && (page + count*PAGE_SIZE == right_pg)) { 1210 /* The interval can be added by merging the two already present intervals. */ 1256 } else if ((page == left_pg + left_cnt * PAGE_SIZE) && 1257 (page + count * PAGE_SIZE == right_pg)) { 1258 /* 1259 * The interval can be added by merging the two already 1260 * present intervals. 1261 */ 1211 1262 node->value[node->keys - 1] += count + right_cnt; 1212 1263 btree_remove(&a->used_space, right_pg, leaf); 1213 1264 return 1; 1214 } else if (page == left_pg + left_cnt*PAGE_SIZE) { 1215 /* The interval can be added by simply growing the left interval. */ 1265 } else if (page == left_pg + left_cnt * PAGE_SIZE) { 1266 /* 1267 * The interval can be added by simply growing the left 1268 * interval. 1269 */ 1216 1270 node->value[node->keys - 1] += count; 1217 1271 return 1; 1218 } else if (page + count *PAGE_SIZE == right_pg) {1272 } else if (page + count * PAGE_SIZE == right_pg) { 1219 1273 /* 1220 * The interval can be addded by simply moving base of the right 1221 * interval down and increasing its size accordingly. 1274 * The interval can be addded by simply moving base of 1275 * the right interval down and increasing its size 1276 * accordingly. 1222 1277 */ 1223 1278 leaf->value[0] += count; … … 1229 1284 * but cannot be merged with any of them. 1230 1285 */ 1231 btree_insert(&a->used_space, page, (void *) count, leaf); 1286 btree_insert(&a->used_space, page, (void *) count, 1287 leaf); 1232 1288 return 1; 1233 1289 } … … 1237 1293 1238 1294 /* 1239 * Investigate the border case in which the left neighbour does not1240 * exist but the interval fits from the left.1295 * Investigate the border case in which the left neighbour does 1296 * not exist but the interval fits from the left. 1241 1297 */ 1242 1298 1243 if (overlaps(page, count*PAGE_SIZE, right_pg, right_cnt*PAGE_SIZE)) { 1299 if (overlaps(page, count * PAGE_SIZE, right_pg, 1300 right_cnt * PAGE_SIZE)) { 1244 1301 /* The interval intersects with the right interval. */ 1245 1302 return 0; 1246 } else if (page + count *PAGE_SIZE == right_pg) {1303 } else if (page + count * PAGE_SIZE == right_pg) { 1247 1304 /* 1248 * The interval can be added by moving the base of the right interval down 1249 * and increasing its size accordingly. 1305 * The interval can be added by moving the base of the 1306 * right interval down and increasing its size 1307 * accordingly. 1250 1308 */ 1251 1309 leaf->key[0] = page; … … 1257 1315 * It must be added individually. 1258 1316 */ 1259 btree_insert(&a->used_space, page, (void *) count, leaf); 1317 btree_insert(&a->used_space, page, (void *) count, 1318 leaf); 1260 1319 return 1; 1261 1320 } … … 1264 1323 node = btree_leaf_node_right_neighbour(&a->used_space, leaf); 1265 1324 if (node) { 1266 uintptr_t left_pg = leaf->key[leaf->keys - 1], right_pg = node->key[0]; 1267 count_t left_cnt = (count_t) leaf->value[leaf->keys - 1], right_cnt = (count_t) node->value[0]; 1325 uintptr_t left_pg = leaf->key[leaf->keys - 1]; 1326 uintptr_t right_pg = node->key[0]; 1327 count_t left_cnt = (count_t) leaf->value[leaf->keys - 1]; 1328 count_t right_cnt = (count_t) node->value[0]; 1268 1329 1269 1330 /* … … 1275 1336 if (page < left_pg) { 1276 1337 /* Do nothing. */ 1277 } else if (overlaps(page, count*PAGE_SIZE, left_pg, left_cnt*PAGE_SIZE)) { 1338 } else if (overlaps(page, count * PAGE_SIZE, left_pg, 1339 left_cnt * PAGE_SIZE)) { 1278 1340 /* The interval intersects with the left interval. */ 1279 1341 return 0; 1280 } else if (overlaps(page, count*PAGE_SIZE, right_pg, right_cnt*PAGE_SIZE)) { 1342 } else if (overlaps(page, count * PAGE_SIZE, right_pg, 1343 right_cnt * PAGE_SIZE)) { 1281 1344 /* The interval intersects with the right interval. */ 1282 1345 return 0; 1283 } else if ((page == left_pg + left_cnt*PAGE_SIZE) && (page + count*PAGE_SIZE == right_pg)) { 1284 /* The interval can be added by merging the two already present intervals. */ 1346 } else if ((page == left_pg + left_cnt * PAGE_SIZE) && 1347 (page + count * PAGE_SIZE == right_pg)) { 1348 /* 1349 * The interval can be added by merging the two already 1350 * present intervals. 1351 * */ 1285 1352 leaf->value[leaf->keys - 1] += count + right_cnt; 1286 1353 btree_remove(&a->used_space, right_pg, node); 1287 1354 return 1; 1288 } else if (page == left_pg + left_cnt*PAGE_SIZE) { 1289 /* The interval can be added by simply growing the left interval. */ 1355 } else if (page == left_pg + left_cnt * PAGE_SIZE) { 1356 /* 1357 * The interval can be added by simply growing the left 1358 * interval. 1359 * */ 1290 1360 leaf->value[leaf->keys - 1] += count; 1291 1361 return 1; 1292 } else if (page + count *PAGE_SIZE == right_pg) {1362 } else if (page + count * PAGE_SIZE == right_pg) { 1293 1363 /* 1294 * The interval can be addded by simply moving base of the right 1295 * interval down and increasing its size accordingly. 1364 * The interval can be addded by simply moving base of 1365 * the right interval down and increasing its size 1366 * accordingly. 1296 1367 */ 1297 1368 node->value[0] += count; … … 1303 1374 * but cannot be merged with any of them. 1304 1375 */ 1305 btree_insert(&a->used_space, page, (void *) count, leaf); 1376 btree_insert(&a->used_space, page, (void *) count, 1377 leaf); 1306 1378 return 1; 1307 1379 } … … 1311 1383 1312 1384 /* 1313 * Investigate the border case in which the right neighbour does not1314 * exist but the interval fits from the right.1385 * Investigate the border case in which the right neighbour 1386 * does not exist but the interval fits from the right. 1315 1387 */ 1316 1388 1317 if (overlaps(page, count*PAGE_SIZE, left_pg, left_cnt*PAGE_SIZE)) { 1389 if (overlaps(page, count * PAGE_SIZE, left_pg, 1390 left_cnt * PAGE_SIZE)) { 1318 1391 /* The interval intersects with the left interval. */ 1319 1392 return 0; 1320 } else if (left_pg + left_cnt*PAGE_SIZE == page) { 1321 /* The interval can be added by growing the left interval. */ 1393 } else if (left_pg + left_cnt * PAGE_SIZE == page) { 1394 /* 1395 * The interval can be added by growing the left 1396 * interval. 1397 */ 1322 1398 leaf->value[leaf->keys - 1] += count; 1323 1399 return 1; … … 1327 1403 * It must be added individually. 1328 1404 */ 1329 btree_insert(&a->used_space, page, (void *) count, leaf); 1405 btree_insert(&a->used_space, page, (void *) count, 1406 leaf); 1330 1407 return 1; 1331 1408 } … … 1333 1410 1334 1411 /* 1335 * Note that if the algorithm made it thus far, the interval can fit only1336 * between two other intervals of the leaf. The two border cases were already1337 * resolved.1412 * Note that if the algorithm made it thus far, the interval can fit 1413 * only between two other intervals of the leaf. The two border cases 1414 * were already resolved. 1338 1415 */ 1339 1416 for (i = 1; i < leaf->keys; i++) { 1340 1417 if (page < leaf->key[i]) { 1341 uintptr_t left_pg = leaf->key[i - 1], right_pg = leaf->key[i]; 1342 count_t left_cnt = (count_t) leaf->value[i - 1], right_cnt = (count_t) leaf->value[i]; 1418 uintptr_t left_pg = leaf->key[i - 1]; 1419 uintptr_t right_pg = leaf->key[i]; 1420 count_t left_cnt = (count_t) leaf->value[i - 1]; 1421 count_t right_cnt = (count_t) leaf->value[i]; 1343 1422 1344 1423 /* … … 1346 1425 */ 1347 1426 1348 if (overlaps(page, count*PAGE_SIZE, left_pg, left_cnt*PAGE_SIZE)) { 1349 /* The interval intersects with the left interval. */ 1427 if (overlaps(page, count * PAGE_SIZE, left_pg, 1428 left_cnt * PAGE_SIZE)) { 1429 /* 1430 * The interval intersects with the left 1431 * interval. 1432 */ 1350 1433 return 0; 1351 } else if (overlaps(page, count*PAGE_SIZE, right_pg, right_cnt*PAGE_SIZE)) { 1352 /* The interval intersects with the right interval. */ 1434 } else if (overlaps(page, count * PAGE_SIZE, right_pg, 1435 right_cnt * PAGE_SIZE)) { 1436 /* 1437 * The interval intersects with the right 1438 * interval. 1439 */ 1353 1440 return 0; 1354 } else if ((page == left_pg + left_cnt*PAGE_SIZE) && (page + count*PAGE_SIZE == right_pg)) { 1355 /* The interval can be added by merging the two already present intervals. */ 1441 } else if ((page == left_pg + left_cnt * PAGE_SIZE) && 1442 (page + count * PAGE_SIZE == right_pg)) { 1443 /* 1444 * The interval can be added by merging the two 1445 * already present intervals. 1446 */ 1356 1447 leaf->value[i - 1] += count + right_cnt; 1357 1448 btree_remove(&a->used_space, right_pg, leaf); 1358 1449 return 1; 1359 } else if (page == left_pg + left_cnt*PAGE_SIZE) { 1360 /* The interval can be added by simply growing the left interval. */ 1450 } else if (page == left_pg + left_cnt * PAGE_SIZE) { 1451 /* 1452 * The interval can be added by simply growing 1453 * the left interval. 1454 */ 1361 1455 leaf->value[i - 1] += count; 1362 1456 return 1; 1363 } else if (page + count *PAGE_SIZE == right_pg) {1457 } else if (page + count * PAGE_SIZE == right_pg) { 1364 1458 /* 1365 * The interval can be addded by simply moving base of the right 1366 * interval down and increasing its size accordingly. 1459 * The interval can be addded by simply moving 1460 * base of the right interval down and 1461 * increasing its size accordingly. 1367 1462 */ 1368 1463 leaf->value[i] += count; … … 1371 1466 } else { 1372 1467 /* 1373 * The interval is between both neigbouring intervals, 1374 * but cannot be merged with any of them. 1468 * The interval is between both neigbouring 1469 * intervals, but cannot be merged with any of 1470 * them. 1375 1471 */ 1376 btree_insert(&a->used_space, page, (void *) count, leaf); 1472 btree_insert(&a->used_space, page, 1473 (void *) count, leaf); 1377 1474 return 1; 1378 1475 } … … 1380 1477 } 1381 1478 1382 panic("Inconsistency detected while adding %d pages of used space at %p.\n", count, page); 1479 panic("Inconsistency detected while adding %d pages of used space at " 1480 "%p.\n", count, page); 1383 1481 } 1384 1482 … … 1419 1517 for (i = 0; i < leaf->keys; i++) { 1420 1518 if (leaf->key[i] == page) { 1421 leaf->key[i] += count *PAGE_SIZE;1519 leaf->key[i] += count * PAGE_SIZE; 1422 1520 leaf->value[i] -= count; 1423 1521 return 1; … … 1433 1531 count_t left_cnt = (count_t) node->value[node->keys - 1]; 1434 1532 1435 if (overlaps(left_pg, left_cnt*PAGE_SIZE, page, count*PAGE_SIZE)) { 1436 if (page + count*PAGE_SIZE == left_pg + left_cnt*PAGE_SIZE) { 1533 if (overlaps(left_pg, left_cnt * PAGE_SIZE, page, 1534 count * PAGE_SIZE)) { 1535 if (page + count * PAGE_SIZE == 1536 left_pg + left_cnt * PAGE_SIZE) { 1437 1537 /* 1438 * The interval is contained in the rightmost interval 1439 * of the left neighbour and can be removed by 1440 * updating the size of the bigger interval. 1538 * The interval is contained in the rightmost 1539 * interval of the left neighbour and can be 1540 * removed by updating the size of the bigger 1541 * interval. 1441 1542 */ 1442 1543 node->value[node->keys - 1] -= count; 1443 1544 return 1; 1444 } else if (page + count*PAGE_SIZE < left_pg + left_cnt*PAGE_SIZE) { 1545 } else if (page + count * PAGE_SIZE < 1546 left_pg + left_cnt*PAGE_SIZE) { 1445 1547 count_t new_cnt; 1446 1548 1447 1549 /* 1448 * The interval is contained in the rightmost interval 1449 * of the left neighbour but its removal requires 1450 * both updating the size of the original interval and 1451 * also inserting a new interval. 1550 * The interval is contained in the rightmost 1551 * interval of the left neighbour but its 1552 * removal requires both updating the size of 1553 * the original interval and also inserting a 1554 * new interval. 1452 1555 */ 1453 new_cnt = ((left_pg + left_cnt*PAGE_SIZE) - (page + count*PAGE_SIZE)) >> PAGE_WIDTH; 1556 new_cnt = ((left_pg + left_cnt * PAGE_SIZE) - 1557 (page + count*PAGE_SIZE)) >> PAGE_WIDTH; 1454 1558 node->value[node->keys - 1] -= count + new_cnt; 1455 btree_insert(&a->used_space, page + count*PAGE_SIZE, (void *) new_cnt, leaf); 1559 btree_insert(&a->used_space, page + 1560 count * PAGE_SIZE, (void *) new_cnt, leaf); 1456 1561 return 1; 1457 1562 } … … 1466 1571 count_t left_cnt = (count_t) leaf->value[leaf->keys - 1]; 1467 1572 1468 if (overlaps(left_pg, left_cnt*PAGE_SIZE, page, count*PAGE_SIZE)) { 1469 if (page + count*PAGE_SIZE == left_pg + left_cnt*PAGE_SIZE) { 1573 if (overlaps(left_pg, left_cnt * PAGE_SIZE, page, 1574 count * PAGE_SIZE)) { 1575 if (page + count * PAGE_SIZE == 1576 left_pg + left_cnt * PAGE_SIZE) { 1470 1577 /* 1471 * The interval is contained in the rightmost interval1472 * of the leaf and can be removed by updating the size1473 * of the bigger interval.1578 * The interval is contained in the rightmost 1579 * interval of the leaf and can be removed by 1580 * updating the size of the bigger interval. 1474 1581 */ 1475 1582 leaf->value[leaf->keys - 1] -= count; 1476 1583 return 1; 1477 } else if (page + count*PAGE_SIZE < left_pg + left_cnt*PAGE_SIZE) { 1584 } else if (page + count * PAGE_SIZE < left_pg + 1585 left_cnt * PAGE_SIZE) { 1478 1586 count_t new_cnt; 1479 1587 1480 1588 /* 1481 * The interval is contained in the rightmost interval 1482 * of the leaf but its removal requires both updating 1483 * the size of the original interval and 1484 * also inserting a new interval. 1589 * The interval is contained in the rightmost 1590 * interval of the leaf but its removal 1591 * requires both updating the size of the 1592 * original interval and also inserting a new 1593 * interval. 1485 1594 */ 1486 new_cnt = ((left_pg + left_cnt*PAGE_SIZE) - (page + count*PAGE_SIZE)) >> PAGE_WIDTH; 1595 new_cnt = ((left_pg + left_cnt * PAGE_SIZE) - 1596 (page + count * PAGE_SIZE)) >> PAGE_WIDTH; 1487 1597 leaf->value[leaf->keys - 1] -= count + new_cnt; 1488 btree_insert(&a->used_space, page + count*PAGE_SIZE, (void *) new_cnt, leaf); 1598 btree_insert(&a->used_space, page + 1599 count * PAGE_SIZE, (void *) new_cnt, leaf); 1489 1600 return 1; 1490 1601 } … … 1503 1614 1504 1615 /* 1505 * Now the interval is between intervals corresponding to (i - 1) and i. 1616 * Now the interval is between intervals corresponding 1617 * to (i - 1) and i. 1506 1618 */ 1507 if (overlaps(left_pg, left_cnt*PAGE_SIZE, page, count*PAGE_SIZE)) { 1508 if (page + count*PAGE_SIZE == left_pg + left_cnt*PAGE_SIZE) { 1619 if (overlaps(left_pg, left_cnt * PAGE_SIZE, page, 1620 count * PAGE_SIZE)) { 1621 if (page + count * PAGE_SIZE == 1622 left_pg + left_cnt*PAGE_SIZE) { 1509 1623 /* 1510 * The interval is contained in the interval (i - 1) 1511 * of the leaf and can be removed by updating the size 1512 * of the bigger interval. 1624 * The interval is contained in the 1625 * interval (i - 1) of the leaf and can 1626 * be removed by updating the size of 1627 * the bigger interval. 1513 1628 */ 1514 1629 leaf->value[i - 1] -= count; 1515 1630 return 1; 1516 } else if (page + count*PAGE_SIZE < left_pg + left_cnt*PAGE_SIZE) { 1631 } else if (page + count * PAGE_SIZE < 1632 left_pg + left_cnt * PAGE_SIZE) { 1517 1633 count_t new_cnt; 1518 1634 1519 1635 /* 1520 * The interval is contained in the interval (i - 1) 1521 * of the leaf but its removal requires both updating 1522 * the size of the original interval and 1636 * The interval is contained in the 1637 * interval (i - 1) of the leaf but its 1638 * removal requires both updating the 1639 * size of the original interval and 1523 1640 * also inserting a new interval. 1524 1641 */ 1525 new_cnt = ((left_pg + left_cnt*PAGE_SIZE) - (page + count*PAGE_SIZE)) >> PAGE_WIDTH; 1642 new_cnt = ((left_pg + 1643 left_cnt * PAGE_SIZE) - 1644 (page + count * PAGE_SIZE)) >> 1645 PAGE_WIDTH; 1526 1646 leaf->value[i - 1] -= count + new_cnt; 1527 btree_insert(&a->used_space, page + count*PAGE_SIZE, (void *) new_cnt, leaf); 1647 btree_insert(&a->used_space, page + 1648 count * PAGE_SIZE, (void *) new_cnt, 1649 leaf); 1528 1650 return 1; 1529 1651 } … … 1534 1656 1535 1657 error: 1536 panic("Inconsistency detected while removing %d pages of used space from %p.\n", count, page); 1658 panic("Inconsistency detected while removing %d pages of used space " 1659 "from %p.\n", count, page); 1537 1660 } 1538 1661 … … 1557 1680 * reference from all frames found there. 1558 1681 */ 1559 for (cur = sh_info->pagemap.leaf_head.next; cur != &sh_info->pagemap.leaf_head; cur = cur->next) { 1682 for (cur = sh_info->pagemap.leaf_head.next; 1683 cur != &sh_info->pagemap.leaf_head; cur = cur->next) { 1560 1684 btree_node_t *node; 1561 1685 int i; … … 1582 1706 unative_t sys_as_area_create(uintptr_t address, size_t size, int flags) 1583 1707 { 1584 if (as_area_create(AS, flags | AS_AREA_CACHEABLE, size, address, AS_AREA_ATTR_NONE, &anon_backend, NULL)) 1708 if (as_area_create(AS, flags | AS_AREA_CACHEABLE, size, address, 1709 AS_AREA_ATTR_NONE, &anon_backend, NULL)) 1585 1710 return (unative_t) address; 1586 1711 else … … 1613 1738 /* print out info about address space areas */ 1614 1739 link_t *cur; 1615 for (cur = as->as_area_btree.leaf_head.next; cur != &as->as_area_btree.leaf_head; cur = cur->next) { 1616 btree_node_t *node = list_get_instance(cur, btree_node_t, leaf_link); 1740 for (cur = as->as_area_btree.leaf_head.next; 1741 cur != &as->as_area_btree.leaf_head; cur = cur->next) { 1742 btree_node_t *node; 1743 1744 node = list_get_instance(cur, btree_node_t, leaf_link); 1617 1745 1618 1746 int i; … … 1622 1750 mutex_lock(&area->lock); 1623 1751 printf("as_area: %p, base=%p, pages=%d (%p - %p)\n", 1624 area, area->base, area->pages, area->base, area->base + area->pages*PAGE_SIZE); 1752 area, area->base, area->pages, area->base, 1753 area->base + area->pages*PAGE_SIZE); 1625 1754 mutex_unlock(&area->lock); 1626 1755 }
Note:
See TracChangeset
for help on using the changeset viewer.