Commit c9f19dff authored by Peter Maydell's avatar Peter Maydell
Browse files

Merge remote-tracking branch 'remotes/bonzini/tags/for-upstream' into staging



* switch to C11 atomics (Alex)
* Coverity fixes for IPMI (Corey), i386 (Paolo), qemu-char (Paolo)
* at long last, fail on wrong .pc files if -m32 is in use (Daniel)
* qemu-char regression fix (Daniel)
* SAS1068 device (Paolo)
* memory region docs improvements (Peter)
* target-i386 cleanups (Richard)
* qemu-nbd docs improvements (Sitsofe)
* thread-safe memory hotplug (Stefan)

# gpg: Signature made Tue 09 Feb 2016 16:09:30 GMT using RSA key ID 78C7AE83
# gpg: Good signature from "Paolo Bonzini <bonzini@gnu.org>"
# gpg:                 aka "Paolo Bonzini <pbonzini@redhat.com>"

* remotes/bonzini/tags/for-upstream: (33 commits)
  qemu-char, io: fix ordering of arguments for UDP socket creation
  MAINTAINERS: add all-match entry for qemu-devel@
  get_maintainer.pl: fall back to git if only lists are found
  target-i386: fix PSE36 mode
  docs/memory.txt: Improve list of different memory regions
  ipmi_bmc_sim: Add break to correct watchdog NMI check
  ipmi_bmc_sim: Fix off by one in check.
  ipmi: do not take/drop iothread lock
  target-i386: Deconstruct the cpu_T array
  target-i386: Tidy gen_add_A0_im
  target-i386: Rewrite leave
  target-i386: Rewrite gen_enter inline
  target-i386: Use gen_lea_v_seg in pusha/popa
  target-i386: Access segs via TCG registers
  target-i386: Use gen_lea_v_seg in stack subroutines
  target-i386: Use gen_lea_v_seg in gen_lea_modrm
  target-i386: Introduce mo_stacksize
  target-i386: Create gen_lea_v_seg
  char: fix repeated registration of tcp chardev I/O handlers
  kvm-all: trace: strerror fixup
  ...

Signed-off-by: default avatarPeter Maydell <peter.maydell@linaro.org>
parents f075c89f 150dcd1a
Loading
Loading
Loading
Loading
+5 −0
Original line number Diff line number Diff line
@@ -52,6 +52,11 @@ General Project Administration
------------------------------
M: Peter Maydell <peter.maydell@linaro.org>

All patches CC here
L: qemu-devel@nongnu.org
F: *
F: */

Responsible Disclosure, Reporting Security Issues
------------------------------
W: http://wiki.qemu.org/SecurityProcess
+24 −0
Original line number Diff line number Diff line
@@ -3063,6 +3063,30 @@ for i in $glib_modules; do
    fi
done

# Sanity check that the current size_t matches the
# size that glib thinks it should be. This catches
# problems on multi-arch where people try to build
# 32-bit QEMU while pointing at 64-bit glib headers
cat > $TMPC <<EOF
#include <glib.h>
#include <unistd.h>

#define QEMU_BUILD_BUG_ON(x) \
  typedef char qemu_build_bug_on[(x)?-1:1] __attribute__((unused));

int main(void) {
   QEMU_BUILD_BUG_ON(sizeof(size_t) != GLIB_SIZEOF_SIZE_T);
   return 0;
}
EOF

if ! compile_prog "-Werror $CFLAGS" "$LIBS" ; then
    error_exit "sizeof(size_t) doesn't match GLIB_SIZEOF_SIZE_T."\
               "You probably need to set PKG_CONFIG_LIBDIR"\
	       "to point to the right pkg-config files for your"\
	       "build target"
fi

# g_test_trap_subprocess added in 2.38. Used by some tests.
glib_subprocess=yes
if ! $pkg_config --atleast-version=2.38 glib-2.0; then
+1 −0
Original line number Diff line number Diff line
@@ -15,6 +15,7 @@ CONFIG_ES1370=y
CONFIG_LSI_SCSI_PCI=y
CONFIG_VMW_PVSCSI_SCSI_PCI=y
CONFIG_MEGASAS_SCSI_PCI=y
CONFIG_MPTSAS_SCSI_PCI=y
CONFIG_RTL8139_PCI=y
CONFIG_E1000_PCI=y
CONFIG_VMXNET3_PCI=y
+25 −1
Original line number Diff line number Diff line
@@ -26,14 +26,28 @@ These represent memory as seen from the CPU or a device's viewpoint.
Types of regions
----------------

There are four types of memory regions (all represented by a single C type
There are multiple types of memory regions (all represented by a single C type
MemoryRegion):

- RAM: a RAM region is simply a range of host memory that can be made available
  to the guest.
  You typically initialize these with memory_region_init_ram().  Some special
  purposes require the variants memory_region_init_resizeable_ram(),
  memory_region_init_ram_from_file(), or memory_region_init_ram_ptr().

- MMIO: a range of guest memory that is implemented by host callbacks;
  each read or write causes a callback to be called on the host.
  You initialize these with memory_region_io(), passing it a MemoryRegionOps
  structure describing the callbacks.

- ROM: a ROM memory region works like RAM for reads (directly accessing
  a region of host memory), but like MMIO for writes (invoking a callback).
  You initialize these with memory_region_init_rom_device().

- IOMMU region: an IOMMU region translates addresses of accesses made to it
  and forwards them to some other target memory region.  As the name suggests,
  these are only needed for modelling an IOMMU, not for simple devices.
  You initialize these with memory_region_init_iommu().

- container: a container simply includes other memory regions, each at
  a different offset.  Containers are useful for grouping several regions
@@ -45,12 +59,22 @@ MemoryRegion):
  can overlay a subregion of RAM with MMIO or ROM, or a PCI controller
  that does not prevent card from claiming overlapping BARs.

  You initialize a pure container with memory_region_init().

- alias: a subsection of another region.  Aliases allow a region to be
  split apart into discontiguous regions.  Examples of uses are memory banks
  used when the guest address space is smaller than the amount of RAM
  addressed, or a memory controller that splits main memory to expose a "PCI
  hole".  Aliases may point to any type of region, including other aliases,
  but an alias may not point back to itself, directly or indirectly.
  You initialize these with memory_region_init_alias().

- reservation region: a reservation region is primarily for debugging.
  It claims I/O space that is not supposed to be handled by QEMU itself.
  The typical use is to track parts of the address space which will be
  handled by the host kernel when KVM is enabled.
  You initialize these with memory_region_init_reservation(), or by
  passing a NULL callback parameter to memory_region_init_io().

It is valid to add subregions to a region which is not a pure container
(that is, to an MMIO, RAM or ROM region). This means that the region
+60 −15
Original line number Diff line number Diff line
@@ -980,8 +980,9 @@ bool cpu_physical_memory_test_and_clear_dirty(ram_addr_t start,
                                              ram_addr_t length,
                                              unsigned client)
{
    DirtyMemoryBlocks *blocks;
    unsigned long end, page;
    bool dirty;
    bool dirty = false;

    if (length == 0) {
        return false;
@@ -989,8 +990,22 @@ bool cpu_physical_memory_test_and_clear_dirty(ram_addr_t start,

    end = TARGET_PAGE_ALIGN(start + length) >> TARGET_PAGE_BITS;
    page = start >> TARGET_PAGE_BITS;
    dirty = bitmap_test_and_clear_atomic(ram_list.dirty_memory[client],
                                         page, end - page);

    rcu_read_lock();

    blocks = atomic_rcu_read(&ram_list.dirty_memory[client]);

    while (page < end) {
        unsigned long idx = page / DIRTY_MEMORY_BLOCK_SIZE;
        unsigned long offset = page % DIRTY_MEMORY_BLOCK_SIZE;
        unsigned long num = MIN(end - page, DIRTY_MEMORY_BLOCK_SIZE - offset);

        dirty |= bitmap_test_and_clear_atomic(blocks->blocks[idx],
                                              offset, num);
        page += num;
    }

    rcu_read_unlock();

    if (dirty && tcg_enabled()) {
        tlb_reset_dirty_range_all(start, length);
@@ -1504,6 +1519,47 @@ int qemu_ram_resize(ram_addr_t base, ram_addr_t newsize, Error **errp)
    return 0;
}

/* Called with ram_list.mutex held */
static void dirty_memory_extend(ram_addr_t old_ram_size,
                                ram_addr_t new_ram_size)
{
    ram_addr_t old_num_blocks = DIV_ROUND_UP(old_ram_size,
                                             DIRTY_MEMORY_BLOCK_SIZE);
    ram_addr_t new_num_blocks = DIV_ROUND_UP(new_ram_size,
                                             DIRTY_MEMORY_BLOCK_SIZE);
    int i;

    /* Only need to extend if block count increased */
    if (new_num_blocks <= old_num_blocks) {
        return;
    }

    for (i = 0; i < DIRTY_MEMORY_NUM; i++) {
        DirtyMemoryBlocks *old_blocks;
        DirtyMemoryBlocks *new_blocks;
        int j;

        old_blocks = atomic_rcu_read(&ram_list.dirty_memory[i]);
        new_blocks = g_malloc(sizeof(*new_blocks) +
                              sizeof(new_blocks->blocks[0]) * new_num_blocks);

        if (old_num_blocks) {
            memcpy(new_blocks->blocks, old_blocks->blocks,
                   old_num_blocks * sizeof(old_blocks->blocks[0]));
        }

        for (j = old_num_blocks; j < new_num_blocks; j++) {
            new_blocks->blocks[j] = bitmap_new(DIRTY_MEMORY_BLOCK_SIZE);
        }

        atomic_rcu_set(&ram_list.dirty_memory[i], new_blocks);

        if (old_blocks) {
            g_free_rcu(old_blocks, rcu);
        }
    }
}

static ram_addr_t ram_block_add(RAMBlock *new_block, Error **errp)
{
    RAMBlock *block;
@@ -1543,6 +1599,7 @@ static ram_addr_t ram_block_add(RAMBlock *new_block, Error **errp)
              (new_block->offset + new_block->max_length) >> TARGET_PAGE_BITS);
    if (new_ram_size > old_ram_size) {
        migration_bitmap_extend(old_ram_size, new_ram_size);
        dirty_memory_extend(old_ram_size, new_ram_size);
    }
    /* Keep the list sorted from biggest to smallest block.  Unlike QTAILQ,
     * QLIST (which has an RCU-friendly variant) does not have insertion at
@@ -1568,18 +1625,6 @@ static ram_addr_t ram_block_add(RAMBlock *new_block, Error **errp)
    ram_list.version++;
    qemu_mutex_unlock_ramlist();

    new_ram_size = last_ram_offset() >> TARGET_PAGE_BITS;

    if (new_ram_size > old_ram_size) {
        int i;

        /* ram_list.dirty_memory[] is protected by the iothread lock.  */
        for (i = 0; i < DIRTY_MEMORY_NUM; i++) {
            ram_list.dirty_memory[i] =
                bitmap_zero_extend(ram_list.dirty_memory[i],
                                   old_ram_size, new_ram_size);
       }
    }
    cpu_physical_memory_set_dirty_range(new_block->offset,
                                        new_block->used_length,
                                        DIRTY_CLIENTS_ALL);
Loading