diff --git a/xen/arch/x86/domain_page.c b/xen/arch/x86/domain_page.c index efda6af..7c61adc 100644 --- a/xen/arch/x86/domain_page.c +++ b/xen/arch/x86/domain_page.c @@ -59,12 +59,12 @@ void __init mapcache_override_current(struct vcpu *v) void *map_domain_page(unsigned long mfn) { unsigned long flags; - unsigned int idx, i; + unsigned int idx, i, j = 0; struct vcpu *v; struct mapcache_domain *dcache; struct mapcache_vcpu *vcache; struct vcpu_maphash_entry *hashent; - + int branch = 0; #ifdef NDEBUG if ( mfn <= PFN_DOWN(__pa(HYPERVISOR_VIRT_END - 1)) ) return mfn_to_virt(mfn); @@ -119,27 +119,53 @@ void *map_domain_page(unsigned long mfn) accum |= ~dcache->inuse[i]; } - if ( accum ) + if ( accum ) { idx = find_first_zero_bit(dcache->inuse, dcache->entries); + branch |= 1; + } else { + branch |= 2; /* Replace a hash entry instead. */ i = MAPHASH_HASHFN(mfn); do { hashent = &vcache->hash[i]; if ( hashent->idx != MAPHASHENT_NOTINUSE && !hashent->refcnt ) { + branch |= 4; idx = hashent->idx; ASSERT(l1e_get_pfn(MAPCACHE_L1ENT(idx)) == hashent->mfn); l1e_write(&MAPCACHE_L1ENT(idx), l1e_empty()); hashent->idx = MAPHASHENT_NOTINUSE; hashent->mfn = ~0UL; + if (idx >= dcache->entries) { + branch |= 8; + gdprintk(XENLOG_INFO, "mfn (%lx) -> %ld idx (iter:%d)\n", mfn, MAPHASH_HASHFN(mfn), j); + + for (i = 0; i < MAPHASH_ENTRIES;i++) { + hashent = &vcache->hash[i]; + + gdprintk(XENLOG_INFO, "[%d] idx=%d, mfn=0x%lx, refcnt: %d\n", + i, hashent->idx, hashent->mfn, hashent->refcnt); + } + } break; } if ( ++i == MAPHASH_ENTRIES ) i = 0; + j++; } while ( i != MAPHASH_HASHFN(mfn) ); } + if (idx >= dcache->entries) { + gdprintk(XENLOG_INFO, "mfn (%lx) -> %ld idx: %d(i:%d,j:%d), branch:%x\n", mfn, MAPHASH_HASHFN(mfn), idx, i, j, branch); + + for (i = 0; i < MAPHASH_ENTRIES;i++) { + hashent = &vcache->hash[i]; + + gdprintk(XENLOG_INFO, "[%d] idx=%d, mfn=0x%lx, refcnt: %d\n", + i, hashent->idx, hashent->mfn, hashent->refcnt); + } + } BUG_ON(idx >= dcache->entries); /* /Second/, flush TLBs. */ @@ -254,6 +280,7 @@ int mapcache_domain_init(struct domain *d) 2 * PFN_UP(BITS_TO_LONGS(MAPCACHE_ENTRIES) * sizeof(long))) > MAPCACHE_VIRT_START + (PERDOMAIN_SLOT_MBYTES << 20)); bitmap_pages = PFN_UP(BITS_TO_LONGS(MAPCACHE_ENTRIES) * sizeof(long)); + gdprintk(XENLOG_INFO, "domain bitmap pages: %d\n", bitmap_pages); dcache->inuse = (void *)MAPCACHE_VIRT_END + PAGE_SIZE; dcache->garbage = dcache->inuse + (bitmap_pages + 1) * PAGE_SIZE / sizeof(long); @@ -276,6 +303,7 @@ int mapcache_vcpu_init(struct vcpu *v) if ( is_hvm_vcpu(v) || !dcache->inuse ) return 0; + gdprintk(XENLOG_INFO, "ents: %d, entries: %d\n", ents, dcache->entries); if ( ents > dcache->entries ) { /* Populate page tables. */