1. 24 7月, 2008 1 次提交
  2. 03 8月, 2008 2 次提交
    • E
      ext4: lock block groups when initializing · b5f10eed
      Eric Sandeen 提交于
      I noticed when filling a 1T filesystem with 4 threads using the
      fs_mark benchmark:
      
      fs_mark -d /mnt/test -D 256 -n 100000 -t 4 -s 20480 -F -S 0
      
      that I occasionally got checksum mismatch errors:
      
      EXT4-fs error (device sdb): ext4_init_inode_bitmap: Checksum bad for group 6935
      
      etc.  I'd reliably get 4-5 of them during the run.
      
      It appears that the problem is likely a race to init the bg's
      when the uninit_bg feature is enabled.
      
      With the patch below, which adds sb_bgl_locking around initialization,
      I was able to complete several runs with no errors or warnings.
      Signed-off-by: NEric Sandeen <sandeen@redhat.com>
      Signed-off-by: NTheodore Ts'o <tytso@mit.edu>
      b5f10eed
    • E
      ext4: sync up block and inode bitmap reading functions · e29d1cde
      Eric Sandeen 提交于
      ext4_read_block_bitmap and read_inode_bitmap do essentially
      the same thing, and yet they are structured quite differently.
      I came across this difference while looking at doing bg locking
      during bg initialization.
      
      This patch:
      
      * removes unnecessary casts in the error messages
      * renames read_inode_bitmap to ext4_read_inode_bitmap
      * and more substantially, restructures the inode bitmap
        reading function to be more like the block bitmap counterpart.
      
      The change to the inode bitmap reader simplifies the locking
      to be applied in the next patch.
      Signed-off-by: NEric Sandeen <sandeen@redhat.com>
      Signed-off-by: NTheodore Ts'o <tytso@mit.edu>
      e29d1cde
  3. 27 7月, 2008 1 次提交
  4. 03 8月, 2008 1 次提交
  5. 29 7月, 2008 35 次提交
    • L
      Linux 2.6.27-rc1 · 6e86841d
      Linus Torvalds 提交于
      6e86841d
    • L
      Merge git://git.kernel.org/pub/scm/linux/kernel/git/rusty/linux-2.6-for-linus · 7874d351
      Linus Torvalds 提交于
      * git://git.kernel.org/pub/scm/linux/kernel/git/rusty/linux-2.6-for-linus:
        lguest: turn Waker into a thread, not a process
        lguest: Enlarge virtio rings
        lguest: Use GSO/IFF_VNET_HDR extensions on tun/tap
        lguest: Remove 'network: no dma buffer!' warning
        lguest: Adaptive timeout
        lguest: Tell Guest net not to notify us on every packet xmit
        lguest: net block unneeded receive queue update notifications
        lguest: wrap last_avail accesses.
        lguest: use cpu capability accessors
        lguest: virtio-rng support
        lguest: Support assigning a MAC address
        lguest: Don't leak /dev/zero fd
        lguest: fix verbose printing of device features.
        lguest: fix switcher_page leak on unload
        lguest: Guest int3 fix
        lguest: set max_pfn_mapped, growl loudly at Yinghai Lu
      7874d351
    • L
      Merge branch 'for-linus' of git://git.o-hand.com/linux-mfd · 5dfb66ba
      Linus Torvalds 提交于
      * 'for-linus' of git://git.o-hand.com/linux-mfd:
        mfd: accept pure device as a parent, not only platform_device
        mfd: add platform_data to mfd_cell
        mfd: Coding style fixes
        mfd: Use to_platform_device instead of container_of
      5dfb66ba
    • L
      Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jbarnes/pci-2.6 · 1d9b9f6a
      Linus Torvalds 提交于
      * 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jbarnes/pci-2.6: (21 commits)
        x86/PCI: use dev_printk when possible
        PCI: add D3 power state avoidance quirk
        PCI: fix bogus "'device' may be used uninitialized" warning in pci_slot
        PCI: add an option to allow ASPM enabled forcibly
        PCI: disable ASPM on pre-1.1 PCIe devices
        PCI: disable ASPM per ACPI FADT setting
        PCI MSI: Don't disable MSIs if the mask bit isn't supported
        PCI: handle 64-bit resources better on 32-bit machines
        PCI: rewrite PCI BAR reading code
        PCI: document pci_target_state
        PCI hotplug: fix typo in pcie hotplug output
        x86 gart: replace to_pages macro with iommu_num_pages
        x86, AMD IOMMU: replace to_pages macro with iommu_num_pages
        iommu: add iommu_num_pages helper function
        dma-coherent: add documentation to new interfaces
        Cris: convert to using generic dma-coherent mem allocator
        Sh: use generic per-device coherent dma allocator
        ARM: support generic per-device coherent dma mem
        Generic dma-coherent: fix DMA_MEMORY_EXCLUSIVE
        x86: use generic per-device dma coherent allocator
        ...
      1d9b9f6a
    • L
    • L
      Fix 'get_user_pages_fast()' with non-page-aligned start address · 9b79022c
      Linus Torvalds 提交于
      Alexey Dobriyan reported trouble with LTP with the new fast-gup code,
      and Johannes Weiner debugged it to non-page-aligned addresses, where the
      new get_user_pages_fast() code would do all the wrong things, including
      just traversing past the end of the requested area due to 'addr' never
      matching 'end' exactly.
      
      This is not a pretty fix, and we may actually want to move the alignment
      into generic code, leaving just the core code per-arch, but Alexey
      verified that the vmsplice01 LTP test doesn't crash with this.
      Reported-and-tested-by: NAlexey Dobriyan <adobriyan@gmail.com>
      Debugged-by: NJohannes Weiner <hannes@saeurebad.de>
      Cc: Nick Piggin <npiggin@suse.de>
      Cc: Andrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      9b79022c
    • R
      lguest: turn Waker into a thread, not a process · 8c79873d
      Rusty Russell 提交于
      lguest uses a Waker process to break it out of the kernel (ie.
      actually running the guest) when file descriptor needs attention.
      
      Changing this from a process to a thread somewhat simplifies things:
      it can directly access the fd_set of things to watch.  More
      importantly, it means that the Waker can see Guest memory correctly,
      so /dev/vring file descriptors will work as anticipated (the
      alternative is to actually mmap MAP_SHARED, but you can't do that with
      /dev/zero).
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      8c79873d
    • R
      lguest: Enlarge virtio rings · 0f0c4fab
      Rusty Russell 提交于
      With big packets, 128 entries is a little small.
      
      Guest -> Host 1GB TCP:
      Before: 8.43625 seconds xmit 95640 recv 198266 timeout 49771 usec 1252
      After: 8.01099 seconds xmit 49200 recv 102263 timeout 26014 usec 2118
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      0f0c4fab
    • R
      lguest: Use GSO/IFF_VNET_HDR extensions on tun/tap · 398f187d
      Rusty Russell 提交于
      Guest -> Host 1GB TCP:
      Before 20.1974 seconds xmit 214510 recv 5 timeout 214491 usec 278
      After 8.43625 seconds xmit 95640 recv 198266 timeout 49771 usec 1252
      
      Host -> Guest 1GB TCP:
      Before: Seconds 9.98854 xmit 172166 recv 5344 timeout 172157 usec 251
      After: Seconds 5.72803 xmit 244322 recv 9919 timeout 244302 usec 156
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      398f187d
    • R
      lguest: Remove 'network: no dma buffer!' warning · 9254926f
      Rusty Russell 提交于
      This warning can happen a lot under load, and it should be warnx not
      warn anwyay.
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      9254926f
    • R
      lguest: Adaptive timeout · aa124984
      Rusty Russell 提交于
      Since the correct timeout value varies, use a heuristic which adjusts
      the timeout depending on how many packets we've seen.  This gives
      slightly worse results, but doesn't need tweaking when GSO is
      introduced.
      
      500 usec	19.1887		xmit 561141 recv 1 timeout 559657
      Dynamic (278)	20.1974		xmit 214510 recv 5 timeout 214491 usec 278
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      aa124984
    • R
      lguest: Tell Guest net not to notify us on every packet xmit · a161883a
      Rusty Russell 提交于
      virtio_ring has the ability to suppress notifications.  This prevents
      a guest exit for every packet, but we need to set a timer on packet
      receipt to re-check if there were any remaining packets.
      
      Here are the times for 1G TCP Guest->Host with different timeout
      settings (it matters because the TCP window doesn't grow big enough to
      fill the entire buffer):
      
      Timeout value	Seconds		Xmit/Recv/Timeout
      None (before)	25.3784		xmit 7750233 recv 1
      2500 usec	62.5119		xmit 207020 recv 2 timeout 207020
      1000 usec	34.5379		xmit 207003 recv 2 timeout 207003
      750 usec	29.2305		xmit 207002 recv 1 timeout 207002
      500 usec	19.1887		xmit 561141 recv 1 timeout 559657
      250 usec	20.0465		xmit 214128 recv 2 timeout 214110
      100 usec	19.2583		xmit 561621 recv 1 timeout 560153
      
      (Note that these values are sensitive to the GSO patches which come
       later, and probably other traffic-related variables, so take with a
       large grain of salt).
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      a161883a
    • R
      lguest: net block unneeded receive queue update notifications · 5dae785a
      Rusty Russell 提交于
      Number of exits transmitting 10GB Guest->Host before:
      	network xmit 7858610 recv 118136
      
      After:
      	network xmit 7750233 recv 1
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      5dae785a
    • R
      lguest: wrap last_avail accesses. · b5111790
      Rusty Russell 提交于
      To simplify the transition to when we publish indices in the ring
      (and make shuffling my patch queue easier), wrap them in a lg_last_avail()
      macro.
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      b5111790
    • A
      lguest: use cpu capability accessors · cf485e56
      Andrew Morton 提交于
      To support my little make-x86-bitops-use-proper-typechecking projectlet.
      
      Cc: Thomas Gleixner <tglx@linutronix.de>
      Cc: Andrea Arcangeli <andrea@qumranet.com>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Acked-by: NIngo Molnar <mingo@elte.hu>
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      cf485e56
    • R
      lguest: virtio-rng support · 28fd6d7f
      Rusty Russell 提交于
      This is a simple patch to add support for the virtio "hardware random
      generator" to lguest.  It gets about 1.2 MB/sec reading from /dev/hwrng
      in the guest.
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      28fd6d7f
    • M
      lguest: Support assigning a MAC address · dec6a2be
      Mark McLoughlin 提交于
      If you've got a nice DHCP configuration which maps MAC
      addresses to specific IP addresses, then you're going to
      want to start your guest with one of those MAC addresses.
      
      Also, in Fedora, we have persistent network interface naming
      based on the MAC address, so with randomly assigned
      addresses you're soon going to hit eth13. Who knows what
      will happen then!
      
      Allow assigning a MAC address to the network interface with
      e.g.
      
        --tunnet=bridge:eth0:00:FF:95:6B:DA:3D
      
      or:
      
        --tunnet=192.168.121.1:00:FF:95:6B:DA:3D
      
      which is pretty unintelligable, but ...
      
      (includes Rusty's minor rework)
      Signed-off-by: NMark McLoughlin <markmc@redhat.com>
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      dec6a2be
    • M
      lguest: Don't leak /dev/zero fd · 34bdaab4
      Mark McLoughlin 提交于
      Signed-off-by: NMark McLoughlin <markmc@redhat.com>
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      34bdaab4
    • R
      lguest: fix verbose printing of device features. · 32c68e5c
      Rusty Russell 提交于
      %02x is more appropriate for bytes than %08x.
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      32c68e5c
    • J
      lguest: fix switcher_page leak on unload · 0a707210
      Johannes Weiner 提交于
      map_switcher allocates the array, unmap_switcher has to free it
      accordingly.
      Signed-off-by: NJohannes Weiner <hannes@saeurebad.de>
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      0a707210
    • R
      lguest: Guest int3 fix · 0c12091d
      Rusty Russell 提交于
      Ron Minnich noticed that guest userspace gets a GPF when it tries to int3:
      we need to copy the privilege level from the guest-supplied IDT to the real
      IDT.  int3 is the only common case where guest userspace expects to invoke
      an interrupt, so that's the symptom of failing to do this.
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      0c12091d
    • R
      lguest: set max_pfn_mapped, growl loudly at Yinghai Lu · 5d006d8d
      Rusty Russell 提交于
      6af61a76 'x86: clean up max_pfn_mapped
      usage - 32-bit' makes the following comment:
      
          XEN PV and lguest may need to assign max_pfn_mapped too.
      
      But no CC.  Yinghai, wasting fellow developers' time is a VERY bad
      habit.  If you do it again, I will hunt you down and try to extract
      the three hours of my life I just lost :)
      Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
      Cc: Yinghai Lu <yhlu.kernel@gmail.com>
      5d006d8d
    • D
    • A
      include/asm-generic/pgtable-nopmd.h: macros are noxious, reason #435 · 34ee5501
      Andrew Morton 提交于
      arch/x86/mm/pgtable.c: In function 'pgd_mop_up_pmds':
        arch/x86/mm/pgtable.c:194: warning: unused variable 'pmd'
      
      Cc: Ingo Molnar <mingo@elte.hu>
      Cc: Thomas Gleixner <tglx@linutronix.de>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      34ee5501
    • M
      sh7760fb: write colormap value to hardware · c27ef92d
      Manuel Lauss 提交于
      The computed color value is never actually written to hardware
      colormap register.
      Signed-off-by: NManuel Lauss <mano@roarinelk.homelinux.net>
      Cc: Nobuhiro Iwamatsu <iwamatsu.nobuhiro@renesas.com>
      Cc: Munakata Hisao <munakata.hisao@renesas.com>
      Cc: Paul Mundt <lethal@linux-sh.org>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      c27ef92d
    • E
      eCryptfs: use page_alloc not kmalloc to get a page of memory · 7fcba054
      Eric Sandeen 提交于
      With SLUB debugging turned on in 2.6.26, I was getting memory corruption
      when testing eCryptfs.  The root cause turned out to be that eCryptfs was
      doing kmalloc(PAGE_CACHE_SIZE); virt_to_page() and treating that as a nice
      page-aligned chunk of memory.  But at least with SLUB debugging on, this
      is not always true, and the page we get from virt_to_page does not
      necessarily match the PAGE_CACHE_SIZE worth of memory we got from kmalloc.
      
      My simple testcase was 2 loops doing "rm -f fileX; cp /tmp/fileX ." for 2
      different multi-megabyte files.  With this change I no longer see the
      corruption.
      Signed-off-by: NEric Sandeen <sandeen@redhat.com>
      Acked-by: NMichael Halcrow <mhalcrow@us.ibm.com>
      Acked-by: NRik van Riel <riel@redhat.com>
      Cc: <stable@kernel.org>		[2.6.25.x, 2.6.26.x]
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      7fcba054
    • A
      gpio: fix build on CONFIG_GPIO_SYSFS=n · 25947d5a
      Atsushi Nemoto 提交于
      If CONFIG_GENERIC_GPIO=y && CONFIG_GPIO_SYSFS=n, gpio_export() in
      asm-generic/gpio.h refers -ENOSYS and causes build error.
      Signed-off-by: NAtsushi Nemoto <anemo@mba.ocn.ne.jp>
      Acked-by: NDavid Brownell <dbrownell@users.sourceforge.net>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      25947d5a
    • Y
      bio-integrity: remove EXPORT_SYMBOL for bio_integrity_init_slab() · e3b6e806
      Yoichi Yuasa 提交于
      I got section mismatch message about bio_integrity_init_slab().
      
      WARNING: fs/built-in.o(__ksymtab+0xb60): Section mismatch in reference from the variable __ksymtab_bio_integrity_init_slab to the function .init.text:bio_integrity_init_slab()
      
      The symbol bio_integrity_init_slab is exported and annotated __init Fix
      this by removing the __init annotation of bio_integrity_init_slab or drop
      the export.
      
      It only call from init_bio().  The EXPORT_SYMBOL() can be removed.
      Signed-off-by: NYoichi Yuasa <yoichi_yuasa@tripeaks.co.jp>
      Cc: "Martin K. Petersen" <martin.petersen@oracle.com>
      Cc: Jens Axboe <jens.axboe@oracle.com>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      e3b6e806
    • H
      vfs: pagecache usage optimization for pagesize!=blocksize · 8ab22b9a
      Hisashi Hifumi 提交于
      When we read some part of a file through pagecache, if there is a
      pagecache of corresponding index but this page is not uptodate, read IO
      is issued and this page will be uptodate.
      
      I think this is good for pagesize == blocksize environment but there is
      room for improvement on pagesize != blocksize environment.  Because in
      this case a page can have multiple buffers and even if a page is not
      uptodate, some buffers can be uptodate.
      
      So I suggest that when all buffers which correspond to a part of a file
      that we want to read are uptodate, use this pagecache and copy data from
      this pagecache to user buffer even if a page is not uptodate.  This can
      reduce read IO and improve system throughput.
      
      I wrote a benchmark program and got result number with this program.
      
      This benchmark do:
      
        1: mount and open a test file.
      
        2: create a 512MB file.
      
        3: close a file and umount.
      
        4: mount and again open a test file.
      
        5: pwrite randomly 300000 times on a test file.  offset is aligned
           by IO size(1024bytes).
      
        6: measure time of preading randomly 100000 times on a test file.
      
      The result was:
      	2.6.26
              330 sec
      
      	2.6.26-patched
              226 sec
      
      Arch:i386
      Filesystem:ext3
      Blocksize:1024 bytes
      Memory: 1GB
      
      On ext3/4, a file is written through buffer/block.  So random read/write
      mixed workloads or random read after random write workloads are optimized
      with this patch under pagesize != blocksize environment.  This test result
      showed this.
      
      The benchmark program is as follows:
      
      #include <stdio.h>
      #include <sys/types.h>
      #include <sys/stat.h>
      #include <fcntl.h>
      #include <unistd.h>
      #include <time.h>
      #include <stdlib.h>
      #include <string.h>
      #include <sys/mount.h>
      
      #define LEN 1024
      #define LOOP 1024*512 /* 512MB */
      
      main(void)
      {
      	unsigned long i, offset, filesize;
      	int fd;
      	char buf[LEN];
      	time_t t1, t2;
      
      	if (mount("/dev/sda1", "/root/test1/", "ext3", 0, 0) < 0) {
      		perror("cannot mount\n");
      		exit(1);
      	}
      	memset(buf, 0, LEN);
      	fd = open("/root/test1/testfile", O_CREAT|O_RDWR|O_TRUNC);
      	if (fd < 0) {
      		perror("cannot open file\n");
      		exit(1);
      	}
      	for (i = 0; i < LOOP; i++)
      		write(fd, buf, LEN);
      	close(fd);
      	if (umount("/root/test1/") < 0) {
      		perror("cannot umount\n");
      		exit(1);
      	}
      	if (mount("/dev/sda1", "/root/test1/", "ext3", 0, 0) < 0) {
      		perror("cannot mount\n");
      		exit(1);
      	}
      	fd = open("/root/test1/testfile", O_RDWR);
      	if (fd < 0) {
      		perror("cannot open file\n");
      		exit(1);
      	}
      
      	filesize = LEN * LOOP;
      	for (i = 0; i < 300000; i++){
      		offset = (random() % filesize) & (~(LEN - 1));
      		pwrite(fd, buf, LEN, offset);
      	}
      	printf("start test\n");
      	time(&t1);
      	for (i = 0; i < 100000; i++){
      		offset = (random() % filesize) & (~(LEN - 1));
      		pread(fd, buf, LEN, offset);
      	}
      	time(&t2);
      	printf("%ld sec\n", t2-t1);
      	close(fd);
      	if (umount("/root/test1/") < 0) {
      		perror("cannot umount\n");
      		exit(1);
      	}
      }
      Signed-off-by: NHisashi Hifumi <hifumi.hisashi@oss.ntt.co.jp>
      Cc: Nick Piggin <nickpiggin@yahoo.com.au>
      Cc: Christoph Hellwig <hch@infradead.org>
      Cc: Jan Kara <jack@ucw.cz>
      Cc: <linux-ext4@vger.kernel.org>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      8ab22b9a
    • S
    • B
      spi_s3c24xx: really assign busnum · cb1d0a7a
      Ben Dooks 提交于
      The original "Pass the bus number we expect the S3C24XX SPI driver to
      attach to via the platform data." [1] patch was mis-sent, and missed two
      important parts of the diff, which was to actually set the bus_num field
      and add the relevant field to the platform data.
      
      The previous commit 50f426b5 promised to
      add a bus_num field, but failed to include the two hunks that added this
      field to include/asm-arm/arch-s3c2410/spi.h and then pass it to the spi
      core when creating the new master field in drivers/spi/spi_s3c24xx.c.
      
      [1] git commit 50f426b5Signed-off-by: NBen Dooks <ben-linux@fluff.org>
      Signed-off-by: NDavid Brownell <dbrownell@users.sourceforge.net>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      cb1d0a7a
    • L
      mpc52xx_psc_spi: fix block transfer · 9a7867e1
      Luotao Fu 提交于
      The block transfer routine in the mpc52xx psc spi driver misinterpret
      the datasheet.  According to the processor datasheet the chipselect is
      held as long as the EOF is not written.
      
      Theoretically blocks of any sizes can be transferred in this way.  The
      old routine however writes an EOF after every word, which has the size
      of size_of_word.  This makes the transfer slow.
      
      Also fixed some duplicate code.
      Signed-off-by: NLuotao Fu <l.fu@pengutronix.de>
      Signed-off-by: NDavid Brownell <dbrownell@users.sourceforge.net>
      Cc: <stable@kernel.org>		[2.6.25.x, 2.6.26.x]
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      9a7867e1
    • A
      mm/hugetlb.c must #include <asm/io.h> · 78a34ae2
      Adrian Bunk 提交于
      This patch fixes the following build error on sh caused by commit
      aa888a74 ("hugetlb: support larger than
      MAX_ORDER"):
      
        mm/hugetlb.c: In function 'alloc_bootmem_huge_page':
        mm/hugetlb.c:958: error: implicit declaration of function 'virt_to_phys'
      Signed-off-by: NAdrian Bunk <bunk@kernel.org>
      Cc: Hirokazu Takata <takata@linux-m32r.org>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      78a34ae2
    • A
      mmu-notifiers: core · cddb8a5c
      Andrea Arcangeli 提交于
      With KVM/GFP/XPMEM there isn't just the primary CPU MMU pointing to pages.
       There are secondary MMUs (with secondary sptes and secondary tlbs) too.
      sptes in the kvm case are shadow pagetables, but when I say spte in
      mmu-notifier context, I mean "secondary pte".  In GRU case there's no
      actual secondary pte and there's only a secondary tlb because the GRU
      secondary MMU has no knowledge about sptes and every secondary tlb miss
      event in the MMU always generates a page fault that has to be resolved by
      the CPU (this is not the case of KVM where the a secondary tlb miss will
      walk sptes in hardware and it will refill the secondary tlb transparently
      to software if the corresponding spte is present).  The same way
      zap_page_range has to invalidate the pte before freeing the page, the spte
      (and secondary tlb) must also be invalidated before any page is freed and
      reused.
      
      Currently we take a page_count pin on every page mapped by sptes, but that
      means the pages can't be swapped whenever they're mapped by any spte
      because they're part of the guest working set.  Furthermore a spte unmap
      event can immediately lead to a page to be freed when the pin is released
      (so requiring the same complex and relatively slow tlb_gather smp safe
      logic we have in zap_page_range and that can be avoided completely if the
      spte unmap event doesn't require an unpin of the page previously mapped in
      the secondary MMU).
      
      The mmu notifiers allow kvm/GRU/XPMEM to attach to the tsk->mm and know
      when the VM is swapping or freeing or doing anything on the primary MMU so
      that the secondary MMU code can drop sptes before the pages are freed,
      avoiding all page pinning and allowing 100% reliable swapping of guest
      physical address space.  Furthermore it avoids the code that teardown the
      mappings of the secondary MMU, to implement a logic like tlb_gather in
      zap_page_range that would require many IPI to flush other cpu tlbs, for
      each fixed number of spte unmapped.
      
      To make an example: if what happens on the primary MMU is a protection
      downgrade (from writeable to wrprotect) the secondary MMU mappings will be
      invalidated, and the next secondary-mmu-page-fault will call
      get_user_pages and trigger a do_wp_page through get_user_pages if it
      called get_user_pages with write=1, and it'll re-establishing an updated
      spte or secondary-tlb-mapping on the copied page.  Or it will setup a
      readonly spte or readonly tlb mapping if it's a guest-read, if it calls
      get_user_pages with write=0.  This is just an example.
      
      This allows to map any page pointed by any pte (and in turn visible in the
      primary CPU MMU), into a secondary MMU (be it a pure tlb like GRU, or an
      full MMU with both sptes and secondary-tlb like the shadow-pagetable layer
      with kvm), or a remote DMA in software like XPMEM (hence needing of
      schedule in XPMEM code to send the invalidate to the remote node, while no
      need to schedule in kvm/gru as it's an immediate event like invalidating
      primary-mmu pte).
      
      At least for KVM without this patch it's impossible to swap guests
      reliably.  And having this feature and removing the page pin allows
      several other optimizations that simplify life considerably.
      
      Dependencies:
      
      1) mm_take_all_locks() to register the mmu notifier when the whole VM
         isn't doing anything with "mm".  This allows mmu notifier users to keep
         track if the VM is in the middle of the invalidate_range_begin/end
         critical section with an atomic counter incraese in range_begin and
         decreased in range_end.  No secondary MMU page fault is allowed to map
         any spte or secondary tlb reference, while the VM is in the middle of
         range_begin/end as any page returned by get_user_pages in that critical
         section could later immediately be freed without any further
         ->invalidate_page notification (invalidate_range_begin/end works on
         ranges and ->invalidate_page isn't called immediately before freeing
         the page).  To stop all page freeing and pagetable overwrites the
         mmap_sem must be taken in write mode and all other anon_vma/i_mmap
         locks must be taken too.
      
      2) It'd be a waste to add branches in the VM if nobody could possibly
         run KVM/GRU/XPMEM on the kernel, so mmu notifiers will only enabled if
         CONFIG_KVM=m/y.  In the current kernel kvm won't yet take advantage of
         mmu notifiers, but this already allows to compile a KVM external module
         against a kernel with mmu notifiers enabled and from the next pull from
         kvm.git we'll start using them.  And GRU/XPMEM will also be able to
         continue the development by enabling KVM=m in their config, until they
         submit all GRU/XPMEM GPLv2 code to the mainline kernel.  Then they can
         also enable MMU_NOTIFIERS in the same way KVM does it (even if KVM=n).
         This guarantees nobody selects MMU_NOTIFIER=y if KVM and GRU and XPMEM
         are all =n.
      
      The mmu_notifier_register call can fail because mm_take_all_locks may be
      interrupted by a signal and return -EINTR.  Because mmu_notifier_reigster
      is used when a driver startup, a failure can be gracefully handled.  Here
      an example of the change applied to kvm to register the mmu notifiers.
      Usually when a driver startups other allocations are required anyway and
      -ENOMEM failure paths exists already.
      
       struct  kvm *kvm_arch_create_vm(void)
       {
              struct kvm *kvm = kzalloc(sizeof(struct kvm), GFP_KERNEL);
      +       int err;
      
              if (!kvm)
                      return ERR_PTR(-ENOMEM);
      
              INIT_LIST_HEAD(&kvm->arch.active_mmu_pages);
      
      +       kvm->arch.mmu_notifier.ops = &kvm_mmu_notifier_ops;
      +       err = mmu_notifier_register(&kvm->arch.mmu_notifier, current->mm);
      +       if (err) {
      +               kfree(kvm);
      +               return ERR_PTR(err);
      +       }
      +
              return kvm;
       }
      
      mmu_notifier_unregister returns void and it's reliable.
      
      The patch also adds a few needed but missing includes that would prevent
      kernel to compile after these changes on non-x86 archs (x86 didn't need
      them by luck).
      
      [akpm@linux-foundation.org: coding-style fixes]
      [akpm@linux-foundation.org: fix mm/filemap_xip.c build]
      [akpm@linux-foundation.org: fix mm/mmu_notifier.c build]
      Signed-off-by: NAndrea Arcangeli <andrea@qumranet.com>
      Signed-off-by: NNick Piggin <npiggin@suse.de>
      Signed-off-by: NChristoph Lameter <cl@linux-foundation.org>
      Cc: Jack Steiner <steiner@sgi.com>
      Cc: Robin Holt <holt@sgi.com>
      Cc: Nick Piggin <npiggin@suse.de>
      Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
      Cc: Kanoj Sarcar <kanojsarcar@yahoo.com>
      Cc: Roland Dreier <rdreier@cisco.com>
      Cc: Steve Wise <swise@opengridcomputing.com>
      Cc: Avi Kivity <avi@qumranet.com>
      Cc: Hugh Dickins <hugh@veritas.com>
      Cc: Rusty Russell <rusty@rustcorp.com.au>
      Cc: Anthony Liguori <aliguori@us.ibm.com>
      Cc: Chris Wright <chrisw@redhat.com>
      Cc: Marcelo Tosatti <marcelo@kvack.org>
      Cc: Eric Dumazet <dada1@cosmosbay.com>
      Cc: "Paul E. McKenney" <paulmck@us.ibm.com>
      Cc: Izik Eidus <izike@qumranet.com>
      Cc: Anthony Liguori <aliguori@us.ibm.com>
      Cc: Rik van Riel <riel@redhat.com>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      cddb8a5c
    • A
      mmu-notifiers: add mm_take_all_locks() operation · 7906d00c
      Andrea Arcangeli 提交于
      mm_take_all_locks holds off reclaim from an entire mm_struct.  This allows
      mmu notifiers to register into the mm at any time with the guarantee that
      no mmu operation is in progress on the mm.
      
      This operation locks against the VM for all pte/vma/mm related operations
      that could ever happen on a certain mm.  This includes vmtruncate,
      try_to_unmap, and all page faults.
      
      The caller must take the mmap_sem in write mode before calling
      mm_take_all_locks().  The caller isn't allowed to release the mmap_sem
      until mm_drop_all_locks() returns.
      
      mmap_sem in write mode is required in order to block all operations that
      could modify pagetables and free pages without need of altering the vma
      layout (for example populate_range() with nonlinear vmas).  It's also
      needed in write mode to avoid new anon_vmas to be associated with existing
      vmas.
      
      A single task can't take more than one mm_take_all_locks() in a row or it
      would deadlock.
      
      mm_take_all_locks() and mm_drop_all_locks are expensive operations that
      may have to take thousand of locks.
      
      mm_take_all_locks() can fail if it's interrupted by signals.
      
      When mmu_notifier_register returns, we must be sure that the driver is
      notified if some task is in the middle of a vmtruncate for the 'mm' where
      the mmu notifier was registered (mmu_notifier_invalidate_range_start/end
      is run around the vmtruncation but mmu_notifier_register can run after
      mmu_notifier_invalidate_range_start and before
      mmu_notifier_invalidate_range_end).  Same problem for rmap paths.  And
      we've to remove page pinning to avoid replicating the tlb_gather logic
      inside KVM (and GRU doesn't work well with page pinning regardless of
      needing tlb_gather), so without mm_take_all_locks when vmtruncate frees
      the page, kvm would have no way to notice that it mapped into sptes a page
      that is going into the freelist without a chance of any further
      mmu_notifier notification.
      
      [akpm@linux-foundation.org: coding-style fixes]
      Signed-off-by: NAndrea Arcangeli <andrea@qumranet.com>
      Acked-by: NLinus Torvalds <torvalds@linux-foundation.org>
      Cc: Christoph Lameter <cl@linux-foundation.org>
      Cc: Jack Steiner <steiner@sgi.com>
      Cc: Robin Holt <holt@sgi.com>
      Cc: Nick Piggin <npiggin@suse.de>
      Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
      Cc: Kanoj Sarcar <kanojsarcar@yahoo.com>
      Cc: Roland Dreier <rdreier@cisco.com>
      Cc: Steve Wise <swise@opengridcomputing.com>
      Cc: Avi Kivity <avi@qumranet.com>
      Cc: Hugh Dickins <hugh@veritas.com>
      Cc: Rusty Russell <rusty@rustcorp.com.au>
      Cc: Anthony Liguori <aliguori@us.ibm.com>
      Cc: Chris Wright <chrisw@redhat.com>
      Cc: Marcelo Tosatti <marcelo@kvack.org>
      Cc: Eric Dumazet <dada1@cosmosbay.com>
      Cc: "Paul E. McKenney" <paulmck@us.ibm.com>
      Cc: Izik Eidus <izike@qumranet.com>
      Cc: Anthony Liguori <aliguori@us.ibm.com>
      Cc: Rik van Riel <riel@redhat.com>
      Signed-off-by: NAndrew Morton <akpm@linux-foundation.org>
      Signed-off-by: NLinus Torvalds <torvalds@linux-foundation.org>
      7906d00c