From: Greg Kroah-Hartman Date: Sat, 22 Jul 2017 13:32:37 +0000 (+0200) Subject: 4.12-stable patches X-Git-Tag: v3.18.63~38 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=10ca23711ea2aa7d530ea05e5f7ec3c0fc84f25f;p=thirdparty%2Fkernel%2Fstable-queue.git 4.12-stable patches added patches: btrfs-don-t-clear-sgid-when-inheriting-acls.patch btrfs-fix-invalid-extent-maps-due-to-hole-punching.patch btrfs-incremental-send-fix-invalid-memory-access.patch igb-explicitly-select-page-0-at-initialization.patch mwifiex-fixup-error-cases-in-mwifiex_add_virtual_intf.patch pstore-don-t-warn-if-data-is-uncompressed-and-type-is-not-pstore_type_dmesg.patch spi-atmel-fix-corrupted-data-issue-on-sam9-family-socs.patch wlcore-fix-64k-page-support.patch --- diff --git a/queue-4.12/btrfs-don-t-clear-sgid-when-inheriting-acls.patch b/queue-4.12/btrfs-don-t-clear-sgid-when-inheriting-acls.patch new file mode 100644 index 00000000000..759da3bcc46 --- /dev/null +++ b/queue-4.12/btrfs-don-t-clear-sgid-when-inheriting-acls.patch @@ -0,0 +1,61 @@ +From b7f8a09f8097db776b8d160862540e4fc1f51296 Mon Sep 17 00:00:00 2001 +From: Jan Kara +Date: Thu, 22 Jun 2017 15:31:07 +0200 +Subject: btrfs: Don't clear SGID when inheriting ACLs + +From: Jan Kara + +commit b7f8a09f8097db776b8d160862540e4fc1f51296 upstream. + +When new directory 'DIR1' is created in a directory 'DIR0' with SGID bit +set, DIR1 is expected to have SGID bit set (and owning group equal to +the owning group of 'DIR0'). However when 'DIR0' also has some default +ACLs that 'DIR1' inherits, setting these ACLs will result in SGID bit on +'DIR1' to get cleared if user is not member of the owning group. + +Fix the problem by moving posix_acl_update_mode() out of +__btrfs_set_acl() into btrfs_set_acl(). That way the function will not be +called when inheriting ACLs which is what we want as it prevents SGID +bit clearing and the mode has been properly set by posix_acl_create() +anyway. + +Fixes: 073931017b49d9458aa351605b43a7e34598caef +CC: linux-btrfs@vger.kernel.org +CC: David Sterba +Signed-off-by: Jan Kara +Signed-off-by: David Sterba +Signed-off-by: Greg Kroah-Hartman + +--- + fs/btrfs/acl.c | 13 +++++++------ + 1 file changed, 7 insertions(+), 6 deletions(-) + +--- a/fs/btrfs/acl.c ++++ b/fs/btrfs/acl.c +@@ -78,12 +78,6 @@ static int __btrfs_set_acl(struct btrfs_ + switch (type) { + case ACL_TYPE_ACCESS: + name = XATTR_NAME_POSIX_ACL_ACCESS; +- if (acl) { +- ret = posix_acl_update_mode(inode, &inode->i_mode, &acl); +- if (ret) +- return ret; +- } +- ret = 0; + break; + case ACL_TYPE_DEFAULT: + if (!S_ISDIR(inode->i_mode)) +@@ -119,6 +113,13 @@ out: + + int btrfs_set_acl(struct inode *inode, struct posix_acl *acl, int type) + { ++ int ret; ++ ++ if (type == ACL_TYPE_ACCESS && acl) { ++ ret = posix_acl_update_mode(inode, &inode->i_mode, &acl); ++ if (ret) ++ return ret; ++ } + return __btrfs_set_acl(NULL, inode, acl, type); + } + diff --git a/queue-4.12/btrfs-fix-invalid-extent-maps-due-to-hole-punching.patch b/queue-4.12/btrfs-fix-invalid-extent-maps-due-to-hole-punching.patch new file mode 100644 index 00000000000..eeb87046024 --- /dev/null +++ b/queue-4.12/btrfs-fix-invalid-extent-maps-due-to-hole-punching.patch @@ -0,0 +1,247 @@ +From 609805d809733d0c669f21f710bdac308cc63cba Mon Sep 17 00:00:00 2001 +From: Filipe Manana +Date: Tue, 30 May 2017 05:29:09 +0100 +Subject: Btrfs: fix invalid extent maps due to hole punching + +From: Filipe Manana + +commit 609805d809733d0c669f21f710bdac308cc63cba upstream. + +While punching a hole in a range that is not aligned with the sector size +(currently the same as the page size) we can end up leaving an extent map +in memory with a length that is smaller then the sector size or with a +start offset that is not aligned to the sector size. Both cases are not +expected and can lead to problems. This issue is easily detected +after the patch from commit a7e3b975a0f9 ("Btrfs: fix reported number of +inode blocks"), introduced in kernel 4.12-rc1, in a scenario like the +following for example: + + $ mkfs.btrfs -f /dev/sdb + $ mount /dev/sdb /mnt + $ xfs_io -c "pwrite -S 0xaa -b 100K 0 100K" /mnt/foo + $ xfs_io -c "fpunch 60K 90K" /mnt/foo + $ xfs_io -c "pwrite -S 0xbb -b 100K 50K 100K" /mnt/foo + $ xfs_io -c "pwrite -S 0xcc -b 50K 100K 50K" /mnt/foo + $ umount /mnt + +After the unmount operation we can see several warnings emmitted due to +underflows related to space reservation counters: + +[ 2837.443299] ------------[ cut here ]------------ +[ 2837.447395] WARNING: CPU: 8 PID: 2474 at fs/btrfs/inode.c:9444 btrfs_destroy_inode+0xe8/0x27e [btrfs] +[ 2837.452108] Modules linked in: dm_flakey dm_mod ppdev parport_pc psmouse parport sg pcspkr acpi_cpufreq tpm_tis tpm_tis_core i2c_piix4 i2c_core evdev tpm button se +rio_raw sunrpc loop autofs4 ext4 crc16 jbd2 mbcache btrfs raid10 raid456 async_raid6_recov async_memcpy async_pq async_xor async_tx xor raid6_pq libcrc32c crc32c_gene +ric raid1 raid0 multipath linear md_mod sr_mod cdrom sd_mod ata_generic virtio_scsi ata_piix libata virtio_pci virtio_ring virtio e1000 scsi_mod floppy +[ 2837.458389] CPU: 8 PID: 2474 Comm: umount Tainted: G W 4.10.0-rc8-btrfs-next-43+ #1 +[ 2837.459754] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.9.1-0-gb3ef39f-prebuilt.qemu-project.org 04/01/2014 +[ 2837.462379] Call Trace: +[ 2837.462379] dump_stack+0x68/0x92 +[ 2837.462379] __warn+0xc2/0xdd +[ 2837.462379] warn_slowpath_null+0x1d/0x1f +[ 2837.462379] btrfs_destroy_inode+0xe8/0x27e [btrfs] +[ 2837.462379] destroy_inode+0x3d/0x55 +[ 2837.462379] evict+0x177/0x17e +[ 2837.462379] dispose_list+0x50/0x71 +[ 2837.462379] evict_inodes+0x132/0x141 +[ 2837.462379] generic_shutdown_super+0x3f/0xeb +[ 2837.462379] kill_anon_super+0x12/0x1c +[ 2837.462379] btrfs_kill_super+0x16/0x21 [btrfs] +[ 2837.462379] deactivate_locked_super+0x30/0x68 +[ 2837.462379] deactivate_super+0x36/0x39 +[ 2837.462379] cleanup_mnt+0x58/0x76 +[ 2837.462379] __cleanup_mnt+0x12/0x14 +[ 2837.462379] task_work_run+0x77/0x9b +[ 2837.462379] prepare_exit_to_usermode+0x9d/0xc5 +[ 2837.462379] syscall_return_slowpath+0x196/0x1b9 +[ 2837.462379] entry_SYSCALL_64_fastpath+0xab/0xad +[ 2837.462379] RIP: 0033:0x7f3ef3e6b9a7 +[ 2837.462379] RSP: 002b:00007ffdd0d8de58 EFLAGS: 00000246 ORIG_RAX: 00000000000000a6 +[ 2837.462379] RAX: 0000000000000000 RBX: 0000556f76a39060 RCX: 00007f3ef3e6b9a7 +[ 2837.462379] RDX: 0000000000000001 RSI: 0000000000000000 RDI: 0000556f76a3f910 +[ 2837.462379] RBP: 0000556f76a3f910 R08: 0000556f76a3e670 R09: 0000000000000015 +[ 2837.462379] R10: 00000000000006b4 R11: 0000000000000246 R12: 00007f3ef436ce64 +[ 2837.462379] R13: 0000000000000000 R14: 0000556f76a39240 R15: 00007ffdd0d8e0e0 +[ 2837.519355] ---[ end trace e79345fe24b30b8d ]--- +[ 2837.596256] ------------[ cut here ]------------ +[ 2837.597625] WARNING: CPU: 8 PID: 2474 at fs/btrfs/extent-tree.c:5699 btrfs_free_block_groups+0x246/0x3eb [btrfs] +[ 2837.603547] Modules linked in: dm_flakey dm_mod ppdev parport_pc psmouse parport sg pcspkr acpi_cpufreq tpm_tis tpm_tis_core i2c_piix4 i2c_core evdev tpm button serio_raw sunrpc loop autofs4 ext4 crc16 jbd2 mbcache btrfs raid10 raid456 async_raid6_recov async_memcpy async_pq async_xor async_tx xor raid6_pq libcrc32c crc32c_generic raid1 raid0 multipath linear md_mod sr_mod cdrom sd_mod ata_generic virtio_scsi ata_piix libata virtio_pci virtio_ring virtio e1000 scsi_mod floppy +[ 2837.659372] CPU: 8 PID: 2474 Comm: umount Tainted: G W 4.10.0-rc8-btrfs-next-43+ #1 +[ 2837.663359] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.9.1-0-gb3ef39f-prebuilt.qemu-project.org 04/01/2014 +[ 2837.663359] Call Trace: +[ 2837.663359] dump_stack+0x68/0x92 +[ 2837.663359] __warn+0xc2/0xdd +[ 2837.663359] warn_slowpath_null+0x1d/0x1f +[ 2837.663359] btrfs_free_block_groups+0x246/0x3eb [btrfs] +[ 2837.663359] close_ctree+0x1dd/0x2e1 [btrfs] +[ 2837.663359] ? evict_inodes+0x132/0x141 +[ 2837.663359] btrfs_put_super+0x15/0x17 [btrfs] +[ 2837.663359] generic_shutdown_super+0x6a/0xeb +[ 2837.663359] kill_anon_super+0x12/0x1c +[ 2837.663359] btrfs_kill_super+0x16/0x21 [btrfs] +[ 2837.663359] deactivate_locked_super+0x30/0x68 +[ 2837.663359] deactivate_super+0x36/0x39 +[ 2837.663359] cleanup_mnt+0x58/0x76 +[ 2837.663359] __cleanup_mnt+0x12/0x14 +[ 2837.663359] task_work_run+0x77/0x9b +[ 2837.663359] prepare_exit_to_usermode+0x9d/0xc5 +[ 2837.663359] syscall_return_slowpath+0x196/0x1b9 +[ 2837.663359] entry_SYSCALL_64_fastpath+0xab/0xad +[ 2837.663359] RIP: 0033:0x7f3ef3e6b9a7 +[ 2837.663359] RSP: 002b:00007ffdd0d8de58 EFLAGS: 00000246 ORIG_RAX: 00000000000000a6 +[ 2837.663359] RAX: 0000000000000000 RBX: 0000556f76a39060 RCX: 00007f3ef3e6b9a7 +[ 2837.663359] RDX: 0000000000000001 RSI: 0000000000000000 RDI: 0000556f76a3f910 +[ 2837.663359] RBP: 0000556f76a3f910 R08: 0000556f76a3e670 R09: 0000000000000015 +[ 2837.663359] R10: 00000000000006b4 R11: 0000000000000246 R12: 00007f3ef436ce64 +[ 2837.663359] R13: 0000000000000000 R14: 0000556f76a39240 R15: 00007ffdd0d8e0e0 +[ 2837.739445] ---[ end trace e79345fe24b30b8e ]--- +[ 2837.745595] ------------[ cut here ]------------ +[ 2837.746412] WARNING: CPU: 8 PID: 2474 at fs/btrfs/extent-tree.c:5700 btrfs_free_block_groups+0x261/0x3eb [btrfs] +[ 2837.747955] Modules linked in: dm_flakey dm_mod ppdev parport_pc psmouse parport sg pcspkr acpi_cpufreq tpm_tis tpm_tis_core i2c_piix4 i2c_core evdev tpm button serio_raw sunrpc loop autofs4 ext4 crc16 jbd2 mbcache btrfs raid10 raid456 async_raid6_recov async_memcpy async_pq async_xor async_tx xor raid6_pq libcrc32c crc32c_generic raid1 raid0 multipath linear md_mod sr_mod cdrom sd_mod ata_generic virtio_scsi ata_piix libata virtio_pci virtio_ring virtio e1000 scsi_mod floppy +[ 2837.755395] CPU: 8 PID: 2474 Comm: umount Tainted: G W 4.10.0-rc8-btrfs-next-43+ #1 +[ 2837.756769] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.9.1-0-gb3ef39f-prebuilt.qemu-project.org 04/01/2014 +[ 2837.758526] Call Trace: +[ 2837.758925] dump_stack+0x68/0x92 +[ 2837.759383] __warn+0xc2/0xdd +[ 2837.759383] warn_slowpath_null+0x1d/0x1f +[ 2837.759383] btrfs_free_block_groups+0x261/0x3eb [btrfs] +[ 2837.759383] close_ctree+0x1dd/0x2e1 [btrfs] +[ 2837.759383] ? evict_inodes+0x132/0x141 +[ 2837.759383] btrfs_put_super+0x15/0x17 [btrfs] +[ 2837.759383] generic_shutdown_super+0x6a/0xeb +[ 2837.759383] kill_anon_super+0x12/0x1c +[ 2837.759383] btrfs_kill_super+0x16/0x21 [btrfs] +[ 2837.759383] deactivate_locked_super+0x30/0x68 +[ 2837.759383] deactivate_super+0x36/0x39 +[ 2837.759383] cleanup_mnt+0x58/0x76 +[ 2837.759383] __cleanup_mnt+0x12/0x14 +[ 2837.759383] task_work_run+0x77/0x9b +[ 2837.759383] prepare_exit_to_usermode+0x9d/0xc5 +[ 2837.759383] syscall_return_slowpath+0x196/0x1b9 +[ 2837.759383] entry_SYSCALL_64_fastpath+0xab/0xad +[ 2837.759383] RIP: 0033:0x7f3ef3e6b9a7 +[ 2837.759383] RSP: 002b:00007ffdd0d8de58 EFLAGS: 00000246 ORIG_RAX: 00000000000000a6 +[ 2837.759383] RAX: 0000000000000000 RBX: 0000556f76a39060 RCX: 00007f3ef3e6b9a7 +[ 2837.759383] RDX: 0000000000000001 RSI: 0000000000000000 RDI: 0000556f76a3f910 +[ 2837.759383] RBP: 0000556f76a3f910 R08: 0000556f76a3e670 R09: 0000000000000015 +[ 2837.759383] R10: 00000000000006b4 R11: 0000000000000246 R12: 00007f3ef436ce64 +[ 2837.759383] R13: 0000000000000000 R14: 0000556f76a39240 R15: 00007ffdd0d8e0e0 +[ 2837.777063] ---[ end trace e79345fe24b30b8f ]--- +[ 2837.778235] ------------[ cut here ]------------ +[ 2837.778856] WARNING: CPU: 8 PID: 2474 at fs/btrfs/extent-tree.c:9825 btrfs_free_block_groups+0x348/0x3eb [btrfs] +[ 2837.791385] Modules linked in: dm_flakey dm_mod ppdev parport_pc psmouse parport sg pcspkr acpi_cpufreq tpm_tis tpm_tis_core i2c_piix4 i2c_core evdev tpm button serio_raw sunrpc loop autofs4 ext4 crc16 jbd2 mbcache btrfs raid10 raid456 async_raid6_recov async_memcpy async_pq async_xor async_tx xor raid6_pq libcrc32c crc32c_generic raid1 raid0 multipath linear md_mod sr_mod cdrom sd_mod ata_generic virtio_scsi ata_piix libata virtio_pci virtio_ring virtio e1000 scsi_mod floppy +[ 2837.797711] CPU: 8 PID: 2474 Comm: umount Tainted: G W 4.10.0-rc8-btrfs-next-43+ #1 +[ 2837.798594] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.9.1-0-gb3ef39f-prebuilt.qemu-project.org 04/01/2014 +[ 2837.800118] Call Trace: +[ 2837.800515] dump_stack+0x68/0x92 +[ 2837.801015] __warn+0xc2/0xdd +[ 2837.801471] warn_slowpath_null+0x1d/0x1f +[ 2837.801698] btrfs_free_block_groups+0x348/0x3eb [btrfs] +[ 2837.801698] close_ctree+0x1dd/0x2e1 [btrfs] +[ 2837.801698] ? evict_inodes+0x132/0x141 +[ 2837.801698] btrfs_put_super+0x15/0x17 [btrfs] +[ 2837.801698] generic_shutdown_super+0x6a/0xeb +[ 2837.801698] kill_anon_super+0x12/0x1c +[ 2837.801698] btrfs_kill_super+0x16/0x21 [btrfs] +[ 2837.801698] deactivate_locked_super+0x30/0x68 +[ 2837.801698] deactivate_super+0x36/0x39 +[ 2837.801698] cleanup_mnt+0x58/0x76 +[ 2837.801698] __cleanup_mnt+0x12/0x14 +[ 2837.801698] task_work_run+0x77/0x9b +[ 2837.801698] prepare_exit_to_usermode+0x9d/0xc5 +[ 2837.801698] syscall_return_slowpath+0x196/0x1b9 +[ 2837.801698] entry_SYSCALL_64_fastpath+0xab/0xad +[ 2837.801698] RIP: 0033:0x7f3ef3e6b9a7 +[ 2837.801698] RSP: 002b:00007ffdd0d8de58 EFLAGS: 00000246 ORIG_RAX: 00000000000000a6 +[ 2837.801698] RAX: 0000000000000000 RBX: 0000556f76a39060 RCX: 00007f3ef3e6b9a7 +[ 2837.801698] RDX: 0000000000000001 RSI: 0000000000000000 RDI: 0000556f76a3f910 +[ 2837.801698] RBP: 0000556f76a3f910 R08: 0000556f76a3e670 R09: 0000000000000015 +[ 2837.801698] R10: 00000000000006b4 R11: 0000000000000246 R12: 00007f3ef436ce64 +[ 2837.801698] R13: 0000000000000000 R14: 0000556f76a39240 R15: 00007ffdd0d8e0e0 +[ 2837.818441] ---[ end trace e79345fe24b30b90 ]--- +[ 2837.818991] BTRFS info (device sdc): space_info 1 has 7974912 free, is not full +[ 2837.819830] BTRFS info (device sdc): space_info total=8388608, used=417792, pinned=0, reserved=0, may_use=18446744073709547520, readonly=0 + +What happens in the above example is the following: + +1) When punching the hole, at btrfs_punch_hole(), the variable tail_len + is set to 2048 (as tail_start is 148Kb + 1 and offset + len is 150Kb). + This results in the creation of an extent map with a length of 2Kb + starting at file offset 148Kb, through find_first_non_hole() -> + btrfs_get_extent(). + +2) The second write (first write after the hole punch operation), sets + the range [50Kb, 152Kb[ to delalloc. + +3) The third write, at btrfs_find_new_delalloc_bytes(), sees the extent + map covering the range [148Kb, 150Kb[ and ends up calling + set_extent_bit() for the same range, which results in splitting an + existing extent state record, covering the range [148Kb, 152Kb[ into + two 2Kb extent state records, covering the ranges [148Kb, 150Kb[ and + [150Kb, 152Kb[. + +4) Finally at lock_and_cleanup_extent_if_need(), immediately after calling + btrfs_find_new_delalloc_bytes() we clear the delalloc bit from the + range [100Kb, 152Kb[ which results in the btrfs_clear_bit_hook() + callback being invoked against the two 2Kb extent state records that + cover the ranges [148Kb, 150Kb[ and [150Kb, 152Kb[. When called against + the first 2Kb extent state, it calls btrfs_delalloc_release_metadata() + with a length argument of 2048 bytes. That function rounds up the length + to a sector size aligned length, so it ends up considering a length of + 4096 bytes, and then calls calc_csum_metadata_size() which results in + decrementing the inode's csum_bytes counter by 4096 bytes, so after + it stays a value of 0 bytes. Then the same happens when + btrfs_clear_bit_hook() is called against the second extent state that + has a length of 2Kb, covering the range [150Kb, 152Kb[, the length is + rounded up to 4096 and calc_csum_metadata_size() ends up being called + to decrement 4096 bytes from the inode's csum_bytes counter, which + at that time has a value of 0, leading to an underflow, which is + exactly what triggers the first warning, at btrfs_destroy_inode(). + All the other warnings relate to several space accounting counters + that underflow as well due to similar reasons. + +A similar case but where the hole punching operation creates an extent map +with a start offset not aligned to the sector size is the following: + + $ mkfs.btrfs -f /dev/sdb + $ mount /dev/sdb /mnt + $ xfs_io -f -c "fpunch 695K 820K" $SCRATCH_MNT/bar + $ xfs_io -c "pwrite -S 0xaa 1008K 307K" $SCRATCH_MNT/bar + $ xfs_io -c "pwrite -S 0xbb -b 630K 1073K 630K" $SCRATCH_MNT/bar + $ xfs_io -c "pwrite -S 0xcc -b 459K 1068K 459K" $SCRATCH_MNT/bar + $ umount /mnt + +During the unmount operation we get similar traces for the same reasons as +in the first example. + +So fix the hole punching operation to make sure it never creates extent +maps with a length that is not aligned to the sector size nor with a start +offset that is not aligned to the sector size, as this breaks all +assumptions and it's a land mine. + +Fixes: d77815461f04 ("btrfs: Avoid trucating page or punching hole in a already existed hole.") +Signed-off-by: Filipe Manana +Reviewed-by: Liu Bo +Signed-off-by: David Sterba +Signed-off-by: Greg Kroah-Hartman + +--- + fs/btrfs/file.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +--- a/fs/btrfs/file.c ++++ b/fs/btrfs/file.c +@@ -2390,10 +2390,13 @@ out: + */ + static int find_first_non_hole(struct inode *inode, u64 *start, u64 *len) + { ++ struct btrfs_fs_info *fs_info = btrfs_sb(inode->i_sb); + struct extent_map *em; + int ret = 0; + +- em = btrfs_get_extent(BTRFS_I(inode), NULL, 0, *start, *len, 0); ++ em = btrfs_get_extent(BTRFS_I(inode), NULL, 0, ++ round_down(*start, fs_info->sectorsize), ++ round_up(*len, fs_info->sectorsize), 0); + if (IS_ERR(em)) + return PTR_ERR(em); + diff --git a/queue-4.12/btrfs-incremental-send-fix-invalid-memory-access.patch b/queue-4.12/btrfs-incremental-send-fix-invalid-memory-access.patch new file mode 100644 index 00000000000..e0dd17e089f --- /dev/null +++ b/queue-4.12/btrfs-incremental-send-fix-invalid-memory-access.patch @@ -0,0 +1,154 @@ +From 24e52b11e0ca788513b945a87b57cc0522a92933 Mon Sep 17 00:00:00 2001 +From: Filipe Manana +Date: Thu, 6 Jul 2017 15:31:46 +0100 +Subject: Btrfs: incremental send, fix invalid memory access + +From: Filipe Manana + +commit 24e52b11e0ca788513b945a87b57cc0522a92933 upstream. + +When doing an incremental send, while processing an extent that changed +between the parent and send snapshots and that extent was an inline extent +in the parent snapshot, it's possible to access a memory region beyond +the end of leaf if the inline extent is very small and it is the first +item in a leaf. + +An example scenario is described below. + +The send snapshot has the following leaf: + + leaf 33865728 items 33 free space 773 generation 46 owner 5 + fs uuid ab7090d8-dafd-4fb9-9246-723b6d2e2fb7 + chunk uuid 2d16478c-c704-4ab9-b574-68bff2281b1f + (...) + item 14 key (335 EXTENT_DATA 0) itemoff 3052 itemsize 53 + generation 36 type 1 (regular) + extent data disk byte 12791808 nr 4096 + extent data offset 0 nr 4096 ram 4096 + extent compression 0 (none) + item 15 key (335 EXTENT_DATA 8192) itemoff 2999 itemsize 53 + generation 36 type 1 (regular) + extent data disk byte 138170368 nr 225280 + extent data offset 0 nr 225280 ram 225280 + extent compression 0 (none) + (...) + +And the parent snapshot has the following leaf: + + leaf 31272960 items 17 free space 17 generation 31 owner 5 + fs uuid ab7090d8-dafd-4fb9-9246-723b6d2e2fb7 + chunk uuid 2d16478c-c704-4ab9-b574-68bff2281b1f + item 0 key (335 EXTENT_DATA 0) itemoff 3951 itemsize 44 + generation 31 type 0 (inline) + inline extent data size 23 ram_bytes 613 compression 1 (zlib) + (...) + +When computing the send stream, it is detected that the extent of inode +335, at file offset 0, and at fs/btrfs/send.c:is_extent_unchanged() we +grab the leaf from the parent snapshot and access the inline extent item. +However, before jumping to the 'out' label, we access the 'offset' and +'disk_bytenr' fields of the extent item, which should not be done for +inline extents since the inlined data starts at the offset of the +'disk_bytenr' field and can be very small. For example accessing the +'offset' field of the file extent item results in the following trace: + +[ 599.705368] general protection fault: 0000 [#1] PREEMPT SMP +[ 599.706296] Modules linked in: btrfs psmouse i2c_piix4 ppdev acpi_cpufreq serio_raw parport_pc i2c_core evdev tpm_tis tpm_tis_core sg pcspkr parport tpm button su$ +[ 599.709340] CPU: 7 PID: 5283 Comm: btrfs Not tainted 4.10.0-rc8-btrfs-next-46+ #1 +[ 599.709340] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.9.1-0-gb3ef39f-prebuilt.qemu-project.org 04/01/2014 +[ 599.709340] task: ffff88023eedd040 task.stack: ffffc90006658000 +[ 599.709340] RIP: 0010:read_extent_buffer+0xdb/0xf4 [btrfs] +[ 599.709340] RSP: 0018:ffffc9000665ba00 EFLAGS: 00010286 +[ 599.709340] RAX: db73880000000000 RBX: 0000000000000000 RCX: 0000000000000001 +[ 599.709340] RDX: ffffc9000665ba60 RSI: db73880000000000 RDI: ffffc9000665ba5f +[ 599.709340] RBP: ffffc9000665ba30 R08: 0000000000000001 R09: ffff88020dc5e098 +[ 599.709340] R10: 0000000000001000 R11: 0000160000000000 R12: 6db6db6db6db6db7 +[ 599.709340] R13: ffff880000000000 R14: 0000000000000000 R15: ffff88020dc5e088 +[ 599.709340] FS: 00007f519555a8c0(0000) GS:ffff88023f3c0000(0000) knlGS:0000000000000000 +[ 599.709340] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 +[ 599.709340] CR2: 00007f1411afd000 CR3: 0000000235f8e000 CR4: 00000000000006e0 +[ 599.709340] Call Trace: +[ 599.709340] btrfs_get_token_64+0x93/0xce [btrfs] +[ 599.709340] ? printk+0x48/0x50 +[ 599.709340] btrfs_get_64+0xb/0xd [btrfs] +[ 599.709340] process_extent+0x3a1/0x1106 [btrfs] +[ 599.709340] ? btree_read_extent_buffer_pages+0x5/0xef [btrfs] +[ 599.709340] changed_cb+0xb03/0xb3d [btrfs] +[ 599.709340] ? btrfs_get_token_32+0x7a/0xcc [btrfs] +[ 599.709340] btrfs_compare_trees+0x432/0x53d [btrfs] +[ 599.709340] ? process_extent+0x1106/0x1106 [btrfs] +[ 599.709340] btrfs_ioctl_send+0x960/0xe26 [btrfs] +[ 599.709340] btrfs_ioctl+0x181b/0x1fed [btrfs] +[ 599.709340] ? trace_hardirqs_on_caller+0x150/0x1ac +[ 599.709340] vfs_ioctl+0x21/0x38 +[ 599.709340] ? vfs_ioctl+0x21/0x38 +[ 599.709340] do_vfs_ioctl+0x611/0x645 +[ 599.709340] ? rcu_read_unlock+0x5b/0x5d +[ 599.709340] ? __fget+0x6d/0x79 +[ 599.709340] SyS_ioctl+0x57/0x7b +[ 599.709340] entry_SYSCALL_64_fastpath+0x18/0xad +[ 599.709340] RIP: 0033:0x7f51945eec47 +[ 599.709340] RSP: 002b:00007ffc21c13e98 EFLAGS: 00000202 ORIG_RAX: 0000000000000010 +[ 599.709340] RAX: ffffffffffffffda RBX: ffffffff81096459 RCX: 00007f51945eec47 +[ 599.709340] RDX: 00007ffc21c13f20 RSI: 0000000040489426 RDI: 0000000000000004 +[ 599.709340] RBP: ffffc9000665bf98 R08: 00007f519450d700 R09: 00007f519450d700 +[ 599.709340] R10: 00007f519450d9d0 R11: 0000000000000202 R12: 0000000000000046 +[ 599.709340] R13: ffffc9000665bf78 R14: 0000000000000000 R15: 00007f5195574040 +[ 599.709340] ? trace_hardirqs_off_caller+0x43/0xb1 +[ 599.709340] Code: 29 f0 49 39 d8 4c 0f 47 c3 49 03 81 58 01 00 00 44 89 c1 4c 01 c2 4c 29 c3 48 c1 f8 03 49 0f af c4 48 c1 e0 0c 4c 01 e8 48 01 c6 a4 31 f6 4$ +[ 599.709340] RIP: read_extent_buffer+0xdb/0xf4 [btrfs] RSP: ffffc9000665ba00 +[ 599.762057] ---[ end trace fe00d7af61b9f49e ]--- + +This is because the 'offset' field starts at an offset of 37 bytes +(offsetof(struct btrfs_file_extent_item, offset)), has a length of 8 +bytes and therefore attemping to read it causes a 1 byte access beyond +the end of the leaf, as the first item's content in a leaf is located +at the tail of the leaf, the item size is 44 bytes and the offset of +that field plus its length (37 + 8 = 45) goes beyond the item's size +by 1 byte. + +So fix this by accessing the 'offset' and 'disk_bytenr' fields after +jumping to the 'out' label if we are processing an inline extent. We +move the reading operation of the 'disk_bytenr' field too because we +have the same problem as for the 'offset' field explained above when +the inline data is less then 8 bytes. The access to the 'generation' +field is also moved but just for the sake of grouping access to all +the fields. + +Fixes: e1cbfd7bf6da ("Btrfs: send, fix file hole not being preserved due to inline extent") +Signed-off-by: Filipe Manana +Signed-off-by: Greg Kroah-Hartman + +--- + fs/btrfs/send.c | 7 ++++--- + 1 file changed, 4 insertions(+), 3 deletions(-) + +--- a/fs/btrfs/send.c ++++ b/fs/btrfs/send.c +@@ -5190,15 +5190,12 @@ static int is_extent_unchanged(struct se + goto out; + } + +- right_disknr = btrfs_file_extent_disk_bytenr(eb, ei); + if (right_type == BTRFS_FILE_EXTENT_INLINE) { + right_len = btrfs_file_extent_inline_len(eb, slot, ei); + right_len = PAGE_ALIGN(right_len); + } else { + right_len = btrfs_file_extent_num_bytes(eb, ei); + } +- right_offset = btrfs_file_extent_offset(eb, ei); +- right_gen = btrfs_file_extent_generation(eb, ei); + + /* + * Are we at extent 8? If yes, we know the extent is changed. +@@ -5223,6 +5220,10 @@ static int is_extent_unchanged(struct se + goto out; + } + ++ right_disknr = btrfs_file_extent_disk_bytenr(eb, ei); ++ right_offset = btrfs_file_extent_offset(eb, ei); ++ right_gen = btrfs_file_extent_generation(eb, ei); ++ + left_offset_fixed = left_offset; + if (key.offset < ekey->offset) { + /* Fix the right offset for 2a and 7. */ diff --git a/queue-4.12/igb-explicitly-select-page-0-at-initialization.patch b/queue-4.12/igb-explicitly-select-page-0-at-initialization.patch new file mode 100644 index 00000000000..92fc53113d5 --- /dev/null +++ b/queue-4.12/igb-explicitly-select-page-0-at-initialization.patch @@ -0,0 +1,47 @@ +From 440aeca4b9858248d8f16d724d9fa87a4f65fa33 Mon Sep 17 00:00:00 2001 +From: Matwey V Kornilov +Date: Thu, 24 Nov 2016 13:32:48 +0300 +Subject: igb: Explicitly select page 0 at initialization + +From: Matwey V Kornilov + +commit 440aeca4b9858248d8f16d724d9fa87a4f65fa33 upstream. + +The functions igb_read_phy_reg_gs40g/igb_write_phy_reg_gs40g (which were +removed in 2a3cdea) explicitly selected the required page at every phy_reg +access. Currently, igb_get_phy_id_82575 relays on the fact that page 0 is +already selected. The assumption is not fulfilled for my Lex 3I380CW +motherboard with integrated dual i211 based gigabit ethernet. This leads to igb +initialization failure and network interfaces are not working: + + igb: Intel(R) Gigabit Ethernet Network Driver - version 5.4.0-k + igb: Copyright (c) 2007-2014 Intel Corporation. + igb: probe of 0000:01:00.0 failed with error -2 + igb: probe of 0000:02:00.0 failed with error -2 + +In order to fix it, we explicitly select page 0 before first access to phy +registers. + +See also: https://bugzilla.suse.com/show_bug.cgi?id=1009911 +See also: http://www.lex.com.tw/products/pdf/3I380A&3I380CW.pdf + +Fixes: 2a3cdea ("igb: Remove GS40G specific defines/functions") +Signed-off-by: Matwey V Kornilov +Tested-by: Aaron Brown +Signed-off-by: Jeff Kirsher +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/net/ethernet/intel/igb/e1000_82575.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/net/ethernet/intel/igb/e1000_82575.c ++++ b/drivers/net/ethernet/intel/igb/e1000_82575.c +@@ -257,6 +257,7 @@ static s32 igb_init_phy_params_82575(str + } + + /* Set phy->phy_addr and phy->id. */ ++ igb_write_phy_reg_82580(hw, I347AT4_PAGE_SELECT, 0); + ret_val = igb_get_phy_id_82575(hw); + if (ret_val) + return ret_val; diff --git a/queue-4.12/mwifiex-fixup-error-cases-in-mwifiex_add_virtual_intf.patch b/queue-4.12/mwifiex-fixup-error-cases-in-mwifiex_add_virtual_intf.patch new file mode 100644 index 00000000000..726046db225 --- /dev/null +++ b/queue-4.12/mwifiex-fixup-error-cases-in-mwifiex_add_virtual_intf.patch @@ -0,0 +1,181 @@ +From 8535107aa4ef92520cbb9a4739563b389c5f8e2c Mon Sep 17 00:00:00 2001 +From: Brian Norris +Date: Fri, 12 May 2017 09:41:58 -0700 +Subject: mwifiex: fixup error cases in mwifiex_add_virtual_intf() + +From: Brian Norris + +commit 8535107aa4ef92520cbb9a4739563b389c5f8e2c upstream. + +If we fail to add an interface in mwifiex_add_virtual_intf(), we might +hit a BUG_ON() in the networking code, because we didn't tear things +down properly. Among the problems: + + (a) when failing to allocate workqueues, we fail to unregister the + netdev before calling free_netdev() + (b) even if we do try to unregister the netdev, we're still holding the + rtnl lock, so the device never properly unregistered; we'll be at + state NETREG_UNREGISTERING, and then hit free_netdev()'s: + BUG_ON(dev->reg_state != NETREG_UNREGISTERED); + (c) we're allocating some dependent resources (e.g., DFS workqueues) + after we've registered the interface; this may or may not cause + problems, but it's good practice to allocate these before registering + (d) we're not even trying to unwind anything when mwifiex_send_cmd() or + mwifiex_sta_init_cmd() fail + +To fix these issues, let's: + + * add a stacked set of error handling labels, to keep error handling + consistent and properly ordered (resolving (a) and (d)) + * move the workqueue allocations before the registration (to resolve + (c); also resolves (b) by avoiding error cases where we have to + unregister) + +[Incidentally, it's pretty easy to interrupt the alloc_workqueue() in, +e.g., the following: + + iw phy phy0 interface add mlan0 type station + +by sending it SIGTERM.] + +This bugfix covers commits like commit 7d652034d1a0 ("mwifiex: channel +switch support for mwifiex"), but parts of this bug exist all the way +back to the introduction of dynamic interface handling in commit +93a1df48d224 ("mwifiex: add cfg80211 handlers add/del_virtual_intf"). + +Signed-off-by: Brian Norris +Signed-off-by: Kalle Valo +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/net/wireless/marvell/mwifiex/cfg80211.c | 71 +++++++++++------------- + 1 file changed, 35 insertions(+), 36 deletions(-) + +--- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c ++++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c +@@ -2964,10 +2964,8 @@ struct wireless_dev *mwifiex_add_virtual + if (!dev) { + mwifiex_dbg(adapter, ERROR, + "no memory available for netdevice\n"); +- memset(&priv->wdev, 0, sizeof(priv->wdev)); +- priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED; +- priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED; +- return ERR_PTR(-ENOMEM); ++ ret = -ENOMEM; ++ goto err_alloc_netdev; + } + + mwifiex_init_priv_params(priv, dev); +@@ -2976,11 +2974,11 @@ struct wireless_dev *mwifiex_add_virtual + ret = mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE, + HostCmd_ACT_GEN_SET, 0, NULL, true); + if (ret) +- return ERR_PTR(ret); ++ goto err_set_bss_mode; + + ret = mwifiex_sta_init_cmd(priv, false, false); + if (ret) +- return ERR_PTR(ret); ++ goto err_sta_init; + + mwifiex_setup_ht_caps(&wiphy->bands[NL80211_BAND_2GHZ]->ht_cap, priv); + if (adapter->is_hw_11ac_capable) +@@ -3011,31 +3009,14 @@ struct wireless_dev *mwifiex_add_virtual + + SET_NETDEV_DEV(dev, adapter->dev); + +- /* Register network device */ +- if (register_netdevice(dev)) { +- mwifiex_dbg(adapter, ERROR, +- "cannot register virtual network device\n"); +- free_netdev(dev); +- priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED; +- priv->netdev = NULL; +- memset(&priv->wdev, 0, sizeof(priv->wdev)); +- priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED; +- return ERR_PTR(-EFAULT); +- } +- + priv->dfs_cac_workqueue = alloc_workqueue("MWIFIEX_DFS_CAC%s", + WQ_HIGHPRI | + WQ_MEM_RECLAIM | + WQ_UNBOUND, 1, name); + if (!priv->dfs_cac_workqueue) { +- mwifiex_dbg(adapter, ERROR, +- "cannot register virtual network device\n"); +- free_netdev(dev); +- priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED; +- priv->netdev = NULL; +- memset(&priv->wdev, 0, sizeof(priv->wdev)); +- priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED; +- return ERR_PTR(-ENOMEM); ++ mwifiex_dbg(adapter, ERROR, "cannot alloc DFS CAC queue\n"); ++ ret = -ENOMEM; ++ goto err_alloc_cac; + } + + INIT_DELAYED_WORK(&priv->dfs_cac_work, mwifiex_dfs_cac_work_queue); +@@ -3044,16 +3025,9 @@ struct wireless_dev *mwifiex_add_virtual + WQ_HIGHPRI | WQ_UNBOUND | + WQ_MEM_RECLAIM, 1, name); + if (!priv->dfs_chan_sw_workqueue) { +- mwifiex_dbg(adapter, ERROR, +- "cannot register virtual network device\n"); +- free_netdev(dev); +- priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED; +- priv->netdev = NULL; +- memset(&priv->wdev, 0, sizeof(priv->wdev)); +- priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED; +- destroy_workqueue(priv->dfs_cac_workqueue); +- priv->dfs_cac_workqueue = NULL; +- return ERR_PTR(-ENOMEM); ++ mwifiex_dbg(adapter, ERROR, "cannot alloc DFS channel sw queue\n"); ++ ret = -ENOMEM; ++ goto err_alloc_chsw; + } + + INIT_DELAYED_WORK(&priv->dfs_chan_sw_work, +@@ -3061,6 +3035,13 @@ struct wireless_dev *mwifiex_add_virtual + + sema_init(&priv->async_sem, 1); + ++ /* Register network device */ ++ if (register_netdevice(dev)) { ++ mwifiex_dbg(adapter, ERROR, "cannot register network device\n"); ++ ret = -EFAULT; ++ goto err_reg_netdev; ++ } ++ + mwifiex_dbg(adapter, INFO, + "info: %s: Marvell 802.11 Adapter\n", dev->name); + +@@ -3081,11 +3062,29 @@ struct wireless_dev *mwifiex_add_virtual + adapter->curr_iface_comb.p2p_intf++; + break; + default: ++ /* This should be dead code; checked above */ + mwifiex_dbg(adapter, ERROR, "type not supported\n"); + return ERR_PTR(-EINVAL); + } + + return &priv->wdev; ++ ++err_reg_netdev: ++ destroy_workqueue(priv->dfs_chan_sw_workqueue); ++ priv->dfs_chan_sw_workqueue = NULL; ++err_alloc_chsw: ++ destroy_workqueue(priv->dfs_cac_workqueue); ++ priv->dfs_cac_workqueue = NULL; ++err_alloc_cac: ++ free_netdev(dev); ++ priv->netdev = NULL; ++err_sta_init: ++err_set_bss_mode: ++err_alloc_netdev: ++ memset(&priv->wdev, 0, sizeof(priv->wdev)); ++ priv->wdev.iftype = NL80211_IFTYPE_UNSPECIFIED; ++ priv->bss_mode = NL80211_IFTYPE_UNSPECIFIED; ++ return ERR_PTR(ret); + } + EXPORT_SYMBOL_GPL(mwifiex_add_virtual_intf); + diff --git a/queue-4.12/pstore-don-t-warn-if-data-is-uncompressed-and-type-is-not-pstore_type_dmesg.patch b/queue-4.12/pstore-don-t-warn-if-data-is-uncompressed-and-type-is-not-pstore_type_dmesg.patch new file mode 100644 index 00000000000..b7bab2d3e51 --- /dev/null +++ b/queue-4.12/pstore-don-t-warn-if-data-is-uncompressed-and-type-is-not-pstore_type_dmesg.patch @@ -0,0 +1,52 @@ +From 4a16d1cb245c56e72fd40a28f3cdb394cde4b341 Mon Sep 17 00:00:00 2001 +From: Ankit Kumar +Date: Tue, 23 May 2017 11:16:52 +0530 +Subject: pstore: Don't warn if data is uncompressed and type is not PSTORE_TYPE_DMESG + +From: Ankit Kumar + +commit 4a16d1cb245c56e72fd40a28f3cdb394cde4b341 upstream. + +commit 9abdcccc3d5f ("pstore: Extract common arguments into structure") +moved record decompression to function. decompress_record() gets +called without checking type and compressed flag. Warning will be +reported if data is uncompressed. Pstore type PSTORE_TYPE_PPC_OPAL, +PSTORE_TYPE_PPC_COMMON doesn't contain compressed data and warning get +printed part of dmesg. + +Partial dmesg log: +[ 35.848914] pstore: ignored compressed record type 6 +[ 35.848927] pstore: ignored compressed record type 8 + +Above warning should not get printed as it is known that data won't be +compressed for above type and it is valid condition. + +This patch returns if data is not compressed and print warning only if +data is compressed and type is not PSTORE_TYPE_DMESG. + +Reported-by: Anton Blanchard +Signed-off-by: Ankit Kumar +Reviewed-by: Mahesh Salgaonkar +Signed-off-by: Kees Cook +Fixes: 9abdcccc3d5f ("pstore: Extract common arguments into structure") +Signed-off-by: Greg Kroah-Hartman + +--- + fs/pstore/platform.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +--- a/fs/pstore/platform.c ++++ b/fs/pstore/platform.c +@@ -770,8 +770,11 @@ static void decompress_record(struct pst + int unzipped_len; + char *decompressed; + ++ if (!record->compressed) ++ return; ++ + /* Only PSTORE_TYPE_DMESG support compression. */ +- if (!record->compressed || record->type != PSTORE_TYPE_DMESG) { ++ if (record->type != PSTORE_TYPE_DMESG) { + pr_warn("ignored compressed record type %d\n", record->type); + return; + } diff --git a/queue-4.12/series b/queue-4.12/series index 08060b50cec..de385522dfe 100644 --- a/queue-4.12/series +++ b/queue-4.12/series @@ -24,3 +24,11 @@ perf-intel-pt-ensure-never-to-set-last_ip-when-packet-count-is-zero.patch perf-intel-pt-use-fup-always-when-scanning-for-an-ip.patch perf-intel-pt-clear-fup-flag-on-error.patch bluetooth-use-constant-time-memory-comparison-for-secret-values.patch +wlcore-fix-64k-page-support.patch +pstore-don-t-warn-if-data-is-uncompressed-and-type-is-not-pstore_type_dmesg.patch +mwifiex-fixup-error-cases-in-mwifiex_add_virtual_intf.patch +btrfs-fix-invalid-extent-maps-due-to-hole-punching.patch +btrfs-don-t-clear-sgid-when-inheriting-acls.patch +btrfs-incremental-send-fix-invalid-memory-access.patch +igb-explicitly-select-page-0-at-initialization.patch +spi-atmel-fix-corrupted-data-issue-on-sam9-family-socs.patch diff --git a/queue-4.12/spi-atmel-fix-corrupted-data-issue-on-sam9-family-socs.patch b/queue-4.12/spi-atmel-fix-corrupted-data-issue-on-sam9-family-socs.patch new file mode 100644 index 00000000000..f781fc4b76a --- /dev/null +++ b/queue-4.12/spi-atmel-fix-corrupted-data-issue-on-sam9-family-socs.patch @@ -0,0 +1,79 @@ +From 7094576ccdc3acfe1e06a1e2ab547add375baf7f Mon Sep 17 00:00:00 2001 +From: Cyrille Pitchen +Date: Fri, 23 Jun 2017 17:39:16 +0200 +Subject: spi: atmel: fix corrupted data issue on SAM9 family SoCs + +From: Cyrille Pitchen + +commit 7094576ccdc3acfe1e06a1e2ab547add375baf7f upstream. + +This patch disables the use of the DMA for data transfer and forces the +use of PIO transfers instead as a quick fixup to solve the cache aliasing +issue on ARM9 based cores, which embeds a VIVT data cache. + +Indeed in the case of VIVT data caches, it is not safe to call dma_map_*() +functions to map buffers for DMA transfers when those buffers have been +allocated by vmalloc() or from any DMA-unsafe area. + +Further patches may propose a better solution based on the use of a bounce +buffer at the SPI sub-system level but such solution needs more time to be +discussed. Then the use of DMA transfers could be enabled again to improve +the performances but before that, this patch already solves the issue. + +Signed-off-by: Cyrille Pitchen +Acked-by: Nicolas Ferre +Signed-off-by: Mark Brown +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/spi/spi-atmel.c | 24 +++++++++++++++++++++++- + 1 file changed, 23 insertions(+), 1 deletion(-) + +--- a/drivers/spi/spi-atmel.c ++++ b/drivers/spi/spi-atmel.c +@@ -269,6 +269,7 @@ struct atmel_spi_caps { + bool is_spi2; + bool has_wdrbt; + bool has_dma_support; ++ bool has_pdc_support; + }; + + /* +@@ -1426,7 +1427,28 @@ static void atmel_get_caps(struct atmel_ + + as->caps.is_spi2 = version > 0x121; + as->caps.has_wdrbt = version >= 0x210; ++#ifdef CONFIG_SOC_SAM_V4_V5 ++ /* ++ * Atmel SoCs based on ARM9 (SAM9x) cores should not use spi_map_buf() ++ * since this later function tries to map buffers with dma_map_sg() ++ * even if they have not been allocated inside DMA-safe areas. ++ * On SoCs based on Cortex A5 (SAMA5Dx), it works anyway because for ++ * those ARM cores, the data cache follows the PIPT model. ++ * Also the L2 cache controller of SAMA5D2 uses the PIPT model too. ++ * In case of PIPT caches, there cannot be cache aliases. ++ * However on ARM9 cores, the data cache follows the VIVT model, hence ++ * the cache aliases issue can occur when buffers are allocated from ++ * DMA-unsafe areas, by vmalloc() for instance, where cache coherency is ++ * not taken into account or at least not handled completely (cache ++ * lines of aliases are not invalidated). ++ * This is not a theorical issue: it was reproduced when trying to mount ++ * a UBI file-system on a at91sam9g35ek board. ++ */ ++ as->caps.has_dma_support = false; ++#else + as->caps.has_dma_support = version >= 0x212; ++#endif ++ as->caps.has_pdc_support = version < 0x212; + } + + /*-------------------------------------------------------------------------*/ +@@ -1567,7 +1589,7 @@ static int atmel_spi_probe(struct platfo + } else if (ret == -EPROBE_DEFER) { + return ret; + } +- } else { ++ } else if (as->caps.has_pdc_support) { + as->use_pdc = true; + } + diff --git a/queue-4.12/wlcore-fix-64k-page-support.patch b/queue-4.12/wlcore-fix-64k-page-support.patch new file mode 100644 index 00000000000..67f665e11f9 --- /dev/null +++ b/queue-4.12/wlcore-fix-64k-page-support.patch @@ -0,0 +1,46 @@ +From 4a4274bf2dbbd1c7a45be0c89a1687c9d2eef4a0 Mon Sep 17 00:00:00 2001 +From: Arnd Bergmann +Date: Thu, 11 May 2017 13:52:09 +0200 +Subject: wlcore: fix 64K page support + +From: Arnd Bergmann + +commit 4a4274bf2dbbd1c7a45be0c89a1687c9d2eef4a0 upstream. + +In the stable linux-3.16 branch, I ran into a warning in the +wlcore driver: + +drivers/net/wireless/ti/wlcore/spi.c: In function 'wl12xx_spi_raw_write': +drivers/net/wireless/ti/wlcore/spi.c:315:1: error: the frame size of 12848 bytes is larger than 2048 bytes [-Werror=frame-larger-than=] + +Newer kernels no longer show the warning, but the bug is still there, +as the allocation is based on the CPU page size rather than the +actual capabilities of the hardware. + +This replaces the PAGE_SIZE macro with the SZ_4K macro, i.e. 4096 bytes +per buffer. + +Signed-off-by: Arnd Bergmann +Signed-off-by: Kalle Valo +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/net/wireless/ti/wlcore/spi.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +--- a/drivers/net/wireless/ti/wlcore/spi.c ++++ b/drivers/net/wireless/ti/wlcore/spi.c +@@ -70,10 +70,10 @@ + #define WSPI_MAX_CHUNK_SIZE 4092 + + /* +- * wl18xx driver aggregation buffer size is (13 * PAGE_SIZE) compared to +- * (4 * PAGE_SIZE) for wl12xx, so use the larger buffer needed for wl18xx ++ * wl18xx driver aggregation buffer size is (13 * 4K) compared to ++ * (4 * 4K) for wl12xx, so use the larger buffer needed for wl18xx + */ +-#define SPI_AGGR_BUFFER_SIZE (13 * PAGE_SIZE) ++#define SPI_AGGR_BUFFER_SIZE (13 * SZ_4K) + + /* Maximum number of SPI write chunks */ + #define WSPI_MAX_NUM_OF_CHUNKS \