Skip to content

Commit

Permalink
Merge branch 'akpm' (patches from Andrew)
Browse files Browse the repository at this point in the history
Merge misc fixes from Andrew Morton:
 "15 fixes"

* emailed patches from Andrew Morton <akpm@linux-foundation.org>:
  mm: numa: mark huge PTEs young when clearing NUMA hinting faults
  mm: numa: slow PTE scan rate if migration failures occur
  mm: numa: preserve PTE write permissions across a NUMA hinting fault
  mm: numa: group related processes based on VMA flags instead of page table flags
  hfsplus: fix B-tree corruption after insertion at position 0
  MAINTAINERS: add Jan as DMI/SMBIOS support maintainer
  fs/affs/file.c: unlock/release page on error
  mm/page_alloc.c: call kernel_map_pages in unset_migrateype_isolate
  mm/slub: fix lockups on PREEMPT && !SMP kernels
  mm/memory hotplug: postpone the reset of obsolete pgdat
  MAINTAINERS: correct rtc armada38x pattern entry
  mm/pagewalk.c: prevent positive return value of walk_page_test() from being passed to callers
  mm: fix anon_vma->degree underflow in anon_vma endless growing prevention
  drivers/rtc/rtc-mrst: fix suspend/resume
  aoe: update aoe maintainer information
  • Loading branch information
Linus Torvalds committed Mar 25, 2015
2 parents b8517e9 + b7b0400 commit 9c8e30d
Show file tree
Hide file tree
Showing 15 changed files with 106 additions and 71 deletions.
13 changes: 10 additions & 3 deletions MAINTAINERS
Original file line number Diff line number Diff line change
Expand Up @@ -1186,7 +1186,7 @@ M: Sebastian Hesselbarth <sebastian.hesselbarth@gmail.com>
L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
S: Maintained
F: arch/arm/mach-mvebu/
F: drivers/rtc/armada38x-rtc
F: drivers/rtc/rtc-armada38x.c

ARM/Marvell Berlin SoC support
M: Sebastian Hesselbarth <sebastian.hesselbarth@gmail.com>
Expand Down Expand Up @@ -1675,8 +1675,8 @@ F: drivers/misc/eeprom/at24.c
F: include/linux/platform_data/at24.h

ATA OVER ETHERNET (AOE) DRIVER
M: "Ed L. Cashin" <ecashin@coraid.com>
W: http://support.coraid.com/support/linux
M: "Ed L. Cashin" <ed.cashin@acm.org>
W: http://www.openaoe.org/
S: Supported
F: Documentation/aoe/
F: drivers/block/aoe/
Expand Down Expand Up @@ -3252,6 +3252,13 @@ S: Maintained
F: Documentation/hwmon/dme1737
F: drivers/hwmon/dme1737.c

DMI/SMBIOS SUPPORT
M: Jean Delvare <jdelvare@suse.de>
S: Maintained
F: drivers/firmware/dmi-id.c
F: drivers/firmware/dmi_scan.c
F: include/linux/dmi.h

DOCKING STATION DRIVER
M: Shaohua Li <shaohua.li@intel.com>
L: linux-acpi@vger.kernel.org
Expand Down
17 changes: 9 additions & 8 deletions drivers/rtc/rtc-mrst.c
Original file line number Diff line number Diff line change
Expand Up @@ -413,8 +413,8 @@ static void rtc_mrst_do_remove(struct device *dev)
mrst->dev = NULL;
}

#ifdef CONFIG_PM
static int mrst_suspend(struct device *dev, pm_message_t mesg)
#ifdef CONFIG_PM_SLEEP
static int mrst_suspend(struct device *dev)
{
struct mrst_rtc *mrst = dev_get_drvdata(dev);
unsigned char tmp;
Expand Down Expand Up @@ -453,7 +453,7 @@ static int mrst_suspend(struct device *dev, pm_message_t mesg)
*/
static inline int mrst_poweroff(struct device *dev)
{
return mrst_suspend(dev, PMSG_HIBERNATE);
return mrst_suspend(dev);
}

static int mrst_resume(struct device *dev)
Expand Down Expand Up @@ -490,9 +490,11 @@ static int mrst_resume(struct device *dev)
return 0;
}

static SIMPLE_DEV_PM_OPS(mrst_pm_ops, mrst_suspend, mrst_resume);
#define MRST_PM_OPS (&mrst_pm_ops)

#else
#define mrst_suspend NULL
#define mrst_resume NULL
#define MRST_PM_OPS NULL

static inline int mrst_poweroff(struct device *dev)
{
Expand Down Expand Up @@ -529,9 +531,8 @@ static struct platform_driver vrtc_mrst_platform_driver = {
.remove = vrtc_mrst_platform_remove,
.shutdown = vrtc_mrst_platform_shutdown,
.driver = {
.name = (char *) driver_name,
.suspend = mrst_suspend,
.resume = mrst_resume,
.name = driver_name,
.pm = MRST_PM_OPS,
}
};

Expand Down
19 changes: 12 additions & 7 deletions fs/affs/file.c
Original file line number Diff line number Diff line change
Expand Up @@ -699,8 +699,10 @@ static int affs_write_end_ofs(struct file *file, struct address_space *mapping,
boff = tmp % bsize;
if (boff) {
bh = affs_bread_ino(inode, bidx, 0);
if (IS_ERR(bh))
return PTR_ERR(bh);
if (IS_ERR(bh)) {
written = PTR_ERR(bh);
goto err_first_bh;
}
tmp = min(bsize - boff, to - from);
BUG_ON(boff + tmp > bsize || tmp > bsize);
memcpy(AFFS_DATA(bh) + boff, data + from, tmp);
Expand All @@ -712,14 +714,16 @@ static int affs_write_end_ofs(struct file *file, struct address_space *mapping,
bidx++;
} else if (bidx) {
bh = affs_bread_ino(inode, bidx - 1, 0);
if (IS_ERR(bh))
return PTR_ERR(bh);
if (IS_ERR(bh)) {
written = PTR_ERR(bh);
goto err_first_bh;
}
}
while (from + bsize <= to) {
prev_bh = bh;
bh = affs_getemptyblk_ino(inode, bidx);
if (IS_ERR(bh))
goto out;
goto err_bh;
memcpy(AFFS_DATA(bh), data + from, bsize);
if (buffer_new(bh)) {
AFFS_DATA_HEAD(bh)->ptype = cpu_to_be32(T_DATA);
Expand Down Expand Up @@ -751,7 +755,7 @@ static int affs_write_end_ofs(struct file *file, struct address_space *mapping,
prev_bh = bh;
bh = affs_bread_ino(inode, bidx, 1);
if (IS_ERR(bh))
goto out;
goto err_bh;
tmp = min(bsize, to - from);
BUG_ON(tmp > bsize);
memcpy(AFFS_DATA(bh), data + from, tmp);
Expand Down Expand Up @@ -790,12 +794,13 @@ static int affs_write_end_ofs(struct file *file, struct address_space *mapping,
if (tmp > inode->i_size)
inode->i_size = AFFS_I(inode)->mmu_private = tmp;

err_first_bh:
unlock_page(page);
page_cache_release(page);

return written;

out:
err_bh:
bh = prev_bh;
if (!written)
written = PTR_ERR(bh);
Expand Down
20 changes: 11 additions & 9 deletions fs/hfsplus/brec.c
Original file line number Diff line number Diff line change
Expand Up @@ -131,13 +131,16 @@ int hfs_brec_insert(struct hfs_find_data *fd, void *entry, int entry_len)
hfs_bnode_write(node, entry, data_off + key_len, entry_len);
hfs_bnode_dump(node);

if (new_node) {
/* update parent key if we inserted a key
* at the start of the first node
*/
if (!rec && new_node != node)
hfs_brec_update_parent(fd);
/*
* update parent key if we inserted a key
* at the start of the node and it is not the new node
*/
if (!rec && new_node != node) {
hfs_bnode_read_key(node, fd->search_key, data_off + size);
hfs_brec_update_parent(fd);
}

if (new_node) {
hfs_bnode_put(fd->bnode);
if (!new_node->parent) {
hfs_btree_inc_height(tree);
Expand Down Expand Up @@ -168,9 +171,6 @@ int hfs_brec_insert(struct hfs_find_data *fd, void *entry, int entry_len)
goto again;
}

if (!rec)
hfs_brec_update_parent(fd);

return 0;
}

Expand Down Expand Up @@ -370,6 +370,8 @@ static int hfs_brec_update_parent(struct hfs_find_data *fd)
if (IS_ERR(parent))
return PTR_ERR(parent);
__hfs_brec_find(parent, fd, hfs_find_rec_by_key);
if (fd->record < 0)
return -ENOENT;
hfs_bnode_dump(parent);
rec = fd->record;

Expand Down
9 changes: 5 additions & 4 deletions include/linux/sched.h
Original file line number Diff line number Diff line change
Expand Up @@ -1625,11 +1625,11 @@ struct task_struct {

/*
* numa_faults_locality tracks if faults recorded during the last
* scan window were remote/local. The task scan period is adapted
* based on the locality of the faults with different weights
* depending on whether they were shared or private faults
* scan window were remote/local or failed to migrate. The task scan
* period is adapted based on the locality of the faults with different
* weights depending on whether they were shared or private faults
*/
unsigned long numa_faults_locality[2];
unsigned long numa_faults_locality[3];

unsigned long numa_pages_migrated;
#endif /* CONFIG_NUMA_BALANCING */
Expand Down Expand Up @@ -1719,6 +1719,7 @@ struct task_struct {
#define TNF_NO_GROUP 0x02
#define TNF_SHARED 0x04
#define TNF_FAULT_LOCAL 0x08
#define TNF_MIGRATE_FAIL 0x10

#ifdef CONFIG_NUMA_BALANCING
extern void task_numa_fault(int last_node, int node, int pages, int flags);
Expand Down
8 changes: 6 additions & 2 deletions kernel/sched/fair.c
Original file line number Diff line number Diff line change
Expand Up @@ -1609,9 +1609,11 @@ static void update_task_scan_period(struct task_struct *p,
/*
* If there were no record hinting faults then either the task is
* completely idle or all activity is areas that are not of interest
* to automatic numa balancing. Scan slower
* to automatic numa balancing. Related to that, if there were failed
* migration then it implies we are migrating too quickly or the local
* node is overloaded. In either case, scan slower
*/
if (local + shared == 0) {
if (local + shared == 0 || p->numa_faults_locality[2]) {
p->numa_scan_period = min(p->numa_scan_period_max,
p->numa_scan_period << 1);

Expand Down Expand Up @@ -2080,6 +2082,8 @@ void task_numa_fault(int last_cpupid, int mem_node, int pages, int flags)

if (migrated)
p->numa_pages_migrated += pages;
if (flags & TNF_MIGRATE_FAIL)
p->numa_faults_locality[2] += pages;

p->numa_faults[task_faults_idx(NUMA_MEMBUF, mem_node, priv)] += pages;
p->numa_faults[task_faults_idx(NUMA_CPUBUF, cpu_node, priv)] += pages;
Expand Down
26 changes: 13 additions & 13 deletions mm/huge_memory.c
Original file line number Diff line number Diff line change
Expand Up @@ -1260,6 +1260,7 @@ int do_huge_pmd_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
int target_nid, last_cpupid = -1;
bool page_locked;
bool migrated = false;
bool was_writable;
int flags = 0;

/* A PROT_NONE fault should not end up here */
Expand Down Expand Up @@ -1291,17 +1292,8 @@ int do_huge_pmd_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
flags |= TNF_FAULT_LOCAL;
}

/*
* Avoid grouping on DSO/COW pages in specific and RO pages
* in general, RO pages shouldn't hurt as much anyway since
* they can be in shared cache state.
*
* FIXME! This checks "pmd_dirty()" as an approximation of
* "is this a read-only page", since checking "pmd_write()"
* is even more broken. We haven't actually turned this into
* a writable page, so pmd_write() will always be false.
*/
if (!pmd_dirty(pmd))
/* See similar comment in do_numa_page for explanation */
if (!(vma->vm_flags & VM_WRITE))
flags |= TNF_NO_GROUP;

/*
Expand Down Expand Up @@ -1358,12 +1350,17 @@ int do_huge_pmd_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
if (migrated) {
flags |= TNF_MIGRATED;
page_nid = target_nid;
}
} else
flags |= TNF_MIGRATE_FAIL;

goto out;
clear_pmdnuma:
BUG_ON(!PageLocked(page));
was_writable = pmd_write(pmd);
pmd = pmd_modify(pmd, vma->vm_page_prot);
pmd = pmd_mkyoung(pmd);
if (was_writable)
pmd = pmd_mkwrite(pmd);
set_pmd_at(mm, haddr, pmdp, pmd);
update_mmu_cache_pmd(vma, addr, pmdp);
unlock_page(page);
Expand Down Expand Up @@ -1487,6 +1484,7 @@ int change_huge_pmd(struct vm_area_struct *vma, pmd_t *pmd,

if (__pmd_trans_huge_lock(pmd, vma, &ptl) == 1) {
pmd_t entry;
bool preserve_write = prot_numa && pmd_write(*pmd);
ret = 1;

/*
Expand All @@ -1502,9 +1500,11 @@ int change_huge_pmd(struct vm_area_struct *vma, pmd_t *pmd,
if (!prot_numa || !pmd_protnone(*pmd)) {
entry = pmdp_get_and_clear_notify(mm, addr, pmd);
entry = pmd_modify(entry, newprot);
if (preserve_write)
entry = pmd_mkwrite(entry);
ret = HPAGE_PMD_NR;
set_pmd_at(mm, addr, pmd, entry);
BUG_ON(pmd_write(entry));
BUG_ON(!preserve_write && pmd_write(entry));
}
spin_unlock(ptl);
}
Expand Down
22 changes: 12 additions & 10 deletions mm/memory.c
Original file line number Diff line number Diff line change
Expand Up @@ -3035,6 +3035,7 @@ static int do_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
int last_cpupid;
int target_nid;
bool migrated = false;
bool was_writable = pte_write(pte);
int flags = 0;

/* A PROT_NONE fault should not end up here */
Expand All @@ -3059,6 +3060,8 @@ static int do_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
/* Make it present again */
pte = pte_modify(pte, vma->vm_page_prot);
pte = pte_mkyoung(pte);
if (was_writable)
pte = pte_mkwrite(pte);
set_pte_at(mm, addr, ptep, pte);
update_mmu_cache(vma, addr, ptep);

Expand All @@ -3069,16 +3072,14 @@ static int do_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
}

/*
* Avoid grouping on DSO/COW pages in specific and RO pages
* in general, RO pages shouldn't hurt as much anyway since
* they can be in shared cache state.
*
* FIXME! This checks "pmd_dirty()" as an approximation of
* "is this a read-only page", since checking "pmd_write()"
* is even more broken. We haven't actually turned this into
* a writable page, so pmd_write() will always be false.
* Avoid grouping on RO pages in general. RO pages shouldn't hurt as
* much anyway since they can be in shared cache state. This misses
* the case where a mapping is writable but the process never writes
* to it but pte_write gets cleared during protection updates and
* pte_dirty has unpredictable behaviour between PTE scan updates,
* background writeback, dirty balancing and application behaviour.
*/
if (!pte_dirty(pte))
if (!(vma->vm_flags & VM_WRITE))
flags |= TNF_NO_GROUP;

/*
Expand All @@ -3102,7 +3103,8 @@ static int do_numa_page(struct mm_struct *mm, struct vm_area_struct *vma,
if (migrated) {
page_nid = target_nid;
flags |= TNF_MIGRATED;
}
} else
flags |= TNF_MIGRATE_FAIL;

out:
if (page_nid != -1)
Expand Down
13 changes: 4 additions & 9 deletions mm/memory_hotplug.c
Original file line number Diff line number Diff line change
Expand Up @@ -1092,6 +1092,10 @@ static pg_data_t __ref *hotadd_new_pgdat(int nid, u64 start)
return NULL;

arch_refresh_nodedata(nid, pgdat);
} else {
/* Reset the nr_zones and classzone_idx to 0 before reuse */
pgdat->nr_zones = 0;
pgdat->classzone_idx = 0;
}

/* we can use NODE_DATA(nid) from here */
Expand Down Expand Up @@ -1977,15 +1981,6 @@ void try_offline_node(int nid)
if (is_vmalloc_addr(zone->wait_table))
vfree(zone->wait_table);
}

/*
* Since there is no way to guarentee the address of pgdat/zone is not
* on stack of any kernel threads or used by other kernel objects
* without reference counting or other symchronizing method, do not
* reset node_data and free pgdat here. Just reset it to 0 and reuse
* the memory when the node is online again.
*/
memset(pgdat, 0, sizeof(*pgdat));
}
EXPORT_SYMBOL(try_offline_node);

Expand Down
4 changes: 1 addition & 3 deletions mm/mmap.c
Original file line number Diff line number Diff line change
Expand Up @@ -774,10 +774,8 @@ again: remove_next = 1 + (end > next->vm_end);

importer->anon_vma = exporter->anon_vma;
error = anon_vma_clone(importer, exporter);
if (error) {
importer->anon_vma = NULL;
if (error)
return error;
}
}
}

Expand Down
Loading

0 comments on commit 9c8e30d

Please sign in to comment.