From: Jan Kiszka <jan.kiszka@web.de>
To: Paolo Bonzini <pbonzini@redhat.com>
Cc: peter.maydell@linaro.org, qemu-devel@nongnu.org,
David Gibson <david@gibson.dropbear.id.au>
Subject: Re: [Qemu-devel] [PATCH 17/30] memory: add address_space_translate
Date: Sat, 25 May 2013 12:19:04 +0200 [thread overview]
Message-ID: <51A09018.7000901@web.de> (raw)
In-Reply-To: <51A06C9B.5060302@redhat.com>
[-- Attachment #1: Type: text/plain, Size: 6501 bytes --]
On 2013-05-25 09:47, Paolo Bonzini wrote:
> Il 25/05/2013 08:40, Jan Kiszka ha scritto:
>> On 2013-05-21 12:57, Paolo Bonzini wrote:
>>> Using phys_page_find to translate an AddressSpace to a
>>> MemoryRegionSection is unwieldy. It requires to pass the page
>>> index rather than the address, and later
>>> memory_region_section_addr has to be called. Replace
>>> memory_region_section_addr with a function that does all of it:
>>> call phys_page_find, compute the offset within the region, and
>>> check how big the current mapping is. This way, a large flat
>>> region can be written with a single lookup rather than a page at
>>> a time.
>>>
>>> address_space_translate will also provide a single point where
>>> IOMMU forwarding is implemented.
>>>
>>> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> --- cputlb.c
>>> | 20 ++--- exec.c | 201
>>> +++++++++++++++++++++++++++-----------------------
>>> include/exec/cputlb.h | 12 ++- include/exec/memory.h | 31
>>> ++++---- translate-all.c | 6 +- 5 files changed, 143
>>> insertions(+), 127 deletions(-)
>>>
>>> diff --git a/cputlb.c b/cputlb.c index aba7e44..1f85da0 100644
>>> --- a/cputlb.c +++ b/cputlb.c @@ -248,13 +248,18 @@ void
>>> tlb_set_page(CPUArchState *env, target_ulong vaddr, target_ulong
>>> code_address; uintptr_t addend; CPUTLBEntry *te; - hwaddr
>>> iotlb; + hwaddr iotlb, xlat, sz;
>>>
>>> assert(size >= TARGET_PAGE_SIZE); if (size != TARGET_PAGE_SIZE)
>>> { tlb_add_large_page(env, vaddr, size); } - section =
>>> phys_page_find(address_space_memory.dispatch, paddr >>
>>> TARGET_PAGE_BITS); + + sz = size; + section =
>>> address_space_translate(&address_space_memory, paddr, &xlat,
>>> &sz, + false); +
>>> assert(sz >= TARGET_PAGE_SIZE); + #if defined(DEBUG_TLB)
>>> printf("tlb_set_page: vaddr=" TARGET_FMT_lx " paddr=0x"
>>> TARGET_FMT_plx " prot=%x idx=%d pd=0x%08lx\n", @@ -269,15 +274,14
>>> @@ void tlb_set_page(CPUArchState *env, target_ulong vaddr, } if
>>> (memory_region_is_ram(section->mr) ||
>>> memory_region_is_romd(section->mr)) { - addend =
>>> (uintptr_t)memory_region_get_ram_ptr(section->mr) - +
>>> memory_region_section_addr(section, paddr); + addend =
>>> (uintptr_t)memory_region_get_ram_ptr(section->mr) + xlat; } else
>>> { addend = 0; }
>>>
>>> code_address = address; - iotlb =
>>> memory_region_section_get_iotlb(env, section, vaddr, paddr,
>>> prot, - &address); +
>>> iotlb = memory_region_section_get_iotlb(env, section, vaddr,
>>> paddr, xlat, + prot,
>>> &address);
>>>
>>> index = (vaddr >> TARGET_PAGE_BITS) & (CPU_TLB_SIZE - 1);
>>> env->iotlb[mmu_idx][index] = iotlb - vaddr; @@ -300,9 +304,7 @@
>>> void tlb_set_page(CPUArchState *env, target_ulong vaddr, /* Write
>>> access calls the I/O callback. */ te->addr_write = address |
>>> TLB_MMIO; } else if (memory_region_is_ram(section->mr) -
>>> && !cpu_physical_memory_is_dirty( -
>>> section->mr->ram_addr - +
>>> memory_region_section_addr(section, paddr))) { +
>>> && !cpu_physical_memory_is_dirty(section->mr->ram_addr + xlat))
>>> { te->addr_write = address | TLB_NOTDIRTY; } else {
>>> te->addr_write = address; diff --git a/exec.c b/exec.c index
>>> 82da067..e5ee8ff 100644 --- a/exec.c +++ b/exec.c @@ -182,7
>>> +182,7 @@ static void phys_page_set(AddressSpaceDispatch *d,
>>> phys_page_set_level(&d->phys_map, &index, &nb, leaf, P_L2_LEVELS
>>> - 1); }
>>>
>>> -MemoryRegionSection *phys_page_find(AddressSpaceDispatch *d,
>>> hwaddr index) +static MemoryRegionSection
>>> *phys_page_find(AddressSpaceDispatch *d, hwaddr index) {
>>> PhysPageEntry lp = d->phys_map; PhysPageEntry *p; @@ -198,6
>>> +198,22 @@ MemoryRegionSection
>>> *phys_page_find(AddressSpaceDispatch *d, hwaddr index) return
>>> &phys_sections[lp.ptr]; }
>>>
>>> +MemoryRegionSection *address_space_translate(AddressSpace *as,
>>> hwaddr addr, + hwaddr
>>> *xlat, hwaddr *plen, +
>>> bool is_write) +{ + MemoryRegionSection *section; + +
>>> section = phys_page_find(as->dispatch, addr >>
>>> TARGET_PAGE_BITS); + /* Compute offset within
>>> MemoryRegionSection */ + addr -=
>>> section->offset_within_address_space; + *plen =
>>> MIN(section->size - addr, *plen);
>
>> This limitation causes problems. Consider two overlapping memory
>> regions A and B. A handles 4-byte accesses and is at least 4 bytes
>> long, B only deals with a single byte. They overlap like this:
>
>> B (prio 1): X A (prio 0): XXXX... ^access here with 4 bytes
>> length
>
>> Now if an access happens at the marked position, it is split into
>> one 2-byte access to A, followed by a one-byte access to B and
>> another one-byte access to A. But the right access emulation would
>> be 4-bytes to A, no?
>
> I guess it depends on the width of the bus. On a 16-bit computer the
> right thing to do would be to split the write in two, one two-byte
> access to A and one two-byte access to B. But as a first
> approximation the fix you suggest is the right one. Implementing bus
> width in TCG is tricky, so we should get by with the simple fix.
>
> This patch is not in the pull request I sent, so there is time to make
> it work. Is it simply
>
> - *plen = MIN(section->size - addr, *plen);
> + addr += section->offset_within_memory_region;
> + *plen = MIN(section->mr->size - addr, *plen);
>
> or something like that? If you post it as a diff I can squash it in.
This works for me now:
diff --git a/exec.c b/exec.c
index 1610604..3d36bc7 100644
--- a/exec.c
+++ b/exec.c
@@ -210,13 +210,15 @@ MemoryRegionSection *address_space_translate(AddressSpace *as, hwaddr addr,
IOMMUTLBEntry iotlb;
MemoryRegionSection *section;
hwaddr len = *plen;
+ Int128 diff;
for (;;) {
section = address_space_lookup_region(as, addr);
/* Compute offset within MemoryRegionSection */
addr -= section->offset_within_address_space;
- len = MIN(section->size - addr, len);
+ diff = int128_sub(section->mr->size, int128_make64(addr));
+ len = MIN(int128_get64(diff), len);
/* Compute offset within MemoryRegion */
addr += section->offset_within_region;
Jan
[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 263 bytes --]
next prev parent reply other threads:[~2013-05-25 10:19 UTC|newest]
Thread overview: 106+ messages / expand[flat|nested] mbox.gz Atom feed top
2013-05-21 10:57 [Qemu-devel] [PATCH 00/30] Introduction of IOMMUs into the memory API Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 01/30] exec: remove obsolete comment Paolo Bonzini
2013-05-21 11:36 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 02/30] exec: eliminate qemu_put_ram_ptr Paolo Bonzini
2013-05-21 11:38 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 03/30] exec: make qemu_get_ram_ptr private Paolo Bonzini
2013-05-21 11:38 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 04/30] exec: eliminate stq_phys_notdirty Paolo Bonzini
2013-05-23 17:32 ` Peter Maydell
2013-05-23 19:18 ` Anthony Liguori
2013-05-23 19:22 ` Paolo Bonzini
2013-05-23 23:14 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 05/30] memory: assert that PhysPageEntry's ptr does not overflow Paolo Bonzini
2013-05-23 17:36 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 06/30] memory: allow memory_region_find() to run on non-root memory regions Paolo Bonzini
2013-05-23 17:52 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 07/30] memory: Replace open-coded memory_region_is_romd Paolo Bonzini
2013-05-21 11:54 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 08/30] memory: Rename readable flag to romd_mode Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 09/30] memory: do not duplicate memory_region_destructor_none Paolo Bonzini
2013-05-21 11:55 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 10/30] memory: make memory_global_sync_dirty_bitmap take an AddressSpace Paolo Bonzini
2013-05-21 11:56 ` Peter Maydell
2013-05-23 1:05 ` David Gibson
2013-05-21 10:57 ` [Qemu-devel] [PATCH 11/30] memory: fix address space initialization/destruction Paolo Bonzini
2013-05-21 11:58 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 12/30] s390x: reduce TARGET_PHYS_ADDR_SPACE_BITS to 62 Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 13/30] memory: limit sections in the radix tree to the actual address space size Paolo Bonzini
2013-05-21 12:02 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 14/30] memory: create FlatView for new address spaces Paolo Bonzini
2013-05-21 12:03 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 15/30] memory: add address_space_valid Paolo Bonzini
2013-05-23 12:05 ` David Gibson
2013-05-23 14:22 ` Jan Kiszka
2013-05-23 14:43 ` Paolo Bonzini
2013-05-23 18:04 ` Peter Maydell
2013-05-24 6:13 ` Jan Kiszka
2013-05-24 10:28 ` Jan Kiszka
2013-05-24 10:50 ` Peter Maydell
2013-05-24 11:02 ` Jan Kiszka
2013-05-24 8:02 ` Paolo Bonzini
2013-05-24 10:52 ` Peter Maydell
2013-05-24 12:58 ` Paolo Bonzini
2013-05-24 13:27 ` Peter Maydell
2013-05-24 13:33 ` Paolo Bonzini
2013-05-24 13:38 ` Peter Maydell
2013-05-25 3:44 ` David Gibson
2013-05-25 9:23 ` Peter Maydell
2013-05-26 13:02 ` David Gibson
2013-05-21 10:57 ` [Qemu-devel] [PATCH 16/30] memory: clean up phys_page_find Paolo Bonzini
2013-05-23 18:06 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 17/30] memory: add address_space_translate Paolo Bonzini
2013-05-23 7:09 ` liu ping fan
2013-05-23 9:59 ` Paolo Bonzini
2013-05-23 13:06 ` liu ping fan
2013-05-23 13:17 ` Paolo Bonzini
2013-05-23 18:15 ` Peter Maydell
2013-05-25 6:40 ` Jan Kiszka
2013-05-25 7:47 ` Paolo Bonzini
2013-05-25 10:19 ` Jan Kiszka [this message]
2013-05-25 11:20 ` Paolo Bonzini
2013-05-25 11:30 ` Jan Kiszka
2013-05-26 8:56 ` Paolo Bonzini
2013-05-26 9:02 ` Jan Kiszka
2013-05-27 7:20 ` Paolo Bonzini
2013-05-27 7:23 ` Jan Kiszka
2013-05-27 8:19 ` Paolo Bonzini
2013-05-27 8:37 ` Jan Kiszka
2013-05-27 10:33 ` Peter Maydell
2013-05-27 10:45 ` Paolo Bonzini
2013-05-27 11:33 ` Peter Maydell
2013-05-26 9:01 ` Paolo Bonzini
2013-05-26 9:12 ` Jan Kiszka
2013-05-26 18:23 ` Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 18/30] memory: add return value to address_space_rw/read/write Paolo Bonzini
2013-05-23 18:18 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 19/30] memory: Introduce address_space_lookup_region Paolo Bonzini
2013-05-23 18:19 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 20/30] memory: iommu support Paolo Bonzini
2013-05-23 18:24 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 21/30] memory: Add iommu map/unmap notifiers Paolo Bonzini
2013-05-23 18:27 ` Peter Maydell
2013-05-23 19:24 ` Paolo Bonzini
2013-05-29 4:08 ` David Gibson
2013-05-21 10:57 ` [Qemu-devel] [PATCH 22/30] vfio: abort if an emulated iommu is used Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 23/30] spapr: convert TCE API to use an opaque type Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 24/30] spapr: make IOMMU translation go through IOMMUTLBEntry Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 25/30] spapr: use memory core for iommu support Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 26/30] dma: eliminate old-style IOMMU support Paolo Bonzini
2013-05-23 18:31 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 27/30] pci: use memory core for iommu support Paolo Bonzini
2013-05-23 18:36 ` Peter Maydell
2013-05-23 21:22 ` Michael S. Tsirkin
2013-05-21 10:57 ` [Qemu-devel] [PATCH 28/30] spapr_vio: take care of creating our own AddressSpace/DMAContext Paolo Bonzini
2013-05-21 10:57 ` [Qemu-devel] [PATCH 29/30] dma: eliminate DMAContext Paolo Bonzini
2013-05-23 18:40 ` Peter Maydell
2013-05-21 10:57 ` [Qemu-devel] [PATCH 30/30] memory: give name to every AddressSpace Paolo Bonzini
2013-05-23 18:46 ` Peter Maydell
2013-05-22 2:30 ` [Qemu-devel] [PATCH 00/30] Introduction of IOMMUs into the memory API Alexey Kardashevskiy
2013-05-22 9:24 ` Paolo Bonzini
2013-05-23 17:08 ` Paolo Bonzini
2013-05-23 17:25 ` Peter Maydell
2013-05-23 17:30 ` Paolo Bonzini
2013-05-23 18:47 ` Peter Maydell
2013-05-24 14:12 ` Alexey Kardashevskiy
2013-05-24 14:20 ` Paolo Bonzini
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=51A09018.7000901@web.de \
--to=jan.kiszka@web.de \
--cc=david@gibson.dropbear.id.au \
--cc=pbonzini@redhat.com \
--cc=peter.maydell@linaro.org \
--cc=qemu-devel@nongnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).