This is the start of the stable review cycle for the 4.4.187 release. There are 158 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Sun 04 Aug 2019 09:19:34 AM UTC. Anything received after that time might be too late.
The whole patch series can be found in one patch at: https://www.kernel.org/pub/linux/kernel/v4.x/stable-review/patch-4.4.187-rc1... or in the git tree and branch at: git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git linux-4.4.y and the diffstat can be found below.
thanks,
greg k-h
------------- Pseudo-Shortlog of commits:
Greg Kroah-Hartman gregkh@linuxfoundation.org Linux 4.4.187-rc1
Yan, Zheng zyan@redhat.com ceph: hold i_ceph_lock when removing caps for freeing inode
Miroslav Lichvar mlichvar@redhat.com drivers/pps/pps.c: clear offset flags in PPS_SETPARAMS ioctl
Jann Horn jannh@google.com sched/fair: Don't free p->numa_faults with concurrent readers
Vladis Dronov vdronov@redhat.com Bluetooth: hci_uart: check for missing tty operations
Luke Nowakowski-Krijger lnowakow@eng.ucsd.edu media: radio-raremono: change devm_k*alloc to k*alloc
Oliver Neukum oneukum@suse.com media: cpia2_usb: first wake up, then free in disconnect
Phong Tran tranmanphong@gmail.com ISDN: hfcsusb: checking idx of ep configuration
Soheil Hassas Yeganeh soheil@google.com tcp: reset sk_send_head in tcp_write_queue_purge
Xin Long lucien.xin@gmail.com ipv6: check sk sk_type and protocol early in ip_mroute_set/getsockopt
Michal Hocko mhocko@suse.com mm, vmstat: make quiet_vmstat lighter
Christoph Lameter cl@linux.com vmstat: Remove BUG_ON from vmstat_update
Linus Torvalds torvalds@linux-foundation.org access: avoid the RCU grace period for the temporary subjective credentials
Michael Neuling mikey@neuling.org powerpc/tm: Fix oops on sigreturn on systems without TM
Hui Wang hui.wang@canonical.com ALSA: hda - Add a conexant codec entry to let mute led work
Kai-Heng Feng kai.heng.feng@canonical.com ALSA: line6: Fix wrong altsetting for LINE6_PODHD500_1
Kefeng Wang wangkefeng.wang@huawei.com hpet: Fix division by zero in hpet_time_div()
Zhenzhong Duan zhenzhong.duan@oracle.com x86/speculation/mds: Apply more accurate check on hypervisor platform
Hans de Goede hdegoede@redhat.com x86/sysfb_efi: Add quirks for some devices with swapped width and height
Ryan Kennedy ryan5544@gmail.com usb: pci-quirks: Correct AMD PLL quirk detection
Phong Tran tranmanphong@gmail.com usb: wusbcore: fix unbalanced get/put cluster_id
Arnd Bergmann arnd@arndb.de locking/lockdep: Hide unused 'class' variable
Yuyang Du duyuyang@gmail.com locking/lockdep: Fix lock used or unused stats error
Jean-Philippe Brucker jean-philippe.brucker@arm.com mm/mmu_notifier: use hlist_add_head_rcu()
Christoph Hellwig hch@lst.de 9p: pass the correct prototype to read_cache_page
Dmitry Vyukov dvyukov@google.com mm/kmemleak.c: fix check for softirq context
Sam Ravnborg sam@ravnborg.org sh: prevent warnings when using iounmap
Oliver O'Halloran oohall@gmail.com powerpc/eeh: Handle hugepages in ioremap space
morten petersen morten_bp@live.dk mailbox: handle failed named mailbox channel request
Ocean Chen oceanchen@google.com f2fs: avoid out-of-range memory access
Numfor Mbiziwo-Tiapo nums@google.com perf test mmap-thread-lookup: Initialize variable to suppress memory sanitizer warning
Vasily Gorbik gor@linux.ibm.com kallsyms: exclude kasan local symbols on s390
Geert Uytterhoeven geert+renesas@glider.be serial: sh-sci: Fix TX DMA buffer flushing and workqueue races
Christian Lamparter chunkeey@gmail.com powerpc/4xx/uic: clear pending interrupt after irq type/pol change
Johannes Berg johannes.berg@intel.com um: Silence lockdep complaint about mmap_sem
Arnd Bergmann arnd@arndb.de mfd: arizona: Fix undefined behavior
Robert Hancock hancock@sedsystems.ca mfd: core: Set fwnode for created devices
Naveen N. Rao naveen.n.rao@linux.vnet.ibm.com recordmcount: Fix spurious mcount entries on powerpc
Bastien Nocera hadess@hadess.net iio: iio-utils: Fix possible incorrect mask calculation
Marek Vasut marek.vasut+renesas@gmail.com PCI: sysfs: Ignore lockdep for remove attribute
Alexey Kardashevskiy aik@ozlabs.ru powerpc/pci/of: Fix OF flags parsing for 64bit BARs
Andrzej Pietrasiewicz andrzej.p@collabora.com usb: gadget: Zero ffs_io_data
Nathan Lynch nathanl@linux.ibm.com powerpc/pseries/mobility: rebuild cacheinfo hierarchy post-migration
Nathan Lynch nathanl@linux.ibm.com powerpc/pseries/mobility: prevent cpu hotplug during DT update
Yoshihiro Shimoda yoshihiro.shimoda.uh@renesas.com phy: renesas: rcar-gen2: Fix memory leak at error paths
David Riley davidriley@chromium.org drm/virtio: Add memory barriers for capset cache.
Jorge Ramirez-Ortiz jorge.ramirez-ortiz@linaro.org tty: serial: msm_serial: avoid system lockup condition
Kefeng Wang wangkefeng.wang@huawei.com tty/serial: digicolor: Fix digicolor-usart already registered warning
Wang Hai wanghai26@huawei.com memstick: Fix error cleanup path of memstick_init
Christophe Leroy christophe.leroy@c-s.fr tty: serial: cpm_uart - fix init when SMC is relocated
Wen Yang wen.yang99@zte.com.cn pinctrl: rockchip: fix leaked of_node references
Serge Semin fancer.lancer@gmail.com tty: max310x: Fix invalid baudrate divisors calculator
Thinh Nguyen Thinh.Nguyen@synopsys.com usb: core: hub: Disable hub-initiated U1/U2
Peter Ujfalusi peter.ujfalusi@ti.com drm/panel: simple: Fix panel_simple_dsi_probe
Paul Menzel pmenzel@molgen.mpg.de nfsd: Fix overflow causing non-working mounts on 1 TB machines
J. Bruce Fields bfields@redhat.com nfsd: fix performance-limiting session calculation
J. Bruce Fields bfields@redhat.com nfsd: give out fewer session slots as limit approaches
J. Bruce Fields bfields@redhat.com nfsd: increase DRC cache limit
Trond Myklebust trond.myklebust@primarydata.com NFSv4: Fix open create exclusive when the server reboots
Eric Biggers ebiggers@google.com elevator: fix truncation of icq_cache_name
Nikolay Aleksandrov nikolay@cumulusnetworks.com net: bridge: stp: don't cache eth dest pointer before skb pull
Nikolay Aleksandrov nikolay@cumulusnetworks.com net: bridge: mcast: fix stale ipv6 hdr pointer when handling v6 query
Nikolay Aleksandrov nikolay@cumulusnetworks.com net: bridge: mcast: fix stale nsrcs pointer in igmp3/mld2 report handling
Cong Wang xiyou.wangcong@gmail.com bonding: validate ip header before check IPPROTO_IGMP
Christoph Paasch cpaasch@apple.com tcp: Reset bytes_acked and bytes_received when disconnecting
Cong Wang xiyou.wangcong@gmail.com netrom: hold sock when setting skb->destructor
Cong Wang xiyou.wangcong@gmail.com netrom: fix a memory leak in nr_rx_frame()
Takashi Iwai tiwai@suse.de sky2: Disable MSI on ASUS P6T
Yang Wei albin_yang@163.com nfc: fix potential illegal memory access
Lorenzo Bianconi lorenzo.bianconi@redhat.com net: neigh: fix multiple neigh timer scheduling
Justin Chen justinpopo6@gmail.com net: bcmgenet: use promisc for unsupported filters
Matteo Croce mcroce@redhat.com ipv4: don't set IPv6 only flags to IPv4 addresses
Taehee Yoo ap420073@gmail.com caif-hsi: fix possible deadlock in cfhsi_exit_module()
Brian King brking@linux.vnet.ibm.com bnx2x: Prevent load reordering in tx completion processing
Junxiao Bi junxiao.bi@oracle.com dm bufio: fix deadlock with loop device
Lee, Chiasheng chiasheng.lee@intel.com usb: Handle USB3 remote wakeup for LPM enabled devices correctly
Szymon Janc szymon.janc@codecoup.pl Bluetooth: Add SMP workaround Microsoft Surface Precision Mouse bug
Alexander Shishkin alexander.shishkin@linux.intel.com intel_th: msu: Fix single mode with disabled IOMMU
Dan Carpenter dan.carpenter@oracle.com eCryptfs: fix a couple type promotion bugs
Ravi Bangoria ravi.bangoria@linux.ibm.com powerpc/watchpoint: Restore NV GPRs while returning from exception
Christophe Leroy christophe.leroy@c-s.fr powerpc/32s: fix suspend/resume when IBATs 4-7 are used
Helge Deller deller@gmx.de parisc: Fix kernel panic due invalid values in IAOQ0 or IAOQ1
Steve Longerbeam slongerbeam@gmail.com gpu: ipu-v3: ipu-ic: Fix saturation bit offset in TPMEM
Jan Harkes jaharkes@cs.cmu.edu coda: pass the host file in vma->vm_file on mmap
Denis Efremov efremov@ispras.ru floppy: fix out-of-bounds read in copy_buffer
Denis Efremov efremov@ispras.ru floppy: fix invalid pointer dereference in drive_name
Denis Efremov efremov@ispras.ru floppy: fix out-of-bounds read in next_valid_format
Denis Efremov efremov@ispras.ru floppy: fix div-by-zero in setup_format_params
Al Viro viro@zeniv.linux.org.uk take floppy compat ioctls to sodding floppy.c
Mika Westerberg mika.westerberg@linux.intel.com PCI: Do not poll for PME if the device is in D3cold
YueHaibing yuehaibing@huawei.com 9p/virtio: Add cleanup path in p9_virtio_init
Daniel Jordan daniel.m.jordan@oracle.com padata: use smp_mb in padata_reorder to avoid orphaned padata jobs
Lyude Paul lyude@redhat.com drm/nouveau/i2c: Enable i2c pads & busses during preinit
Like Xu like.xu@linux.intel.com KVM: x86/vPMU: refine kvm_pmu err msg when event creation failed
Ezequiel Garcia ezequiel@collabora.com media: coda: Remove unbalanced and unneeded mutex unlock
Boris Brezillon boris.brezillon@collabora.com media: v4l2: Test type instead of cfg->type in v4l2_ctrl_new_custom()
Takashi Iwai tiwai@suse.de ALSA: seq: Break too long mutex context in the write loop
Christophe Leroy christophe.leroy@c-s.fr lib/scatterlist: Fix mapping iterator when sg->offset is greater than PAGE_SIZE
Trond Myklebust trond.myklebust@hammerspace.com NFSv4: Handle the special Linux file open access mode
Eiichi Tsukata devel@etsukata.com tracing/snapshot: Resize spare buffer if size changed
Krzysztof Kozlowski krzk@kernel.org regulator: s2mps11: Fix buck7 and buck8 wrong voltages
Grant Hernandez granthernandez@google.com Input: gtco - bounds check collection indent level
Elena Petrova lenaptr@google.com crypto: arm64/sha2-ce - correct digest for empty data in finup
Elena Petrova lenaptr@google.com crypto: arm64/sha1-ce - correct digest for empty data in finup
Eric Biggers ebiggers@google.com crypto: ghash - fix unaligned memory access in ghash_setkey()
csonsino csonsino@gmail.com Bluetooth: validate BLE connection interval updates
Matias Karhumaa matias.karhumaa@gmail.com Bluetooth: Check state in l2cap_disconnect_rsp
Josua Mayer josua.mayer@jm0.eu Bluetooth: 6lowpan: search for destination address in all peers
Tomas Bortoli tomasbortoli@gmail.com Bluetooth: hci_bcsp: Fix memory leak in rx_skb
Coly Li colyli@suse.de bcache: check c->gc_thread by IS_ERR_OR_NULL in cache_set_flush()
Eiichi Tsukata devel@etsukata.com EDAC: Fix global-out-of-bounds write when setting edac_mc_poll_msec
Mauro S. M. Rodrigues maurosr@linux.vnet.ibm.com ixgbe: Check DDM existence in transceiver before access
Ferdinand Blomqvist ferdinand.blomqvist@gmail.com rslib: Fix handling of of caller provided syndrome
Ferdinand Blomqvist ferdinand.blomqvist@gmail.com rslib: Fix decoding of shortened codes
Miaoqing Pan miaoqing@codeaurora.org ath10k: fix PCIE device wake up failed
Lorenzo Bianconi lorenzo@kernel.org mt7601u: fix possible memory leak when the device is disconnected
Masahiro Yamada yamada.masahiro@socionext.com x86/build: Add 'set -e' to mkcapflags.sh to delete broken capflags.c
Lorenzo Bianconi lorenzo@kernel.org mt7601u: do not schedule rx_tasklet when the device has been disconnected
Philipp Zabel p.zabel@pengutronix.de media: coda: increment sequence offset for the last returned frame
Philipp Zabel p.zabel@pengutronix.de media: coda: fix mpeg2 sequence number handling
Ard Biesheuvel ard.biesheuvel@linaro.org acpi/arm64: ignore 5.1 FADTs that are reported as 5.0
Nathan Huckleberry nhuck@google.com timer_list: Guard procfs specific code
Miroslav Lichvar mlichvar@redhat.com ntp: Limit TAI-UTC offset
Anders Roxell anders.roxell@linaro.org media: i2c: fix warning same module names
Pan Bian bianpan2016@163.com EDAC/sysfs: Fix memory leak when creating a csrow object
Jason Wang jasowang@redhat.com vhost_net: disable zerocopy by default
Arnaldo Carvalho de Melo acme@redhat.com perf evsel: Make perf_evsel__name() accept a NULL argument
Nicolas Dichtel nicolas.dichtel@6wind.com xfrm: fix sa selector validation
Waiman Long longman@redhat.com rcu: Force inlining of rcu_read_lock()
Valdis Kletnieks valdis.kletnieks@vt.edu bpf: silence warning messages in core
Srinivas Kandagatla srinivas.kandagatla@linaro.org regmap: fix bulk writes on paged registers
Russell King rmk+kernel@armlinux.org.uk gpio: omap: ensure irq is enabled before wakeup
Russell King rmk+kernel@armlinux.org.uk gpio: omap: fix lack of irqstatus_raw0 for OMAP4
Thomas Richter tmricht@linux.ibm.com perf test 6: Fix missing kvm module load for s390
Julian Wiedmann jwi@linux.ibm.com s390/qdio: handle PENDING state for QEBSM devices
Robert Hancock hancock@sedsystems.ca net: axienet: Fix race condition causing TX hang
Fabio Estevam festevam@gmail.com net: fec: Do not use netdev messages too early
Abhishek Goel huntbag@linux.vnet.ibm.com cpupower : frequency-set -r option misses the last cpu in related cpu list
Kefeng Wang wangkefeng.wang@huawei.com media: wl128x: Fix some error handling in fm_v4l2_init_video_device()
Imre Deak imre.deak@intel.com locking/lockdep: Fix merging of hlocks with non-zero references
David S. Miller davem@davemloft.net tua6100: Avoid build warnings.
Ioana Ciornei ioana.ciornei@nxp.com net: phy: Check against net_device being NULL
Shailendra Verma shailendra.v@samsung.com media: staging: media: davinci_vpfe: - Fix for memory leak if decoder initialization fails.
Anirudh Gupta anirudhrudr@gmail.com xfrm: Fix xfrm sel prefix length validation
Jeremy Sowden jeremy@azazel.net af_key: fix leaks in key_pol_get_resp and dump_sp.
Eric W. Biederman ebiederm@xmission.com signal/pid_namespace: Fix reboot_pid_ns to use send_sig not force_sig
Jose Abreu Jose.Abreu@synopsys.com net: stmmac: dwmac1000: Clear unused address entries
Kangjie Lu kjlu@umn.edu media: vpss: fix a potential NULL pointer dereference
Lubomir Rintel lkundrak@v3.sk media: marvell-ccic: fix DMA s/g desc number calculation
Christophe Leroy christophe.leroy@c-s.fr crypto: talitos - fix skcipher failure due to wrong output IV
Oliver Neukum oneukum@suse.com media: dvb: usb: fix use after free in dvb_usb_device_exit
Jeremy Sowden jeremy@azazel.net batman-adv: fix for leaked TVLV handler.
Anilkumar Kolli akolli@codeaurora.org ath: DFS JP domain W56 fixed pulse type 3 RADAR detection
Dan Carpenter dan.carpenter@oracle.com ath6kl: add some bounds checking
Tim Schumacher timschumi@gmx.de ath9k: Check for errors when reading SREV register
Surabhi Vishnoi svishnoi@codeaurora.org ath10k: Do not send probe response template for mesh
Sven Van Asbroeck thesven73@gmail.com dmaengine: imx-sdma: fix use-after-free on probe error path
Kevin Darbyshire-Bryant ldir@darbyshire-bryant.me.uk MIPS: fix build on non-linux hosts
Stefan Hellermann stefan@the2masters.de MIPS: ath79: fix ar933x uart parity mode
-------------
Diffstat:
Makefile | 4 +- arch/arm64/crypto/sha1-ce-glue.c | 2 +- arch/arm64/crypto/sha2-ce-glue.c | 2 +- arch/arm64/kernel/acpi.c | 10 +- arch/mips/boot/compressed/Makefile | 2 + arch/mips/boot/compressed/calc_vmlinuz_load_addr.c | 2 +- arch/mips/include/asm/mach-ath79/ar933x_uart.h | 4 +- arch/parisc/kernel/ptrace.c | 28 +- arch/powerpc/kernel/eeh.c | 15 +- arch/powerpc/kernel/exceptions-64s.S | 9 +- arch/powerpc/kernel/pci_of_scan.c | 2 + arch/powerpc/kernel/signal_32.c | 3 + arch/powerpc/kernel/signal_64.c | 5 + arch/powerpc/kernel/swsusp_32.S | 73 ++++- arch/powerpc/platforms/powermac/sleep.S | 68 +++- arch/powerpc/platforms/pseries/mobility.c | 19 ++ arch/powerpc/sysdev/uic.c | 1 + arch/sh/include/asm/io.h | 6 +- arch/um/include/asm/mmu_context.h | 2 +- arch/x86/kernel/cpu/bugs.c | 2 +- arch/x86/kernel/cpu/mkcapflags.sh | 2 + arch/x86/kernel/sysfb_efi.c | 46 +++ arch/x86/kvm/pmu.c | 4 +- block/compat_ioctl.c | 340 ------------------- crypto/ghash-generic.c | 8 +- drivers/base/regmap/regmap.c | 2 + drivers/block/floppy.c | 362 ++++++++++++++++++++- drivers/bluetooth/hci_ath.c | 3 + drivers/bluetooth/hci_bcm.c | 3 + drivers/bluetooth/hci_bcsp.c | 5 + drivers/bluetooth/hci_intel.c | 3 + drivers/bluetooth/hci_ldisc.c | 9 + drivers/bluetooth/hci_uart.h | 1 + drivers/char/hpet.c | 3 +- drivers/crypto/talitos.c | 4 + drivers/dma/imx-sdma.c | 48 +-- drivers/edac/edac_mc_sysfs.c | 24 +- drivers/edac/edac_module.h | 2 +- drivers/gpio/gpio-omap.c | 17 +- drivers/gpu/drm/nouveau/nvkm/subdev/i2c/base.c | 20 ++ drivers/gpu/drm/panel/panel-simple.c | 9 +- drivers/gpu/drm/virtio/virtgpu_ioctl.c | 3 + drivers/gpu/drm/virtio/virtgpu_vq.c | 2 + drivers/gpu/ipu-v3/ipu-ic.c | 2 +- drivers/hwtracing/intel_th/msu.c | 2 +- drivers/input/tablet/gtco.c | 20 +- drivers/isdn/hardware/mISDN/hfcsusb.c | 3 + drivers/mailbox/mailbox.c | 6 +- drivers/md/bcache/super.c | 2 +- drivers/md/dm-bufio.c | 4 +- drivers/media/dvb-frontends/tua6100.c | 22 +- drivers/media/i2c/Makefile | 2 +- drivers/media/i2c/{adv7511.c => adv7511-v4l2.c} | 5 + drivers/media/platform/coda/coda-bit.c | 9 +- drivers/media/platform/davinci/vpss.c | 5 + drivers/media/platform/marvell-ccic/mcam-core.c | 5 +- drivers/media/radio/radio-raremono.c | 30 +- drivers/media/radio/wl128x/fmdrv_v4l2.c | 3 + drivers/media/usb/cpia2/cpia2_usb.c | 3 +- drivers/media/usb/dvb-usb/dvb-usb-init.c | 7 +- drivers/media/v4l2-core/v4l2-ctrls.c | 9 +- drivers/memstick/core/memstick.c | 13 +- drivers/mfd/arizona-core.c | 2 +- drivers/mfd/mfd-core.c | 1 + drivers/net/bonding/bond_main.c | 37 ++- drivers/net/caif/caif_hsi.c | 2 +- drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c | 3 + drivers/net/ethernet/broadcom/genet/bcmgenet.c | 57 ++-- drivers/net/ethernet/freescale/fec_main.c | 6 +- drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c | 3 +- drivers/net/ethernet/intel/ixgbe/ixgbe_phy.h | 1 + drivers/net/ethernet/marvell/sky2.c | 7 + .../net/ethernet/stmicro/stmmac/dwmac1000_core.c | 6 + drivers/net/ethernet/xilinx/xilinx_axienet_main.c | 20 +- drivers/net/phy/phy_device.c | 6 + drivers/net/wireless/ath/ath10k/hw.c | 2 +- drivers/net/wireless/ath/ath10k/mac.c | 4 + drivers/net/wireless/ath/ath6kl/wmi.c | 10 +- drivers/net/wireless/ath/ath9k/hw.c | 32 +- drivers/net/wireless/ath/dfs_pattern_detector.c | 2 +- drivers/net/wireless/mediatek/mt7601u/dma.c | 54 +-- drivers/net/wireless/mediatek/mt7601u/tx.c | 4 +- drivers/pci/pci-sysfs.c | 2 +- drivers/pci/pci.c | 7 + drivers/phy/phy-rcar-gen2.c | 2 + drivers/pinctrl/pinctrl-rockchip.c | 1 + drivers/pps/pps.c | 8 + drivers/regulator/s2mps11.c | 4 +- drivers/s390/cio/qdio_main.c | 1 + drivers/staging/media/davinci_vpfe/vpfe_video.c | 3 + drivers/tty/serial/cpm_uart/cpm_uart_core.c | 17 +- drivers/tty/serial/digicolor-usart.c | 6 +- drivers/tty/serial/max310x.c | 51 +-- drivers/tty/serial/msm_serial.c | 4 + drivers/tty/serial/sh-sci.c | 22 +- drivers/usb/core/hub.c | 35 +- drivers/usb/gadget/function/f_fs.c | 6 +- drivers/usb/host/hwa-hc.c | 2 +- drivers/usb/host/pci-quirks.c | 31 +- drivers/vhost/net.c | 2 +- fs/9p/vfs_addr.c | 6 +- fs/ceph/caps.c | 7 +- fs/coda/file.c | 69 +++- fs/ecryptfs/crypto.c | 12 +- fs/exec.c | 2 +- fs/f2fs/segment.c | 5 + fs/nfs/inode.c | 1 + fs/nfs/nfs4file.c | 2 +- fs/nfs/nfs4proc.c | 41 ++- fs/nfsd/nfs4state.c | 11 +- fs/nfsd/nfssvc.c | 2 +- fs/open.c | 19 ++ include/linux/cred.h | 7 +- include/linux/elevator.h | 2 +- include/linux/rcupdate.h | 2 +- include/linux/sched.h | 4 +- include/net/tcp.h | 11 +- kernel/bpf/Makefile | 1 + kernel/cred.c | 21 +- kernel/fork.c | 2 +- kernel/locking/lockdep.c | 18 +- kernel/locking/lockdep_proc.c | 8 +- kernel/padata.c | 12 + kernel/pid_namespace.c | 2 +- kernel/sched/fair.c | 24 +- kernel/time/ntp.c | 4 +- kernel/time/timer_list.c | 36 +- kernel/trace/trace.c | 12 +- lib/reed_solomon/decode_rs.c | 18 +- lib/scatterlist.c | 9 +- mm/kmemleak.c | 2 +- mm/mmu_notifier.c | 2 +- mm/vmstat.c | 80 +++-- net/9p/trans_virtio.c | 8 +- net/batman-adv/translation-table.c | 2 + net/bluetooth/6lowpan.c | 14 +- net/bluetooth/hci_event.c | 5 + net/bluetooth/l2cap_core.c | 15 +- net/bluetooth/smp.c | 13 + net/bridge/br_multicast.c | 32 +- net/bridge/br_stp_bpdu.c | 3 +- net/core/neighbour.c | 2 + net/ipv4/devinet.c | 8 + net/ipv4/tcp.c | 2 + net/ipv6/ip6mr.c | 11 +- net/key/af_key.c | 8 +- net/netrom/af_netrom.c | 4 +- net/nfc/nci/data.c | 2 +- net/xfrm/xfrm_user.c | 19 ++ scripts/kallsyms.c | 3 + scripts/recordmcount.h | 3 +- sound/core/seq/seq_clientmgr.c | 11 +- sound/pci/hda/patch_conexant.c | 1 + sound/usb/line6/podhd.c | 2 +- tools/iio/iio_utils.c | 4 +- tools/perf/tests/mmap-thread-lookup.c | 2 +- tools/perf/tests/parse-events.c | 27 ++ tools/perf/util/evsel.c | 8 +- tools/power/cpupower/utils/cpufreq-set.c | 2 + 159 files changed, 1670 insertions(+), 789 deletions(-)
[ Upstream commit db13a5ba2732755cf13320f3987b77cf2a71e790 ]
While trying to get the uart with parity working I found setting even parity enabled odd parity insted. Fix the register settings to match the datasheet of AR9331.
A similar patch was created by 8devices, but not sent upstream. https://github.com/8devices/openwrt-8devices/commit/77c5586ade3bb72cda010afa...
Signed-off-by: Stefan Hellermann stefan@the2masters.de Signed-off-by: Paul Burton paul.burton@mips.com Cc: linux-mips@vger.kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- arch/mips/include/asm/mach-ath79/ar933x_uart.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/arch/mips/include/asm/mach-ath79/ar933x_uart.h b/arch/mips/include/asm/mach-ath79/ar933x_uart.h index c2917b39966b..bba2c8837951 100644 --- a/arch/mips/include/asm/mach-ath79/ar933x_uart.h +++ b/arch/mips/include/asm/mach-ath79/ar933x_uart.h @@ -27,8 +27,8 @@ #define AR933X_UART_CS_PARITY_S 0 #define AR933X_UART_CS_PARITY_M 0x3 #define AR933X_UART_CS_PARITY_NONE 0 -#define AR933X_UART_CS_PARITY_ODD 1 -#define AR933X_UART_CS_PARITY_EVEN 2 +#define AR933X_UART_CS_PARITY_ODD 2 +#define AR933X_UART_CS_PARITY_EVEN 3 #define AR933X_UART_CS_IF_MODE_S 2 #define AR933X_UART_CS_IF_MODE_M 0x3 #define AR933X_UART_CS_IF_MODE_NONE 0
[ Upstream commit 1196364f21ffe5d1e6d83cafd6a2edb89404a3ae ]
calc_vmlinuz_load_addr.c requires SZ_64K to be defined for alignment purposes. It included "../../../../include/linux/sizes.h" to define that size, however "sizes.h" tries to include <linux/const.h> which assumes linux system headers. These may not exist eg. the following error was encountered when building Linux for OpenWrt under macOS:
In file included from arch/mips/boot/compressed/calc_vmlinuz_load_addr.c:16: arch/mips/boot/compressed/../../../../include/linux/sizes.h:11:10: fatal error: 'linux/const.h' file not found ^~~~~~~~~~
Change makefile to force building on local linux headers instead of system headers. Also change eye-watering relative reference in include file spec.
Thanks to Jo-Philip Wich & Petr Štetiar for assistance in tracking this down & fixing.
Suggested-by: Jo-Philipp Wich jo@mein.io Signed-off-by: Petr Štetiar ynezz@true.cz Signed-off-by: Kevin Darbyshire-Bryant ldir@darbyshire-bryant.me.uk Signed-off-by: Paul Burton paul.burton@mips.com Cc: linux-mips@vger.kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- arch/mips/boot/compressed/Makefile | 2 ++ arch/mips/boot/compressed/calc_vmlinuz_load_addr.c | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-)
diff --git a/arch/mips/boot/compressed/Makefile b/arch/mips/boot/compressed/Makefile index d5bdee115f22..d4918a2bca1b 100644 --- a/arch/mips/boot/compressed/Makefile +++ b/arch/mips/boot/compressed/Makefile @@ -66,6 +66,8 @@ OBJCOPYFLAGS_piggy.o := --add-section=.image=$(obj)/vmlinux.bin.z \ $(obj)/piggy.o: $(obj)/dummy.o $(obj)/vmlinux.bin.z FORCE $(call if_changed,objcopy)
+HOSTCFLAGS_calc_vmlinuz_load_addr.o += $(LINUXINCLUDE) + # Calculate the load address of the compressed kernel image hostprogs-y := calc_vmlinuz_load_addr
diff --git a/arch/mips/boot/compressed/calc_vmlinuz_load_addr.c b/arch/mips/boot/compressed/calc_vmlinuz_load_addr.c index 542c3ede9722..d14f75ec8273 100644 --- a/arch/mips/boot/compressed/calc_vmlinuz_load_addr.c +++ b/arch/mips/boot/compressed/calc_vmlinuz_load_addr.c @@ -13,7 +13,7 @@ #include <stdint.h> #include <stdio.h> #include <stdlib.h> -#include "../../../../include/linux/sizes.h" +#include <linux/sizes.h>
int main(int argc, char *argv[]) {
[ Upstream commit 2b8066c3deb9140fdf258417a51479b2aeaa7622 ]
If probe() fails anywhere beyond the point where sdma_get_firmware() is called, then a kernel oops may occur.
Problematic sequence of events: 1. probe() calls sdma_get_firmware(), which schedules the firmware callback to run when firmware becomes available, using the sdma instance structure as the context 2. probe() encounters an error, which deallocates the sdma instance structure 3. firmware becomes available, firmware callback is called with deallocated sdma instance structure 4. use after free - kernel oops !
Solution: only attempt to load firmware when we're certain that probe() will succeed. This guarantees that the firmware callback's context will remain valid.
Note that the remove() path is unaffected by this issue: the firmware loader will increment the driver module's use count, ensuring that the module cannot be unloaded while the firmware callback is pending or running.
Signed-off-by: Sven Van Asbroeck TheSven73@gmail.com Reviewed-by: Robin Gong yibin.gong@nxp.com [vkoul: fixed braces for if condition] Signed-off-by: Vinod Koul vkoul@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/dma/imx-sdma.c | 48 ++++++++++++++++++++++++------------------ 1 file changed, 27 insertions(+), 21 deletions(-)
diff --git a/drivers/dma/imx-sdma.c b/drivers/dma/imx-sdma.c index 4054747af0cb..dd97dbf6618c 100644 --- a/drivers/dma/imx-sdma.c +++ b/drivers/dma/imx-sdma.c @@ -1786,27 +1786,6 @@ static int sdma_probe(struct platform_device *pdev) if (pdata && pdata->script_addrs) sdma_add_scripts(sdma, pdata->script_addrs);
- if (pdata) { - ret = sdma_get_firmware(sdma, pdata->fw_name); - if (ret) - dev_warn(&pdev->dev, "failed to get firmware from platform data\n"); - } else { - /* - * Because that device tree does not encode ROM script address, - * the RAM script in firmware is mandatory for device tree - * probe, otherwise it fails. - */ - ret = of_property_read_string(np, "fsl,sdma-ram-script-name", - &fw_name); - if (ret) - dev_warn(&pdev->dev, "failed to get firmware name\n"); - else { - ret = sdma_get_firmware(sdma, fw_name); - if (ret) - dev_warn(&pdev->dev, "failed to get firmware from device tree\n"); - } - } - sdma->dma_device.dev = &pdev->dev;
sdma->dma_device.device_alloc_chan_resources = sdma_alloc_chan_resources; @@ -1848,6 +1827,33 @@ static int sdma_probe(struct platform_device *pdev) of_node_put(spba_bus); }
+ /* + * Kick off firmware loading as the very last step: + * attempt to load firmware only if we're not on the error path, because + * the firmware callback requires a fully functional and allocated sdma + * instance. + */ + if (pdata) { + ret = sdma_get_firmware(sdma, pdata->fw_name); + if (ret) + dev_warn(&pdev->dev, "failed to get firmware from platform data\n"); + } else { + /* + * Because that device tree does not encode ROM script address, + * the RAM script in firmware is mandatory for device tree + * probe, otherwise it fails. + */ + ret = of_property_read_string(np, "fsl,sdma-ram-script-name", + &fw_name); + if (ret) { + dev_warn(&pdev->dev, "failed to get firmware name\n"); + } else { + ret = sdma_get_firmware(sdma, fw_name); + if (ret) + dev_warn(&pdev->dev, "failed to get firmware from device tree\n"); + } + } + return 0;
err_register:
[ Upstream commit 97354f2c432788e3163134df6bb144f4b6289d87 ]
Currently mac80211 do not support probe response template for mesh point. When WMI_SERVICE_BEACON_OFFLOAD is enabled, host driver tries to configure probe response template for mesh, but it fails because the interface type is not NL80211_IFTYPE_AP but NL80211_IFTYPE_MESH_POINT.
To avoid this failure, skip sending probe response template to firmware for mesh point.
Tested HW: WCN3990/QCA6174/QCA9984
Signed-off-by: Surabhi Vishnoi svishnoi@codeaurora.org Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/ath/ath10k/mac.c | 4 ++++ 1 file changed, 4 insertions(+)
diff --git a/drivers/net/wireless/ath/ath10k/mac.c b/drivers/net/wireless/ath/ath10k/mac.c index 398068ad0b62..5a0138c1c045 100644 --- a/drivers/net/wireless/ath/ath10k/mac.c +++ b/drivers/net/wireless/ath/ath10k/mac.c @@ -1502,6 +1502,10 @@ static int ath10k_mac_setup_prb_tmpl(struct ath10k_vif *arvif) if (arvif->vdev_type != WMI_VDEV_TYPE_AP) return 0;
+ /* For mesh, probe response and beacon share the same template */ + if (ieee80211_vif_is_mesh(vif)) + return 0; + prb = ieee80211_proberesp_get(hw, vif); if (!prb) { ath10k_warn(ar, "failed to get probe resp template from mac80211\n");
[ Upstream commit 2f90c7e5d09437a4d8d5546feaae9f1cf48cfbe1 ]
Right now, if an error is encountered during the SREV register read (i.e. an EIO in ath9k_regread()), that error code gets passed all the way to __ath9k_hw_init(), where it is visible during the "Chip rev not supported" message.
ath9k_htc 1-1.4:1.0: ath9k_htc: HTC initialized with 33 credits ath: phy2: Mac Chip Rev 0x0f.3 is not supported by this driver ath: phy2: Unable to initialize hardware; initialization status: -95 ath: phy2: Unable to initialize hardware; initialization status: -95 ath9k_htc: Failed to initialize the device
Check for -EIO explicitly in ath9k_hw_read_revisions() and return a boolean based on the success of the operation. Check for that in __ath9k_hw_init() and abort with a more debugging-friendly message if reading the revisions wasn't successful.
ath9k_htc 1-1.4:1.0: ath9k_htc: HTC initialized with 33 credits ath: phy2: Failed to read SREV register ath: phy2: Could not read hardware revision ath: phy2: Unable to initialize hardware; initialization status: -95 ath: phy2: Unable to initialize hardware; initialization status: -95 ath9k_htc: Failed to initialize the device
This helps when debugging by directly showing the first point of failure and it could prevent possible errors if a 0x0f.3 revision is ever supported.
Signed-off-by: Tim Schumacher timschumi@gmx.de Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/ath/ath9k/hw.c | 32 +++++++++++++++++++++-------- 1 file changed, 23 insertions(+), 9 deletions(-)
diff --git a/drivers/net/wireless/ath/ath9k/hw.c b/drivers/net/wireless/ath/ath9k/hw.c index 4435c7bbb625..d50e2e8bd998 100644 --- a/drivers/net/wireless/ath/ath9k/hw.c +++ b/drivers/net/wireless/ath/ath9k/hw.c @@ -250,8 +250,9 @@ void ath9k_hw_get_channel_centers(struct ath_hw *ah, /* Chip Revisions */ /******************/
-static void ath9k_hw_read_revisions(struct ath_hw *ah) +static bool ath9k_hw_read_revisions(struct ath_hw *ah) { + u32 srev; u32 val;
if (ah->get_mac_revision) @@ -267,25 +268,33 @@ static void ath9k_hw_read_revisions(struct ath_hw *ah) val = REG_READ(ah, AR_SREV); ah->hw_version.macRev = MS(val, AR_SREV_REVISION2); } - return; + return true; case AR9300_DEVID_AR9340: ah->hw_version.macVersion = AR_SREV_VERSION_9340; - return; + return true; case AR9300_DEVID_QCA955X: ah->hw_version.macVersion = AR_SREV_VERSION_9550; - return; + return true; case AR9300_DEVID_AR953X: ah->hw_version.macVersion = AR_SREV_VERSION_9531; - return; + return true; case AR9300_DEVID_QCA956X: ah->hw_version.macVersion = AR_SREV_VERSION_9561; - return; + return true; }
- val = REG_READ(ah, AR_SREV) & AR_SREV_ID; + srev = REG_READ(ah, AR_SREV); + + if (srev == -EIO) { + ath_err(ath9k_hw_common(ah), + "Failed to read SREV register"); + return false; + } + + val = srev & AR_SREV_ID;
if (val == 0xFF) { - val = REG_READ(ah, AR_SREV); + val = srev; ah->hw_version.macVersion = (val & AR_SREV_VERSION2) >> AR_SREV_TYPE2_S; ah->hw_version.macRev = MS(val, AR_SREV_REVISION2); @@ -304,6 +313,8 @@ static void ath9k_hw_read_revisions(struct ath_hw *ah) if (ah->hw_version.macVersion == AR_SREV_VERSION_5416_PCIE) ah->is_pciexpress = true; } + + return true; }
/************************************/ @@ -556,7 +567,10 @@ static int __ath9k_hw_init(struct ath_hw *ah) struct ath_common *common = ath9k_hw_common(ah); int r = 0;
- ath9k_hw_read_revisions(ah); + if (!ath9k_hw_read_revisions(ah)) { + ath_err(common, "Could not read hardware revisions"); + return -EOPNOTSUPP; + }
switch (ah->hw_version.macVersion) { case AR_SREV_VERSION_5416_PCI:
[ Upstream commit 5d6751eaff672ea77642e74e92e6c0ac7f9709ab ]
The "ev->traffic_class" and "reply->ac" variables come from the network and they're used as an offset into the wmi->stream_exist_for_ac[] array. Those variables are u8 so they can be 0-255 but the stream_exist_for_ac[] array only has WMM_NUM_AC (4) elements. We need to add a couple bounds checks to prevent array overflows.
I also modified one existing check from "if (traffic_class > 3) {" to "if (traffic_class >= WMM_NUM_AC) {" just to make them all consistent.
Fixes: bdcd81707973 (" Add ath6kl cleaned up driver") Signed-off-by: Dan Carpenter dan.carpenter@oracle.com Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/ath/ath6kl/wmi.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-)
diff --git a/drivers/net/wireless/ath/ath6kl/wmi.c b/drivers/net/wireless/ath/ath6kl/wmi.c index a5e1de75a4a3..b2ec254f154e 100644 --- a/drivers/net/wireless/ath/ath6kl/wmi.c +++ b/drivers/net/wireless/ath/ath6kl/wmi.c @@ -1178,6 +1178,10 @@ static int ath6kl_wmi_pstream_timeout_event_rx(struct wmi *wmi, u8 *datap, return -EINVAL;
ev = (struct wmi_pstream_timeout_event *) datap; + if (ev->traffic_class >= WMM_NUM_AC) { + ath6kl_err("invalid traffic class: %d\n", ev->traffic_class); + return -EINVAL; + }
/* * When the pstream (fat pipe == AC) timesout, it means there were @@ -1519,6 +1523,10 @@ static int ath6kl_wmi_cac_event_rx(struct wmi *wmi, u8 *datap, int len, return -EINVAL;
reply = (struct wmi_cac_event *) datap; + if (reply->ac >= WMM_NUM_AC) { + ath6kl_err("invalid AC: %d\n", reply->ac); + return -EINVAL; + }
if ((reply->cac_indication == CAC_INDICATION_ADMISSION_RESP) && (reply->status_code != IEEE80211_TSPEC_STATUS_ADMISS_ACCEPTED)) { @@ -2631,7 +2639,7 @@ int ath6kl_wmi_delete_pstream_cmd(struct wmi *wmi, u8 if_idx, u8 traffic_class, u16 active_tsids = 0; int ret;
- if (traffic_class > 3) { + if (traffic_class >= WMM_NUM_AC) { ath6kl_err("invalid traffic class: %d\n", traffic_class); return -EINVAL; }
[ Upstream commit d8792393a783158cbb2c39939cb897dc5e5299b6 ]
Increase pulse width range from 1-2usec to 0-4usec. During data traffic HW occasionally fails detecting radar pulses, so that SW cannot get enough radar reports to achieve the success rate.
Tested ath10k hw and fw: * QCA9888(10.4-3.5.1-00052) * QCA4019(10.4-3.2.1.1-00017) * QCA9984(10.4-3.6-00104) * QCA988X(10.2.4-1.0-00041)
Tested ath9k hw: AR9300
Tested-by: Tamizh chelvam tamizhr@codeaurora.org Signed-off-by: Tamizh chelvam tamizhr@codeaurora.org Signed-off-by: Anilkumar Kolli akolli@codeaurora.org Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/ath/dfs_pattern_detector.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/net/wireless/ath/dfs_pattern_detector.c b/drivers/net/wireless/ath/dfs_pattern_detector.c index 2303ef96299d..0835828ffed7 100644 --- a/drivers/net/wireless/ath/dfs_pattern_detector.c +++ b/drivers/net/wireless/ath/dfs_pattern_detector.c @@ -111,7 +111,7 @@ static const struct radar_detector_specs jp_radar_ref_types[] = { JP_PATTERN(0, 0, 1, 1428, 1428, 1, 18, 29, false), JP_PATTERN(1, 2, 3, 3846, 3846, 1, 18, 29, false), JP_PATTERN(2, 0, 1, 1388, 1388, 1, 18, 50, false), - JP_PATTERN(3, 1, 2, 4000, 4000, 1, 18, 50, false), + JP_PATTERN(3, 0, 4, 4000, 4000, 1, 18, 50, false), JP_PATTERN(4, 0, 5, 150, 230, 1, 23, 50, false), JP_PATTERN(5, 6, 10, 200, 500, 1, 16, 50, false), JP_PATTERN(6, 11, 20, 200, 500, 1, 12, 50, false),
[ Upstream commit 17f78dd1bd624a4dd78ed5db3284a63ee807fcc3 ]
A handler for BATADV_TVLV_ROAM was being registered when the translation-table was initialized, but not unregistered when the translation-table was freed. Unregister it.
Fixes: 122edaa05940 ("batman-adv: tvlv - convert roaming adv packet to use tvlv unicast packets") Reported-by: syzbot+d454a826e670502484b8@syzkaller.appspotmail.com Signed-off-by: Jeremy Sowden jeremy@azazel.net Signed-off-by: Sven Eckelmann sven@narfation.org Signed-off-by: Simon Wunderlich sw@simonwunderlich.de Signed-off-by: Sasha Levin sashal@kernel.org --- net/batman-adv/translation-table.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/net/batman-adv/translation-table.c b/net/batman-adv/translation-table.c index f2079acb555d..ffd49b40e76a 100644 --- a/net/batman-adv/translation-table.c +++ b/net/batman-adv/translation-table.c @@ -3158,6 +3158,8 @@ static void batadv_tt_purge(struct work_struct *work)
void batadv_tt_free(struct batadv_priv *bat_priv) { + batadv_tvlv_handler_unregister(bat_priv, BATADV_TVLV_ROAM, 1); + batadv_tvlv_container_unregister(bat_priv, BATADV_TVLV_TT, 1); batadv_tvlv_handler_unregister(bat_priv, BATADV_TVLV_TT, 1);
[ Upstream commit 6cf97230cd5f36b7665099083272595c55d72be7 ]
dvb_usb_device_exit() frees and uses the device name in that order. Fix by storing the name in a buffer before freeing it.
Signed-off-by: Oliver Neukum oneukum@suse.com Reported-by: syzbot+26ec41e9f788b3eba396@syzkaller.appspotmail.com Signed-off-by: Sean Young sean@mess.org Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/usb/dvb-usb/dvb-usb-init.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
diff --git a/drivers/media/usb/dvb-usb/dvb-usb-init.c b/drivers/media/usb/dvb-usb/dvb-usb-init.c index 1adf325012f7..97a89ef7e4c1 100644 --- a/drivers/media/usb/dvb-usb/dvb-usb-init.c +++ b/drivers/media/usb/dvb-usb/dvb-usb-init.c @@ -286,12 +286,15 @@ EXPORT_SYMBOL(dvb_usb_device_init); void dvb_usb_device_exit(struct usb_interface *intf) { struct dvb_usb_device *d = usb_get_intfdata(intf); - const char *name = "generic DVB-USB module"; + const char *default_name = "generic DVB-USB module"; + char name[40];
usb_set_intfdata(intf, NULL); if (d != NULL && d->desc != NULL) { - name = d->desc->name; + strscpy(name, d->desc->name, sizeof(name)); dvb_usb_exit(d); + } else { + strscpy(name, default_name, sizeof(name)); } info("%s successfully deinitialized and disconnected.", name);
[ Upstream commit 3e03e792865ae48b8cfc69a0b4d65f02f467389f ]
Selftests report the following:
[ 2.984845] alg: skcipher: cbc-aes-talitos encryption test failed (wrong output IV) on test vector 0, cfg="in-place" [ 2.995377] 00000000: 3d af ba 42 9d 9e b4 30 b4 22 da 80 2c 9f ac 41 [ 3.032673] alg: skcipher: cbc-des-talitos encryption test failed (wrong output IV) on test vector 0, cfg="in-place" [ 3.043185] 00000000: fe dc ba 98 76 54 32 10 [ 3.063238] alg: skcipher: cbc-3des-talitos encryption test failed (wrong output IV) on test vector 0, cfg="in-place" [ 3.073818] 00000000: 7d 33 88 93 0f 93 b2 42
This above dumps show that the actual output IV is indeed the input IV. This is due to the IV not being copied back into the request.
This patch fixes that.
Signed-off-by: Christophe Leroy christophe.leroy@c-s.fr Reviewed-by: Horia Geantă horia.geanta@nxp.com Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/crypto/talitos.c | 4 ++++ 1 file changed, 4 insertions(+)
diff --git a/drivers/crypto/talitos.c b/drivers/crypto/talitos.c index 62ce93568e11..a000c2667392 100644 --- a/drivers/crypto/talitos.c +++ b/drivers/crypto/talitos.c @@ -1446,11 +1446,15 @@ static void ablkcipher_done(struct device *dev, int err) { struct ablkcipher_request *areq = context; + struct crypto_ablkcipher *cipher = crypto_ablkcipher_reqtfm(areq); + struct talitos_ctx *ctx = crypto_ablkcipher_ctx(cipher); + unsigned int ivsize = crypto_ablkcipher_ivsize(cipher); struct talitos_edesc *edesc;
edesc = container_of(desc, struct talitos_edesc, desc);
common_nonsnoop_unmap(dev, edesc, areq); + memcpy(areq->info, ctx->iv, ivsize);
kfree(edesc);
[ Upstream commit 0c7aa32966dab0b8a7424e1b34c7f206817953ec ]
The commit d790b7eda953 ("[media] vb2-dma-sg: move dma_(un)map_sg here") left dma_desc_nent unset. It previously contained the number of DMA descriptors as returned from dma_map_sg().
We can now (since the commit referred to above) obtain the same value from the sg_table and drop dma_desc_nent altogether.
Tested on OLPC XO-1.75 machine. Doesn't affect the OLPC XO-1's Cafe driver, since that one doesn't do DMA.
[mchehab+samsung@kernel.org: fix a checkpatch warning]
Fixes: d790b7eda953 ("[media] vb2-dma-sg: move dma_(un)map_sg here") Signed-off-by: Lubomir Rintel lkundrak@v3.sk Signed-off-by: Sakari Ailus sakari.ailus@linux.intel.com Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/marvell-ccic/mcam-core.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/drivers/media/platform/marvell-ccic/mcam-core.c b/drivers/media/platform/marvell-ccic/mcam-core.c index aa2b44041d3f..22fe771d4dd2 100644 --- a/drivers/media/platform/marvell-ccic/mcam-core.c +++ b/drivers/media/platform/marvell-ccic/mcam-core.c @@ -209,7 +209,6 @@ struct mcam_vb_buffer { struct list_head queue; struct mcam_dma_desc *dma_desc; /* Descriptor virtual address */ dma_addr_t dma_desc_pa; /* Descriptor physical address */ - int dma_desc_nent; /* Number of mapped descriptors */ };
static inline struct mcam_vb_buffer *vb_to_mvb(struct vb2_v4l2_buffer *vb) @@ -616,9 +615,11 @@ static void mcam_dma_contig_done(struct mcam_camera *cam, int frame) static void mcam_sg_next_buffer(struct mcam_camera *cam) { struct mcam_vb_buffer *buf; + struct sg_table *sg_table;
buf = list_first_entry(&cam->buffers, struct mcam_vb_buffer, queue); list_del_init(&buf->queue); + sg_table = vb2_dma_sg_plane_desc(&buf->vb_buf.vb2_buf, 0); /* * Very Bad Not Good Things happen if you don't clear * C1_DESC_ENA before making any descriptor changes. @@ -626,7 +627,7 @@ static void mcam_sg_next_buffer(struct mcam_camera *cam) mcam_reg_clear_bit(cam, REG_CTRL1, C1_DESC_ENA); mcam_reg_write(cam, REG_DMA_DESC_Y, buf->dma_desc_pa); mcam_reg_write(cam, REG_DESC_LEN_Y, - buf->dma_desc_nent*sizeof(struct mcam_dma_desc)); + sg_table->nents * sizeof(struct mcam_dma_desc)); mcam_reg_write(cam, REG_DESC_LEN_U, 0); mcam_reg_write(cam, REG_DESC_LEN_V, 0); mcam_reg_set_bit(cam, REG_CTRL1, C1_DESC_ENA);
[ Upstream commit e08f0761234def47961d3252eac09ccedfe4c6a0 ]
In case ioremap fails, the fix returns -ENOMEM to avoid NULL pointer dereference.
Signed-off-by: Kangjie Lu kjlu@umn.edu Acked-by: Lad, Prabhakar prabhakar.csengg@gmail.com Reviewed-by: Mukesh Ojha mojha@codeaurora.org Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/davinci/vpss.c | 5 +++++ 1 file changed, 5 insertions(+)
diff --git a/drivers/media/platform/davinci/vpss.c b/drivers/media/platform/davinci/vpss.c index fce86f17dffc..c2c68988e38a 100644 --- a/drivers/media/platform/davinci/vpss.c +++ b/drivers/media/platform/davinci/vpss.c @@ -523,6 +523,11 @@ static int __init vpss_init(void) return -EBUSY;
oper_cfg.vpss_regs_base2 = ioremap(VPSS_CLK_CTRL, 4); + if (unlikely(!oper_cfg.vpss_regs_base2)) { + release_mem_region(VPSS_CLK_CTRL, 4); + return -ENOMEM; + } + writel(VPSS_CLK_CTRL_VENCCLKEN | VPSS_CLK_CTRL_DACCLKEN, oper_cfg.vpss_regs_base2);
[ Upstream commit 9463c445590091202659cdfdd44b236acadfbd84 ]
In case we don't use a given address entry we need to clear it because it could contain previous values that are no longer valid.
Found out while running stmmac selftests.
Signed-off-by: Jose Abreu joabreu@synopsys.com Cc: Joao Pinto jpinto@synopsys.com Cc: David S. Miller davem@davemloft.net Cc: Giuseppe Cavallaro peppe.cavallaro@st.com Cc: Alexandre Torgue alexandre.torgue@st.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c | 6 ++++++ 1 file changed, 6 insertions(+)
diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c index 371a669d69fd..1df84c8de9d7 100644 --- a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c +++ b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c @@ -187,6 +187,12 @@ static void dwmac1000_set_filter(struct mac_device_info *hw, GMAC_ADDR_LOW(reg)); reg++; } + + while (reg <= perfect_addr_number) { + writel(0, ioaddr + GMAC_ADDR_HIGH(reg)); + writel(0, ioaddr + GMAC_ADDR_LOW(reg)); + reg++; + } }
#ifdef FRAME_FILTER_DEBUG
[ Upstream commit f9070dc94542093fd516ae4ccea17ef46a4362c5 ]
The locking in force_sig_info is not prepared to deal with a task that exits or execs (as sighand may change). The is not a locking problem in force_sig as force_sig is only built to handle synchronous exceptions.
Further the function force_sig_info changes the signal state if the signal is ignored, or blocked or if SIGNAL_UNKILLABLE will prevent the delivery of the signal. The signal SIGKILL can not be ignored and can not be blocked and SIGNAL_UNKILLABLE won't prevent it from being delivered.
So using force_sig rather than send_sig for SIGKILL is confusing and pointless.
Because it won't impact the sending of the signal and and because using force_sig is wrong, replace force_sig with send_sig.
Cc: Daniel Lezcano daniel.lezcano@free.fr Cc: Serge Hallyn serge@hallyn.com Cc: Oleg Nesterov oleg@redhat.com Fixes: cf3f89214ef6 ("pidns: add reboot_pid_ns() to handle the reboot syscall") Signed-off-by: "Eric W. Biederman" ebiederm@xmission.com Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/pid_namespace.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/kernel/pid_namespace.c b/kernel/pid_namespace.c index 567ecc826bc8..6353372801f2 100644 --- a/kernel/pid_namespace.c +++ b/kernel/pid_namespace.c @@ -325,7 +325,7 @@ int reboot_pid_ns(struct pid_namespace *pid_ns, int cmd) }
read_lock(&tasklist_lock); - force_sig(SIGKILL, pid_ns->child_reaper); + send_sig(SIGKILL, pid_ns->child_reaper, 1); read_unlock(&tasklist_lock);
do_exit(0);
[ Upstream commit 7c80eb1c7e2b8420477fbc998971d62a648035d9 ]
In both functions, if pfkey_xfrm_policy2msg failed we leaked the newly allocated sk_buff. Free it on error.
Fixes: 55569ce256ce ("Fix conversion between IPSEC_MODE_xxx and XFRM_MODE_xxx.") Reported-by: syzbot+4f0529365f7f2208d9f0@syzkaller.appspotmail.com Signed-off-by: Jeremy Sowden jeremy@azazel.net Signed-off-by: Steffen Klassert steffen.klassert@secunet.com Signed-off-by: Sasha Levin sashal@kernel.org --- net/key/af_key.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-)
diff --git a/net/key/af_key.c b/net/key/af_key.c index 3ba903ff2bb0..36db179d848e 100644 --- a/net/key/af_key.c +++ b/net/key/af_key.c @@ -2463,8 +2463,10 @@ static int key_pol_get_resp(struct sock *sk, struct xfrm_policy *xp, const struc goto out; } err = pfkey_xfrm_policy2msg(out_skb, xp, dir); - if (err < 0) + if (err < 0) { + kfree_skb(out_skb); goto out; + }
out_hdr = (struct sadb_msg *) out_skb->data; out_hdr->sadb_msg_version = hdr->sadb_msg_version; @@ -2717,8 +2719,10 @@ static int dump_sp(struct xfrm_policy *xp, int dir, int count, void *ptr) return PTR_ERR(out_skb);
err = pfkey_xfrm_policy2msg(out_skb, xp, dir); - if (err < 0) + if (err < 0) { + kfree_skb(out_skb); return err; + }
out_hdr = (struct sadb_msg *) out_skb->data; out_hdr->sadb_msg_version = pfk->dump.msg_version;
[ Upstream commit b38ff4075a80b4da5cb2202d7965332ca0efb213 ]
Family of src/dst can be different from family of selector src/dst. Use xfrm selector family to validate address prefix length, while verifying new sa from userspace.
Validated patch with this command: ip xfrm state add src 1.1.6.1 dst 1.1.6.2 proto esp spi 4260196 \ reqid 20004 mode tunnel aead "rfc4106(gcm(aes))" \ 0x1111016400000000000000000000000044440001 128 \ sel src 1011:1:4::2/128 sel dst 1021:1:4::2/128 dev Port5
Fixes: 07bf7908950a ("xfrm: Validate address prefix lengths in the xfrm selector.") Signed-off-by: Anirudh Gupta anirudh.gupta@sophos.com Acked-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Steffen Klassert steffen.klassert@secunet.com Signed-off-by: Sasha Levin sashal@kernel.org --- net/xfrm/xfrm_user.c | 16 ++++++++++++++++ 1 file changed, 16 insertions(+)
diff --git a/net/xfrm/xfrm_user.c b/net/xfrm/xfrm_user.c index b04c03043976..10fda9a39cc2 100644 --- a/net/xfrm/xfrm_user.c +++ b/net/xfrm/xfrm_user.c @@ -150,6 +150,22 @@ static int verify_newsa_info(struct xfrm_usersa_info *p,
err = -EINVAL; switch (p->family) { + case AF_INET: + break; + + case AF_INET6: +#if IS_ENABLED(CONFIG_IPV6) + break; +#else + err = -EAFNOSUPPORT; + goto out; +#endif + + default: + goto out; + } + + switch (p->sel.family) { case AF_INET: if (p->sel.prefixlen_d > 32 || p->sel.prefixlen_s > 32) goto out;
[ Upstream commit 6995a659101bd4effa41cebb067f9dc18d77520d ]
Fix to avoid possible memory leak if the decoder initialization got failed.Free the allocated memory for file handle object before return in case decoder initialization fails.
Signed-off-by: Shailendra Verma shailendra.v@samsung.com Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/staging/media/davinci_vpfe/vpfe_video.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/drivers/staging/media/davinci_vpfe/vpfe_video.c b/drivers/staging/media/davinci_vpfe/vpfe_video.c index 0fdff91624fd..43474f562b43 100644 --- a/drivers/staging/media/davinci_vpfe/vpfe_video.c +++ b/drivers/staging/media/davinci_vpfe/vpfe_video.c @@ -406,6 +406,9 @@ static int vpfe_open(struct file *file) /* If decoder is not initialized. initialize it */ if (!video->initialized && vpfe_update_pipe_state(video)) { mutex_unlock(&video->lock); + v4l2_fh_del(&handle->vfh); + v4l2_fh_exit(&handle->vfh); + kfree(handle); return -ENODEV; } /* Increment device users counter */
[ Upstream commit 82c76aca81187b3d28a6fb3062f6916450ce955e ]
In general, we don't want MAC drivers calling phy_attach_direct with the net_device being NULL. Add checks against this in all the functions calling it: phy_attach() and phy_connect_direct().
Signed-off-by: Ioana Ciornei ioana.ciornei@nxp.com Suggested-by: Andrew Lunn andrew@lunn.ch Reviewed-by: Andrew Lunn andrew@lunn.ch Reviewed-by: Florian Fainelli f.fainelli@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/phy/phy_device.c | 6 ++++++ 1 file changed, 6 insertions(+)
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c index 70f26b30729c..c6a87834723d 100644 --- a/drivers/net/phy/phy_device.c +++ b/drivers/net/phy/phy_device.c @@ -472,6 +472,9 @@ int phy_connect_direct(struct net_device *dev, struct phy_device *phydev, { int rc;
+ if (!dev) + return -EINVAL; + rc = phy_attach_direct(dev, phydev, phydev->dev_flags, interface); if (rc) return rc; @@ -704,6 +707,9 @@ struct phy_device *phy_attach(struct net_device *dev, const char *bus_id, struct device *d; int rc;
+ if (!dev) + return ERR_PTR(-EINVAL); + /* Search the list of PHY devices on the mdio bus for the * PHY with the requested name */
[ Upstream commit 621ccc6cc5f8d6730b740d31d4818227866c93c9 ]
Rename _P to _P_VAL and _R to _R_VAL to avoid global namespace conflicts:
drivers/media/dvb-frontends/tua6100.c: In function ‘tua6100_set_params’: drivers/media/dvb-frontends/tua6100.c:79: warning: "_P" redefined #define _P 32
In file included from ./include/acpi/platform/aclinux.h:54, from ./include/acpi/platform/acenv.h:152, from ./include/acpi/acpi.h:22, from ./include/linux/acpi.h:34, from ./include/linux/i2c.h:17, from drivers/media/dvb-frontends/tua6100.h:30, from drivers/media/dvb-frontends/tua6100.c:32: ./include/linux/ctype.h:14: note: this is the location of the previous definition #define _P 0x10 /* punct */
Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/dvb-frontends/tua6100.c | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-)
diff --git a/drivers/media/dvb-frontends/tua6100.c b/drivers/media/dvb-frontends/tua6100.c index 029384d1fddd..7a3e91cda5df 100644 --- a/drivers/media/dvb-frontends/tua6100.c +++ b/drivers/media/dvb-frontends/tua6100.c @@ -80,8 +80,8 @@ static int tua6100_set_params(struct dvb_frontend *fe) struct i2c_msg msg1 = { .addr = priv->i2c_address, .flags = 0, .buf = reg1, .len = 4 }; struct i2c_msg msg2 = { .addr = priv->i2c_address, .flags = 0, .buf = reg2, .len = 3 };
-#define _R 4 -#define _P 32 +#define _R_VAL 4 +#define _P_VAL 32 #define _ri 4000000
// setup register 0 @@ -96,14 +96,14 @@ static int tua6100_set_params(struct dvb_frontend *fe) else reg1[1] = 0x0c;
- if (_P == 64) + if (_P_VAL == 64) reg1[1] |= 0x40; if (c->frequency >= 1525000) reg1[1] |= 0x80;
// register 2 - reg2[1] = (_R >> 8) & 0x03; - reg2[2] = _R; + reg2[1] = (_R_VAL >> 8) & 0x03; + reg2[2] = _R_VAL; if (c->frequency < 1455000) reg2[1] |= 0x1c; else if (c->frequency < 1630000) @@ -115,18 +115,18 @@ static int tua6100_set_params(struct dvb_frontend *fe) * The N divisor ratio (note: c->frequency is in kHz, but we * need it in Hz) */ - prediv = (c->frequency * _R) / (_ri / 1000); - div = prediv / _P; + prediv = (c->frequency * _R_VAL) / (_ri / 1000); + div = prediv / _P_VAL; reg1[1] |= (div >> 9) & 0x03; reg1[2] = div >> 1; reg1[3] = (div << 7); - priv->frequency = ((div * _P) * (_ri / 1000)) / _R; + priv->frequency = ((div * _P_VAL) * (_ri / 1000)) / _R_VAL;
// Finally, calculate and store the value for A - reg1[3] |= (prediv - (div*_P)) & 0x7f; + reg1[3] |= (prediv - (div*_P_VAL)) & 0x7f;
-#undef _R -#undef _P +#undef _R_VAL +#undef _P_VAL #undef _ri
if (fe->ops.i2c_gate_ctrl)
[ Upstream commit d9349850e188b8b59e5322fda17ff389a1c0cd7d ]
The sequence
static DEFINE_WW_CLASS(test_ww_class);
struct ww_acquire_ctx ww_ctx; struct ww_mutex ww_lock_a; struct ww_mutex ww_lock_b; struct ww_mutex ww_lock_c; struct mutex lock_c;
ww_acquire_init(&ww_ctx, &test_ww_class);
ww_mutex_init(&ww_lock_a, &test_ww_class); ww_mutex_init(&ww_lock_b, &test_ww_class); ww_mutex_init(&ww_lock_c, &test_ww_class);
mutex_init(&lock_c);
ww_mutex_lock(&ww_lock_a, &ww_ctx);
mutex_lock(&lock_c);
ww_mutex_lock(&ww_lock_b, &ww_ctx); ww_mutex_lock(&ww_lock_c, &ww_ctx);
mutex_unlock(&lock_c); (*)
ww_mutex_unlock(&ww_lock_c); ww_mutex_unlock(&ww_lock_b); ww_mutex_unlock(&ww_lock_a);
ww_acquire_fini(&ww_ctx); (**)
will trigger the following error in __lock_release() when calling mutex_release() at **:
DEBUG_LOCKS_WARN_ON(depth <= 0)
The problem is that the hlock merging happening at * updates the references for test_ww_class incorrectly to 3 whereas it should've updated it to 4 (representing all the instances for ww_ctx and ww_lock_[abc]).
Fix this by updating the references during merging correctly taking into account that we can have non-zero references (both for the hlock that we merge into another hlock or for the hlock we are merging into).
Signed-off-by: Imre Deak imre.deak@intel.com Signed-off-by: Peter Zijlstra (Intel) peterz@infradead.org Cc: =?UTF-8?q?Ville=20Syrj=C3=A4l=C3=A4?= ville.syrjala@linux.intel.com Cc: Linus Torvalds torvalds@linux-foundation.org Cc: Peter Zijlstra peterz@infradead.org Cc: Thomas Gleixner tglx@linutronix.de Cc: Will Deacon will.deacon@arm.com Link: https://lkml.kernel.org/r/20190524201509.9199-2-imre.deak@intel.com Signed-off-by: Ingo Molnar mingo@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/locking/lockdep.c | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-)
diff --git a/kernel/locking/lockdep.c b/kernel/locking/lockdep.c index 774ab79d3ec7..f2df5f86af28 100644 --- a/kernel/locking/lockdep.c +++ b/kernel/locking/lockdep.c @@ -3128,17 +3128,17 @@ static int __lock_acquire(struct lockdep_map *lock, unsigned int subclass, if (depth) { hlock = curr->held_locks + depth - 1; if (hlock->class_idx == class_idx && nest_lock) { - if (hlock->references) { - /* - * Check: unsigned int references:12, overflow. - */ - if (DEBUG_LOCKS_WARN_ON(hlock->references == (1 << 12)-1)) - return 0; + if (!references) + references++;
+ if (!hlock->references) hlock->references++; - } else { - hlock->references = 2; - } + + hlock->references += references; + + /* Overflow */ + if (DEBUG_LOCKS_WARN_ON(hlock->references < references)) + return 0;
return 1; }
[ Upstream commit 69fbb3f47327d959830c94bf31893972b8c8f700 ]
X-Originating-IP: [10.175.113.25] X-CFilter-Loop: Reflected The fm_v4l2_init_video_device() forget to unregister v4l2/video device in the error path, it could lead to UAF issue, eg,
BUG: KASAN: use-after-free in atomic64_read include/asm-generic/atomic-instrumented.h:836 [inline] BUG: KASAN: use-after-free in atomic_long_read include/asm-generic/atomic-long.h:28 [inline] BUG: KASAN: use-after-free in __mutex_unlock_slowpath+0x92/0x690 kernel/locking/mutex.c:1206 Read of size 8 at addr ffff8881e84a7c70 by task v4l_id/3659
CPU: 1 PID: 3659 Comm: v4l_id Not tainted 5.1.0 #8 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.10.2-1ubuntu1 04/01/2014 Call Trace: __dump_stack lib/dump_stack.c:77 [inline] dump_stack+0xa9/0x10e lib/dump_stack.c:113 print_address_description+0x65/0x270 mm/kasan/report.c:187 kasan_report+0x149/0x18d mm/kasan/report.c:317 atomic64_read include/asm-generic/atomic-instrumented.h:836 [inline] atomic_long_read include/asm-generic/atomic-long.h:28 [inline] __mutex_unlock_slowpath+0x92/0x690 kernel/locking/mutex.c:1206 fm_v4l2_fops_open+0xac/0x120 [fm_drv] v4l2_open+0x191/0x390 [videodev] chrdev_open+0x20d/0x570 fs/char_dev.c:417 do_dentry_open+0x700/0xf30 fs/open.c:777 do_last fs/namei.c:3416 [inline] path_openat+0x7c4/0x2a90 fs/namei.c:3532 do_filp_open+0x1a5/0x2b0 fs/namei.c:3563 do_sys_open+0x302/0x490 fs/open.c:1069 do_syscall_64+0x9f/0x450 arch/x86/entry/common.c:290 entry_SYSCALL_64_after_hwframe+0x49/0xbe RIP: 0033:0x7f8180c17c8e ... Allocated by task 3642: set_track mm/kasan/common.c:87 [inline] __kasan_kmalloc.constprop.3+0xa0/0xd0 mm/kasan/common.c:497 fm_drv_init+0x13/0x1000 [fm_drv] do_one_initcall+0xbc/0x47d init/main.c:901 do_init_module+0x1b5/0x547 kernel/module.c:3456 load_module+0x6405/0x8c10 kernel/module.c:3804 __do_sys_finit_module+0x162/0x190 kernel/module.c:3898 do_syscall_64+0x9f/0x450 arch/x86/entry/common.c:290 entry_SYSCALL_64_after_hwframe+0x49/0xbe
Freed by task 3642: set_track mm/kasan/common.c:87 [inline] __kasan_slab_free+0x130/0x180 mm/kasan/common.c:459 slab_free_hook mm/slub.c:1429 [inline] slab_free_freelist_hook mm/slub.c:1456 [inline] slab_free mm/slub.c:3003 [inline] kfree+0xe1/0x270 mm/slub.c:3958 fm_drv_init+0x1e6/0x1000 [fm_drv] do_one_initcall+0xbc/0x47d init/main.c:901 do_init_module+0x1b5/0x547 kernel/module.c:3456 load_module+0x6405/0x8c10 kernel/module.c:3804 __do_sys_finit_module+0x162/0x190 kernel/module.c:3898 do_syscall_64+0x9f/0x450 arch/x86/entry/common.c:290 entry_SYSCALL_64_after_hwframe+0x49/0xbe
Add relevant unregister functions to fix it.
Cc: Hans Verkuil hans.verkuil@cisco.com Reported-by: Hulk Robot hulkci@huawei.com Signed-off-by: Kefeng Wang wangkefeng.wang@huawei.com Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/radio/wl128x/fmdrv_v4l2.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/drivers/media/radio/wl128x/fmdrv_v4l2.c b/drivers/media/radio/wl128x/fmdrv_v4l2.c index fb42f0fd0c1f..add26eac1677 100644 --- a/drivers/media/radio/wl128x/fmdrv_v4l2.c +++ b/drivers/media/radio/wl128x/fmdrv_v4l2.c @@ -553,6 +553,7 @@ int fm_v4l2_init_video_device(struct fmdev *fmdev, int radio_nr)
/* Register with V4L2 subsystem as RADIO device */ if (video_register_device(&gradio_dev, VFL_TYPE_RADIO, radio_nr)) { + v4l2_device_unregister(&fmdev->v4l2_dev); fmerr("Could not register video device\n"); return -ENOMEM; } @@ -566,6 +567,8 @@ int fm_v4l2_init_video_device(struct fmdev *fmdev, int radio_nr) if (ret < 0) { fmerr("(fmdev): Can't init ctrl handler\n"); v4l2_ctrl_handler_free(&fmdev->ctrl_handler); + video_unregister_device(fmdev->radio_dev); + v4l2_device_unregister(&fmdev->v4l2_dev); return -EBUSY; }
[ Upstream commit 04507c0a9385cc8280f794a36bfff567c8cc1042 ]
To set frequency on specific cpus using cpupower, following syntax can be used : cpupower -c #i frequency-set -f #f -r
While setting frequency using cpupower frequency-set command, if we use '-r' option, it is expected to set frequency for all cpus related to cpu #i. But it is observed to be missing the last cpu in related cpu list. This patch fixes the problem.
Signed-off-by: Abhishek Goel huntbag@linux.vnet.ibm.com Reviewed-by: Thomas Renninger trenn@suse.de Signed-off-by: Shuah Khan skhan@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- tools/power/cpupower/utils/cpufreq-set.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/tools/power/cpupower/utils/cpufreq-set.c b/tools/power/cpupower/utils/cpufreq-set.c index 0fbd1a22c0a9..2f86935094ca 100644 --- a/tools/power/cpupower/utils/cpufreq-set.c +++ b/tools/power/cpupower/utils/cpufreq-set.c @@ -306,6 +306,8 @@ int cmd_freq_set(int argc, char **argv) bitmask_setbit(cpus_chosen, cpus->cpu); cpus = cpus->next; } + /* Set the last cpu in related cpus list */ + bitmask_setbit(cpus_chosen, cpus->cpu); cpufreq_put_related_cpus(cpus); } }
[ Upstream commit a19a0582363b9a5f8ba812f34f1b8df394898780 ]
When a valid MAC address is not found the current messages are shown:
fec 2188000.ethernet (unnamed net_device) (uninitialized): Invalid MAC address: 00:00:00:00:00:00 fec 2188000.ethernet (unnamed net_device) (uninitialized): Using random MAC address: aa:9f:25:eb:7e:aa
Since the network device has not been registered at this point, it is better to use dev_err()/dev_info() instead, which will provide cleaner log messages like these:
fec 2188000.ethernet: Invalid MAC address: 00:00:00:00:00:00 fec 2188000.ethernet: Using random MAC address: aa:9f:25:eb:7e:aa
Tested on a imx6dl-pico-pi board.
Signed-off-by: Fabio Estevam festevam@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/ethernet/freescale/fec_main.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/drivers/net/ethernet/freescale/fec_main.c b/drivers/net/ethernet/freescale/fec_main.c index ae8e4fc22e7b..0ee164d09f39 100644 --- a/drivers/net/ethernet/freescale/fec_main.c +++ b/drivers/net/ethernet/freescale/fec_main.c @@ -1699,10 +1699,10 @@ static void fec_get_mac(struct net_device *ndev) */ if (!is_valid_ether_addr(iap)) { /* Report it and use a random ethernet address instead */ - netdev_err(ndev, "Invalid MAC address: %pM\n", iap); + dev_err(&fep->pdev->dev, "Invalid MAC address: %pM\n", iap); eth_hw_addr_random(ndev); - netdev_info(ndev, "Using random MAC address: %pM\n", - ndev->dev_addr); + dev_info(&fep->pdev->dev, "Using random MAC address: %pM\n", + ndev->dev_addr); return; }
[ Upstream commit 7de44285c1f69ccfbe8be1d6a16fcd956681fee6 ]
It is possible that the interrupt handler fires and frees up space in the TX ring in between checking for sufficient TX ring space and stopping the TX queue in axienet_start_xmit. If this happens, the queue wake from the interrupt handler will occur before the queue is stopped, causing a lost wakeup and the adapter's transmit hanging.
To avoid this, after stopping the queue, check again whether there is sufficient space in the TX ring. If so, wake up the queue again.
Signed-off-by: Robert Hancock hancock@sedsystems.ca Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- .../net/ethernet/xilinx/xilinx_axienet_main.c | 20 ++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-)
diff --git a/drivers/net/ethernet/xilinx/xilinx_axienet_main.c b/drivers/net/ethernet/xilinx/xilinx_axienet_main.c index 58ba579793f8..f1e969128a4e 100644 --- a/drivers/net/ethernet/xilinx/xilinx_axienet_main.c +++ b/drivers/net/ethernet/xilinx/xilinx_axienet_main.c @@ -613,6 +613,10 @@ static void axienet_start_xmit_done(struct net_device *ndev)
ndev->stats.tx_packets += packets; ndev->stats.tx_bytes += size; + + /* Matches barrier in axienet_start_xmit */ + smp_mb(); + netif_wake_queue(ndev); }
@@ -667,9 +671,19 @@ static int axienet_start_xmit(struct sk_buff *skb, struct net_device *ndev) cur_p = &lp->tx_bd_v[lp->tx_bd_tail];
if (axienet_check_tx_bd_space(lp, num_frag)) { - if (!netif_queue_stopped(ndev)) - netif_stop_queue(ndev); - return NETDEV_TX_BUSY; + if (netif_queue_stopped(ndev)) + return NETDEV_TX_BUSY; + + netif_stop_queue(ndev); + + /* Matches barrier in axienet_start_xmit_done */ + smp_mb(); + + /* Space might have just been freed - check again */ + if (axienet_check_tx_bd_space(lp, num_frag)) + return NETDEV_TX_BUSY; + + netif_wake_queue(ndev); }
if (skb->ip_summed == CHECKSUM_PARTIAL) {
[ Upstream commit 04310324c6f482921c071444833e70fe861b73d9 ]
When a CQ-enabled device uses QEBSM for SBAL state inspection, get_buf_states() can return the PENDING state for an Output Queue. get_outbound_buffer_frontier() isn't prepared for this, and any PENDING buffer will permanently stall all further completion processing on this Queue.
This isn't a concern for non-QEBSM devices, as get_buf_states() for such devices will manually turn PENDING buffers into EMPTY ones.
Fixes: 104ea556ee7f ("qdio: support asynchronous delivery of storage blocks") Signed-off-by: Julian Wiedmann jwi@linux.ibm.com Signed-off-by: Heiko Carstens heiko.carstens@de.ibm.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/s390/cio/qdio_main.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/s390/cio/qdio_main.c b/drivers/s390/cio/qdio_main.c index d64b401f3d05..8d7fc3b6ca63 100644 --- a/drivers/s390/cio/qdio_main.c +++ b/drivers/s390/cio/qdio_main.c @@ -752,6 +752,7 @@ static int get_outbound_buffer_frontier(struct qdio_q *q)
switch (state) { case SLSB_P_OUTPUT_EMPTY: + case SLSB_P_OUTPUT_PENDING: /* the adapter got it */ DBF_DEV_EVENT(DBF_INFO, q->irq_ptr, "out empty:%1d %02x", q->nr, count);
[ Upstream commit 53fe307dfd309e425b171f6272d64296a54f4dff ]
Command
# perf test -Fv 6
fails with error
running test 100 'kvm-s390:kvm_s390_create_vm' failed to parse event 'kvm-s390:kvm_s390_create_vm', err -1, str 'unknown tracepoint' event syntax error: 'kvm-s390:kvm_s390_create_vm' ___ unknown tracepoint
when the kvm module is not loaded or not built in.
Fix this by adding a valid function which tests if the module is loaded. Loaded modules (or builtin KVM support) have a directory named /sys/kernel/debug/tracing/events/kvm-s390 for this tracepoint.
Check for existence of this directory.
Signed-off-by: Thomas Richter tmricht@linux.ibm.com Reviewed-by: Christian Borntraeger borntraeger@de.ibm.com Cc: Heiko Carstens heiko.carstens@de.ibm.com Cc: Hendrik Brueckner brueckner@linux.vnet.ibm.com Link: http://lkml.kernel.org/r/20190604053504.43073-1-tmricht@linux.ibm.com Signed-off-by: Arnaldo Carvalho de Melo acme@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- tools/perf/tests/parse-events.c | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+)
diff --git a/tools/perf/tests/parse-events.c b/tools/perf/tests/parse-events.c index 54af2f2e2ee4..1a35ab044c11 100644 --- a/tools/perf/tests/parse-events.c +++ b/tools/perf/tests/parse-events.c @@ -12,6 +12,32 @@ #define PERF_TP_SAMPLE_TYPE (PERF_SAMPLE_RAW | PERF_SAMPLE_TIME | \ PERF_SAMPLE_CPU | PERF_SAMPLE_PERIOD)
+#if defined(__s390x__) +/* Return true if kvm module is available and loaded. Test this + * and retun success when trace point kvm_s390_create_vm + * exists. Otherwise this test always fails. + */ +static bool kvm_s390_create_vm_valid(void) +{ + char *eventfile; + bool rc = false; + + eventfile = get_events_file("kvm-s390"); + + if (eventfile) { + DIR *mydir = opendir(eventfile); + + if (mydir) { + rc = true; + closedir(mydir); + } + put_events_file(eventfile); + } + + return rc; +} +#endif + static int test__checkevent_tracepoint(struct perf_evlist *evlist) { struct perf_evsel *evsel = perf_evlist__first(evlist); @@ -1561,6 +1587,7 @@ static struct evlist_test test__events[] = { { .name = "kvm-s390:kvm_s390_create_vm", .check = test__checkevent_tracepoint, + .valid = kvm_s390_create_vm_valid, .id = 100, }, #endif
[ Upstream commit 64ea3e9094a1f13b96c33244a3fb3a0f45690bd2 ]
Commit 384ebe1c2849 ("gpio/omap: Add DT support to GPIO driver") added the register definition tables to the gpio-omap driver. Subsequently to that commit, commit 4e962e8998cc ("gpio/omap: remove cpu_is_omapxxxx() checks from *_runtime_resume()") added definitions for irqstatus_raw* registers to the legacy OMAP4 definitions, but missed the DT definitions.
This causes an unintentional change of behaviour for the 1.101 errata workaround on OMAP4 platforms. Fix this oversight.
Fixes: 4e962e8998cc ("gpio/omap: remove cpu_is_omapxxxx() checks from *_runtime_resume()") Signed-off-by: Russell King rmk+kernel@armlinux.org.uk Signed-off-by: Grygorii Strashko grygorii.strashko@ti.com Tested-by: Tony Lindgren tony@atomide.com Signed-off-by: Linus Walleij linus.walleij@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/gpio/gpio-omap.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/drivers/gpio/gpio-omap.c b/drivers/gpio/gpio-omap.c index c8c49b1d5f9f..f23136825a6e 100644 --- a/drivers/gpio/gpio-omap.c +++ b/drivers/gpio/gpio-omap.c @@ -1611,6 +1611,8 @@ static struct omap_gpio_reg_offs omap4_gpio_regs = { .clr_dataout = OMAP4_GPIO_CLEARDATAOUT, .irqstatus = OMAP4_GPIO_IRQSTATUS0, .irqstatus2 = OMAP4_GPIO_IRQSTATUS1, + .irqstatus_raw0 = OMAP4_GPIO_IRQSTATUSRAW0, + .irqstatus_raw1 = OMAP4_GPIO_IRQSTATUSRAW1, .irqenable = OMAP4_GPIO_IRQSTATUSSET0, .irqenable2 = OMAP4_GPIO_IRQSTATUSSET1, .set_irqenable = OMAP4_GPIO_IRQSTATUSSET0,
[ Upstream commit c859e0d479b3b4f6132fc12637c51e01492f31f6 ]
Documentation states:
NOTE: There must be a correlation between the wake-up enable and interrupt-enable registers. If a GPIO pin has a wake-up configured on it, it must also have the corresponding interrupt enabled (on one of the two interrupt lines).
Ensure that this condition is always satisfied by enabling the detection events after enabling the interrupt, and disabling the detection before disabling the interrupt. This ensures interrupt/wakeup events can not happen until both the wakeup and interrupt enables correlate.
If we do any clearing, clear between the interrupt enable/disable and trigger setting.
Signed-off-by: Russell King rmk+kernel@armlinux.org.uk Signed-off-by: Grygorii Strashko grygorii.strashko@ti.com Tested-by: Tony Lindgren tony@atomide.com Signed-off-by: Linus Walleij linus.walleij@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/gpio/gpio-omap.c | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-)
diff --git a/drivers/gpio/gpio-omap.c b/drivers/gpio/gpio-omap.c index f23136825a6e..6e65c02baad1 100644 --- a/drivers/gpio/gpio-omap.c +++ b/drivers/gpio/gpio-omap.c @@ -821,9 +821,9 @@ static void omap_gpio_irq_shutdown(struct irq_data *d)
raw_spin_lock_irqsave(&bank->lock, flags); bank->irq_usage &= ~(BIT(offset)); - omap_set_gpio_irqenable(bank, offset, 0); - omap_clear_gpio_irqstatus(bank, offset); omap_set_gpio_triggering(bank, offset, IRQ_TYPE_NONE); + omap_clear_gpio_irqstatus(bank, offset); + omap_set_gpio_irqenable(bank, offset, 0); if (!LINE_USED(bank->mod_usage, offset)) omap_clear_gpio_debounce(bank, offset); omap_disable_gpio_module(bank, offset); @@ -865,8 +865,8 @@ static void omap_gpio_mask_irq(struct irq_data *d) unsigned long flags;
raw_spin_lock_irqsave(&bank->lock, flags); - omap_set_gpio_irqenable(bank, offset, 0); omap_set_gpio_triggering(bank, offset, IRQ_TYPE_NONE); + omap_set_gpio_irqenable(bank, offset, 0); raw_spin_unlock_irqrestore(&bank->lock, flags); }
@@ -878,9 +878,6 @@ static void omap_gpio_unmask_irq(struct irq_data *d) unsigned long flags;
raw_spin_lock_irqsave(&bank->lock, flags); - if (trigger) - omap_set_gpio_triggering(bank, offset, trigger); - omap_set_gpio_irqenable(bank, offset, 1);
/* @@ -888,9 +885,13 @@ static void omap_gpio_unmask_irq(struct irq_data *d) * is cleared, thus after the handler has run. OMAP4 needs this done * after enabing the interrupt to clear the wakeup status. */ - if (bank->level_mask & BIT(offset)) + if (bank->regs->leveldetect0 && bank->regs->wkup_en && + trigger & (IRQ_TYPE_LEVEL_HIGH | IRQ_TYPE_LEVEL_LOW)) omap_clear_gpio_irqstatus(bank, offset);
+ if (trigger) + omap_set_gpio_triggering(bank, offset, trigger); + raw_spin_unlock_irqrestore(&bank->lock, flags); }
[ Upstream commit db057679de3e9e6a03c1bcd5aee09b0d25fd9f5b ]
On buses like SlimBus and SoundWire which does not support gather_writes yet in regmap, A bulk write on paged register would be silently ignored after programming page. This is because local variable 'ret' value in regmap_raw_write_impl() gets reset to 0 once page register is written successfully and the code below checks for 'ret' value to be -ENOTSUPP before linearising the write buffer to send to bus->write().
Fix this by resetting the 'ret' value to -ENOTSUPP in cases where gather_writes() is not supported or single register write is not possible.
Signed-off-by: Srinivas Kandagatla srinivas.kandagatla@linaro.org Signed-off-by: Mark Brown broonie@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/base/regmap/regmap.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/drivers/base/regmap/regmap.c b/drivers/base/regmap/regmap.c index fd377b956199..77cabde977ed 100644 --- a/drivers/base/regmap/regmap.c +++ b/drivers/base/regmap/regmap.c @@ -1358,6 +1358,8 @@ int _regmap_raw_write(struct regmap *map, unsigned int reg, map->format.reg_bytes + map->format.pad_bytes, val, val_len); + else + ret = -ENOTSUPP;
/* If that didn't work fall back on linearising by hand. */ if (ret == -ENOTSUPP) {
[ Upstream commit aee450cbe482a8c2f6fa5b05b178ef8b8ff107ca ]
Compiling kernel/bpf/core.c with W=1 causes a flood of warnings:
kernel/bpf/core.c:1198:65: warning: initialized field overwritten [-Woverride-init] 1198 | #define BPF_INSN_3_TBL(x, y, z) [BPF_##x | BPF_##y | BPF_##z] = true | ^~~~ kernel/bpf/core.c:1087:2: note: in expansion of macro 'BPF_INSN_3_TBL' 1087 | INSN_3(ALU, ADD, X), \ | ^~~~~~ kernel/bpf/core.c:1202:3: note: in expansion of macro 'BPF_INSN_MAP' 1202 | BPF_INSN_MAP(BPF_INSN_2_TBL, BPF_INSN_3_TBL), | ^~~~~~~~~~~~ kernel/bpf/core.c:1198:65: note: (near initialization for 'public_insntable[12]') 1198 | #define BPF_INSN_3_TBL(x, y, z) [BPF_##x | BPF_##y | BPF_##z] = true | ^~~~ kernel/bpf/core.c:1087:2: note: in expansion of macro 'BPF_INSN_3_TBL' 1087 | INSN_3(ALU, ADD, X), \ | ^~~~~~ kernel/bpf/core.c:1202:3: note: in expansion of macro 'BPF_INSN_MAP' 1202 | BPF_INSN_MAP(BPF_INSN_2_TBL, BPF_INSN_3_TBL), | ^~~~~~~~~~~~
98 copies of the above.
The attached patch silences the warnings, because we *know* we're overwriting the default initializer. That leaves bpf/core.c with only 6 other warnings, which become more visible in comparison.
Signed-off-by: Valdis Kletnieks valdis.kletnieks@vt.edu Acked-by: Andrii Nakryiko andriin@fb.com Signed-off-by: Daniel Borkmann daniel@iogearbox.net Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/bpf/Makefile | 1 + 1 file changed, 1 insertion(+)
diff --git a/kernel/bpf/Makefile b/kernel/bpf/Makefile index 13272582eee0..677991f29d66 100644 --- a/kernel/bpf/Makefile +++ b/kernel/bpf/Makefile @@ -1,4 +1,5 @@ obj-y := core.o +CFLAGS_core.o += $(call cc-disable-warning, override-init)
obj-$(CONFIG_BPF_SYSCALL) += syscall.o verifier.o inode.o helpers.o obj-$(CONFIG_BPF_SYSCALL) += hashtab.o arraymap.o
[ Upstream commit 6da9f775175e516fc7229ceaa9b54f8f56aa7924 ]
When debugging options are turned on, the rcu_read_lock() function might not be inlined. This results in lockdep's print_lock() function printing "rcu_read_lock+0x0/0x70" instead of rcu_read_lock()'s caller. For example:
[ 10.579995] ============================= [ 10.584033] WARNING: suspicious RCU usage [ 10.588074] 4.18.0.memcg_v2+ #1 Not tainted [ 10.593162] ----------------------------- [ 10.597203] include/linux/rcupdate.h:281 Illegal context switch in RCU read-side critical section! [ 10.606220] [ 10.606220] other info that might help us debug this: [ 10.606220] [ 10.614280] [ 10.614280] rcu_scheduler_active = 2, debug_locks = 1 [ 10.620853] 3 locks held by systemd/1: [ 10.624632] #0: (____ptrval____) (&type->i_mutex_dir_key#5){.+.+}, at: lookup_slow+0x42/0x70 [ 10.633232] #1: (____ptrval____) (rcu_read_lock){....}, at: rcu_read_lock+0x0/0x70 [ 10.640954] #2: (____ptrval____) (rcu_read_lock){....}, at: rcu_read_lock+0x0/0x70
These "rcu_read_lock+0x0/0x70" strings are not providing any useful information. This commit therefore forces inlining of the rcu_read_lock() function so that rcu_read_lock()'s caller is instead shown.
Signed-off-by: Waiman Long longman@redhat.com Signed-off-by: Paul E. McKenney paulmck@linux.ibm.com Signed-off-by: Sasha Levin sashal@kernel.org --- include/linux/rcupdate.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/include/linux/rcupdate.h b/include/linux/rcupdate.h index addd03641e1a..0a93e9d1708e 100644 --- a/include/linux/rcupdate.h +++ b/include/linux/rcupdate.h @@ -852,7 +852,7 @@ static inline void rcu_preempt_sleep_check(void) * read-side critical sections may be preempted and they may also block, but * only when acquiring spinlocks that are subject to priority inheritance. */ -static inline void rcu_read_lock(void) +static __always_inline void rcu_read_lock(void) { __rcu_read_lock(); __acquire(RCU);
[ Upstream commit b8d6d0079757cbd1b69724cfd1c08e2171c68cee ]
After commit b38ff4075a80, the following command does not work anymore: $ ip xfrm state add src 10.125.0.2 dst 10.125.0.1 proto esp spi 34 reqid 1 \ mode tunnel enc 'cbc(aes)' 0xb0abdba8b782ad9d364ec81e3a7d82a1 auth-trunc \ 'hmac(sha1)' 0xe26609ebd00acb6a4d51fca13e49ea78a72c73e6 96 flag align4
In fact, the selector is not mandatory, allow the user to provide an empty selector.
Fixes: b38ff4075a80 ("xfrm: Fix xfrm sel prefix length validation") CC: Anirudh Gupta anirudh.gupta@sophos.com Signed-off-by: Nicolas Dichtel nicolas.dichtel@6wind.com Acked-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Steffen Klassert steffen.klassert@secunet.com Signed-off-by: Sasha Levin sashal@kernel.org --- net/xfrm/xfrm_user.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/net/xfrm/xfrm_user.c b/net/xfrm/xfrm_user.c index 10fda9a39cc2..8cc2a9df84fd 100644 --- a/net/xfrm/xfrm_user.c +++ b/net/xfrm/xfrm_user.c @@ -166,6 +166,9 @@ static int verify_newsa_info(struct xfrm_usersa_info *p, }
switch (p->sel.family) { + case AF_UNSPEC: + break; + case AF_INET: if (p->sel.prefixlen_d > 32 || p->sel.prefixlen_s > 32) goto out;
[ Upstream commit fdbdd7e8580eac9bdafa532746c865644d125e34 ]
In which case it simply returns "unknown", like when it can't figure out the evsel->name value.
This makes this code more robust and fixes a problem in 'perf trace' where a NULL evsel was being passed to a routine that only used the evsel for printing its name when a invalid syscall id was passed.
Reported-by: Leo Yan leo.yan@linaro.org Cc: Adrian Hunter adrian.hunter@intel.com Cc: Jiri Olsa jolsa@kernel.org Cc: Namhyung Kim namhyung@kernel.org Link: https://lkml.kernel.org/n/tip-f30ztaasku3z935cn3ak3h53@git.kernel.org Signed-off-by: Arnaldo Carvalho de Melo acme@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- tools/perf/util/evsel.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/tools/perf/util/evsel.c b/tools/perf/util/evsel.c index 97fde9275f42..a8507fee654b 100644 --- a/tools/perf/util/evsel.c +++ b/tools/perf/util/evsel.c @@ -491,6 +491,9 @@ const char *perf_evsel__name(struct perf_evsel *evsel) { char bf[128];
+ if (!evsel) + goto out_unknown; + if (evsel->name) return evsel->name;
@@ -527,7 +530,10 @@ const char *perf_evsel__name(struct perf_evsel *evsel)
evsel->name = strdup(bf);
- return evsel->name ?: "unknown"; + if (evsel->name) + return evsel->name; +out_unknown: + return "unknown"; }
const char *perf_evsel__group_name(struct perf_evsel *evsel)
[ Upstream commit 098eadce3c622c07b328d0a43dda379b38cf7c5e ]
Vhost_net was known to suffer from HOL[1] issues which is not easy to fix. Several downstream disable the feature by default. What's more, the datapath was split and datacopy path got the support of batching and XDP support recently which makes it faster than zerocopy part for small packets transmission.
It looks to me that disable zerocopy by default is more appropriate. It cold be enabled by default again in the future if we fix the above issues.
[1] https://patchwork.kernel.org/patch/3787671/
Signed-off-by: Jason Wang jasowang@redhat.com Acked-by: Michael S. Tsirkin mst@redhat.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/vhost/net.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/vhost/net.c b/drivers/vhost/net.c index 645b2197930e..f46317135224 100644 --- a/drivers/vhost/net.c +++ b/drivers/vhost/net.c @@ -30,7 +30,7 @@
#include "vhost.h"
-static int experimental_zcopytx = 1; +static int experimental_zcopytx = 0; module_param(experimental_zcopytx, int, 0444); MODULE_PARM_DESC(experimental_zcopytx, "Enable Zero Copy TX;" " 1 -Enable; 0 - Disable");
[ Upstream commit 585fb3d93d32dbe89e718b85009f9c322cc554cd ]
In edac_create_csrow_object(), the reference to the object is not released when adding the device to the device hierarchy fails (device_add()). This may result in a memory leak.
Signed-off-by: Pan Bian bianpan2016@163.com Signed-off-by: Borislav Petkov bp@suse.de Reviewed-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Cc: James Morse james.morse@arm.com Cc: Mauro Carvalho Chehab mchehab@kernel.org Cc: linux-edac linux-edac@vger.kernel.org Link: https://lkml.kernel.org/r/1555554438-103953-1-git-send-email-bianpan2016@163... Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/edac/edac_mc_sysfs.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/drivers/edac/edac_mc_sysfs.c b/drivers/edac/edac_mc_sysfs.c index 3c8f19f5ac81..0c53f2d54765 100644 --- a/drivers/edac/edac_mc_sysfs.c +++ b/drivers/edac/edac_mc_sysfs.c @@ -426,6 +426,8 @@ static inline int nr_pages_per_csrow(struct csrow_info *csrow) static int edac_create_csrow_object(struct mem_ctl_info *mci, struct csrow_info *csrow, int index) { + int err; + csrow->dev.type = &csrow_attr_type; csrow->dev.bus = mci->bus; csrow->dev.groups = csrow_dev_groups; @@ -438,7 +440,11 @@ static int edac_create_csrow_object(struct mem_ctl_info *mci, edac_dbg(0, "creating (virtual) csrow node %s\n", dev_name(&csrow->dev));
- return device_add(&csrow->dev); + err = device_add(&csrow->dev); + if (err) + put_device(&csrow->dev); + + return err; }
/* Create a CSROW object under specifed edac_mc_device */
[ Upstream commit b2ce5617dad254230551feda3599f2cc68e53ad8 ]
When building with CONFIG_VIDEO_ADV7511 and CONFIG_DRM_I2C_ADV7511 enabled as loadable modules, we see the following warning:
drivers/gpu/drm/bridge/adv7511/adv7511.ko drivers/media/i2c/adv7511.ko
Rework so that the file is named adv7511-v4l2.c.
Signed-off-by: Anders Roxell anders.roxell@linaro.org Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/i2c/Makefile | 2 +- drivers/media/i2c/{adv7511.c => adv7511-v4l2.c} | 5 +++++ 2 files changed, 6 insertions(+), 1 deletion(-) rename drivers/media/i2c/{adv7511.c => adv7511-v4l2.c} (99%)
diff --git a/drivers/media/i2c/Makefile b/drivers/media/i2c/Makefile index 07db257abfc1..d5711def1fff 100644 --- a/drivers/media/i2c/Makefile +++ b/drivers/media/i2c/Makefile @@ -28,7 +28,7 @@ obj-$(CONFIG_VIDEO_ADV7393) += adv7393.o obj-$(CONFIG_VIDEO_ADV7604) += adv7604.o obj-$(CONFIG_VIDEO_ADV7842) += adv7842.o obj-$(CONFIG_VIDEO_AD9389B) += ad9389b.o -obj-$(CONFIG_VIDEO_ADV7511) += adv7511.o +obj-$(CONFIG_VIDEO_ADV7511) += adv7511-v4l2.o obj-$(CONFIG_VIDEO_VPX3220) += vpx3220.o obj-$(CONFIG_VIDEO_VS6624) += vs6624.o obj-$(CONFIG_VIDEO_BT819) += bt819.o diff --git a/drivers/media/i2c/adv7511.c b/drivers/media/i2c/adv7511-v4l2.c similarity index 99% rename from drivers/media/i2c/adv7511.c rename to drivers/media/i2c/adv7511-v4l2.c index c24839cfcc35..b35400e4e9af 100644 --- a/drivers/media/i2c/adv7511.c +++ b/drivers/media/i2c/adv7511-v4l2.c @@ -17,6 +17,11 @@ * SOFTWARE. */
+/* + * This file is named adv7511-v4l2.c so it doesn't conflict with the Analog + * Device ADV7511 (config fragment CONFIG_DRM_I2C_ADV7511). + */ +
#include <linux/kernel.h> #include <linux/module.h>
[ Upstream commit d897a4ab11dc8a9fda50d2eccc081a96a6385998 ]
Don't allow the TAI-UTC offset of the system clock to be set by adjtimex() to a value larger than 100000 seconds.
This prevents an overflow in the conversion to int, prevents the CLOCK_TAI clock from getting too far ahead of the CLOCK_REALTIME clock, and it is still large enough to allow leap seconds to be inserted at the maximum rate currently supported by the kernel (once per day) for the next ~270 years, however unlikely it is that someone can survive a catastrophic event which slowed down the rotation of the Earth so much.
Reported-by: Weikang shi swkhack@gmail.com Signed-off-by: Miroslav Lichvar mlichvar@redhat.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Cc: John Stultz john.stultz@linaro.org Cc: Prarit Bhargava prarit@redhat.com Cc: Richard Cochran richardcochran@gmail.com Cc: Stephen Boyd sboyd@kernel.org Link: https://lkml.kernel.org/r/20190618154713.20929-1-mlichvar@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/time/ntp.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/kernel/time/ntp.c b/kernel/time/ntp.c index 0e0dc5d89911..bbe767b1f454 100644 --- a/kernel/time/ntp.c +++ b/kernel/time/ntp.c @@ -39,6 +39,7 @@ static u64 tick_length_base; #define MAX_TICKADJ 500LL /* usecs */ #define MAX_TICKADJ_SCALED \ (((MAX_TICKADJ * NSEC_PER_USEC) << NTP_SCALE_SHIFT) / NTP_INTERVAL_FREQ) +#define MAX_TAI_OFFSET 100000
/* * phase-lock loop variables @@ -633,7 +634,8 @@ static inline void process_adjtimex_modes(struct timex *txc, time_constant = max(time_constant, 0l); }
- if (txc->modes & ADJ_TAI && txc->constant >= 0) + if (txc->modes & ADJ_TAI && + txc->constant >= 0 && txc->constant <= MAX_TAI_OFFSET) *time_tai = txc->constant;
if (txc->modes & ADJ_OFFSET)
[ Upstream commit a9314773a91a1d3b36270085246a6715a326ff00 ]
With CONFIG_PROC_FS=n the following warning is emitted:
kernel/time/timer_list.c:361:36: warning: unused variable 'timer_list_sops' [-Wunused-const-variable] static const struct seq_operations timer_list_sops = {
Add #ifdef guard around procfs specific code.
Signed-off-by: Nathan Huckleberry nhuck@google.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Reviewed-by: Nick Desaulniers ndesaulniers@google.com Cc: john.stultz@linaro.org Cc: sboyd@kernel.org Cc: clang-built-linux@googlegroups.com Link: https://github.com/ClangBuiltLinux/linux/issues/534 Link: https://lkml.kernel.org/r/20190614181604.112297-1-nhuck@google.com Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/time/timer_list.c | 36 +++++++++++++++++++----------------- 1 file changed, 19 insertions(+), 17 deletions(-)
diff --git a/kernel/time/timer_list.c b/kernel/time/timer_list.c index 1407ed20ea93..b7c5d230b4b2 100644 --- a/kernel/time/timer_list.c +++ b/kernel/time/timer_list.c @@ -299,23 +299,6 @@ static inline void timer_list_header(struct seq_file *m, u64 now) SEQ_printf(m, "\n"); }
-static int timer_list_show(struct seq_file *m, void *v) -{ - struct timer_list_iter *iter = v; - - if (iter->cpu == -1 && !iter->second_pass) - timer_list_header(m, iter->now); - else if (!iter->second_pass) - print_cpu(m, iter->cpu, iter->now); -#ifdef CONFIG_GENERIC_CLOCKEVENTS - else if (iter->cpu == -1 && iter->second_pass) - timer_list_show_tickdevices_header(m); - else - print_tickdevice(m, tick_get_device(iter->cpu), iter->cpu); -#endif - return 0; -} - void sysrq_timer_list_show(void) { u64 now = ktime_to_ns(ktime_get()); @@ -334,6 +317,24 @@ void sysrq_timer_list_show(void) return; }
+#ifdef CONFIG_PROC_FS +static int timer_list_show(struct seq_file *m, void *v) +{ + struct timer_list_iter *iter = v; + + if (iter->cpu == -1 && !iter->second_pass) + timer_list_header(m, iter->now); + else if (!iter->second_pass) + print_cpu(m, iter->cpu, iter->now); +#ifdef CONFIG_GENERIC_CLOCKEVENTS + else if (iter->cpu == -1 && iter->second_pass) + timer_list_show_tickdevices_header(m); + else + print_tickdevice(m, tick_get_device(iter->cpu), iter->cpu); +#endif + return 0; +} + static void *move_iter(struct timer_list_iter *iter, loff_t offset) { for (; offset; offset--) { @@ -405,3 +406,4 @@ static int __init init_timer_list_procfs(void) return 0; } __initcall(init_timer_list_procfs); +#endif
[ Upstream commit 2af22f3ec3ca452f1e79b967f634708ff01ced8a ]
Some Qualcomm Snapdragon based laptops built to run Microsoft Windows are clearly ACPI 5.1 based, given that that is the first ACPI revision that supports ARM, and introduced the FADT 'arm_boot_flags' field, which has a non-zero field on those systems.
So in these cases, infer from the ARM boot flags that the FADT must be 5.1 or later, and treat it as 5.1.
Acked-by: Sudeep Holla sudeep.holla@arm.com Tested-by: Lee Jones lee.jones@linaro.org Reviewed-by: Graeme Gregory graeme.gregory@linaro.org Acked-by: Lorenzo Pieralisi lorenzo.pieralisi@arm.com Acked-by: Hanjun Guo guohanjun@huawei.com Signed-off-by: Ard Biesheuvel ard.biesheuvel@linaro.org Signed-off-by: Catalin Marinas catalin.marinas@arm.com Signed-off-by: Sasha Levin sashal@kernel.org --- arch/arm64/kernel/acpi.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-)
diff --git a/arch/arm64/kernel/acpi.c b/arch/arm64/kernel/acpi.c index d1ce8e2f98b9..4d0577d09681 100644 --- a/arch/arm64/kernel/acpi.c +++ b/arch/arm64/kernel/acpi.c @@ -141,10 +141,14 @@ static int __init acpi_fadt_sanity_check(void) */ if (table->revision < 5 || (table->revision == 5 && fadt->minor_revision < 1)) { - pr_err("Unsupported FADT revision %d.%d, should be 5.1+\n", + pr_err(FW_BUG "Unsupported FADT revision %d.%d, should be 5.1+\n", table->revision, fadt->minor_revision); - ret = -EINVAL; - goto out; + + if (!fadt->arm_boot_flags) { + ret = -EINVAL; + goto out; + } + pr_err("FADT has ARM boot flags set, assuming 5.1\n"); }
if (!(fadt->flags & ACPI_FADT_HW_REDUCED)) {
[ Upstream commit 56d159a4ec6d8da7313aac6fcbb95d8fffe689ba ]
Sequence number handling assumed that the BIT processor frame number starts counting at 1, but this is not true for the MPEG-2 decoder, which starts at 0. Fix the sequence counter offset detection to handle this.
Signed-off-by: Philipp Zabel p.zabel@pengutronix.de Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/coda/coda-bit.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/drivers/media/platform/coda/coda-bit.c b/drivers/media/platform/coda/coda-bit.c index a4639813cf35..a7ed2dba7a0e 100644 --- a/drivers/media/platform/coda/coda-bit.c +++ b/drivers/media/platform/coda/coda-bit.c @@ -1581,6 +1581,7 @@ static int __coda_start_decoding(struct coda_ctx *ctx) coda_write(dev, 0, CODA_REG_BIT_BIT_STREAM_PARAM); return -ETIMEDOUT; } + ctx->sequence_offset = ~0U; ctx->initialized = 1;
/* Update kfifo out pointer from coda bitstream read pointer */ @@ -1971,7 +1972,9 @@ static void coda_finish_decode(struct coda_ctx *ctx) v4l2_err(&dev->v4l2_dev, "decoded frame index out of range: %d\n", decoded_idx); } else { - val = coda_read(dev, CODA_RET_DEC_PIC_FRAME_NUM) - 1; + val = coda_read(dev, CODA_RET_DEC_PIC_FRAME_NUM); + if (ctx->sequence_offset == -1) + ctx->sequence_offset = val; val -= ctx->sequence_offset; spin_lock_irqsave(&ctx->buffer_meta_lock, flags); if (!list_empty(&ctx->buffer_meta_list)) {
[ Upstream commit b3b7d96817cdb8b6fc353867705275dce8f41ccc ]
If no more frames are decoded in bitstream end mode, and a previously decoded frame has been returned, the firmware still increments the frame number. To avoid a sequence number mismatch after decoder restart, increment the sequence_offset correction parameter.
Signed-off-by: Philipp Zabel p.zabel@pengutronix.de Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/coda/coda-bit.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/drivers/media/platform/coda/coda-bit.c b/drivers/media/platform/coda/coda-bit.c index a7ed2dba7a0e..b19e70b83f4a 100644 --- a/drivers/media/platform/coda/coda-bit.c +++ b/drivers/media/platform/coda/coda-bit.c @@ -1967,6 +1967,9 @@ static void coda_finish_decode(struct coda_ctx *ctx) else if (ctx->display_idx < 0) ctx->hold = true; } else if (decoded_idx == -2) { + if (ctx->display_idx >= 0 && + ctx->display_idx < ctx->num_internal_frames) + ctx->sequence_offset++; /* no frame was decoded, we still return remaining buffers */ } else if (decoded_idx < 0 || decoded_idx >= ctx->num_internal_frames) { v4l2_err(&dev->v4l2_dev,
[ Upstream commit 4079e8ccabc3b6d1b503f2376123cb515d14921f ]
Do not schedule rx_tasklet when the usb dongle is disconnected. Moreover do not grub rx_lock in mt7601u_kill_rx since usb_poison_urb can run concurrently with urb completion and we can unlink urbs from rx ring in any order. This patch fixes the common kernel warning reported when the device is removed.
[ 24.921354] usb 3-14: USB disconnect, device number 7 [ 24.921593] ------------[ cut here ]------------ [ 24.921594] RX urb mismatch [ 24.921675] WARNING: CPU: 4 PID: 163 at drivers/net/wireless/mediatek/mt7601u/dma.c:200 mt7601u_complete_rx+0xcb/0xd0 [mt7601u] [ 24.921769] CPU: 4 PID: 163 Comm: kworker/4:2 Tainted: G OE 4.19.31-041931-generic #201903231635 [ 24.921770] Hardware name: To Be Filled By O.E.M. To Be Filled By O.E.M./Z97 Extreme4, BIOS P1.30 05/23/2014 [ 24.921782] Workqueue: usb_hub_wq hub_event [ 24.921797] RIP: 0010:mt7601u_complete_rx+0xcb/0xd0 [mt7601u] [ 24.921800] RSP: 0018:ffff9bd9cfd03d08 EFLAGS: 00010086 [ 24.921802] RAX: 0000000000000000 RBX: ffff9bd9bf043540 RCX: 0000000000000006 [ 24.921803] RDX: 0000000000000007 RSI: 0000000000000096 RDI: ffff9bd9cfd16420 [ 24.921804] RBP: ffff9bd9cfd03d28 R08: 0000000000000002 R09: 00000000000003a8 [ 24.921805] R10: 0000002f485fca34 R11: 0000000000000000 R12: ffff9bd9bf043c1c [ 24.921806] R13: ffff9bd9c62fa3c0 R14: 0000000000000082 R15: 0000000000000000 [ 24.921807] FS: 0000000000000000(0000) GS:ffff9bd9cfd00000(0000) knlGS:0000000000000000 [ 24.921808] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 24.921808] CR2: 00007fb2648b0000 CR3: 0000000142c0a004 CR4: 00000000001606e0 [ 24.921809] Call Trace: [ 24.921812] <IRQ> [ 24.921819] __usb_hcd_giveback_urb+0x8b/0x140 [ 24.921821] usb_hcd_giveback_urb+0xca/0xe0 [ 24.921828] xhci_giveback_urb_in_irq.isra.42+0x82/0xf0 [ 24.921834] handle_cmd_completion+0xe02/0x10d0 [ 24.921837] xhci_irq+0x274/0x4a0 [ 24.921838] xhci_msi_irq+0x11/0x20 [ 24.921851] __handle_irq_event_percpu+0x44/0x190 [ 24.921856] handle_irq_event_percpu+0x32/0x80 [ 24.921861] handle_irq_event+0x3b/0x5a [ 24.921867] handle_edge_irq+0x80/0x190 [ 24.921874] handle_irq+0x20/0x30 [ 24.921889] do_IRQ+0x4e/0xe0 [ 24.921891] common_interrupt+0xf/0xf [ 24.921892] </IRQ> [ 24.921900] RIP: 0010:usb_hcd_flush_endpoint+0x78/0x180 [ 24.921354] usb 3-14: USB disconnect, device number 7
Signed-off-by: Lorenzo Bianconi lorenzo@kernel.org Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/mediatek/mt7601u/dma.c | 33 +++++++++++---------- 1 file changed, 18 insertions(+), 15 deletions(-)
diff --git a/drivers/net/wireless/mediatek/mt7601u/dma.c b/drivers/net/wireless/mediatek/mt7601u/dma.c index 57a80cfa39b1..6ba30129a3d8 100644 --- a/drivers/net/wireless/mediatek/mt7601u/dma.c +++ b/drivers/net/wireless/mediatek/mt7601u/dma.c @@ -193,10 +193,23 @@ static void mt7601u_complete_rx(struct urb *urb) struct mt7601u_rx_queue *q = &dev->rx_q; unsigned long flags;
- spin_lock_irqsave(&dev->rx_lock, flags); + /* do no schedule rx tasklet if urb has been unlinked + * or the device has been removed + */ + switch (urb->status) { + case -ECONNRESET: + case -ESHUTDOWN: + case -ENOENT: + return; + default: + dev_err_ratelimited(dev->dev, "rx urb failed: %d\n", + urb->status); + /* fall through */ + case 0: + break; + }
- if (mt7601u_urb_has_error(urb)) - dev_err(dev->dev, "Error: RX urb failed:%d\n", urb->status); + spin_lock_irqsave(&dev->rx_lock, flags); if (WARN_ONCE(q->e[q->end].urb != urb, "RX urb mismatch")) goto out;
@@ -363,19 +376,9 @@ int mt7601u_dma_enqueue_tx(struct mt7601u_dev *dev, struct sk_buff *skb, static void mt7601u_kill_rx(struct mt7601u_dev *dev) { int i; - unsigned long flags;
- spin_lock_irqsave(&dev->rx_lock, flags); - - for (i = 0; i < dev->rx_q.entries; i++) { - int next = dev->rx_q.end; - - spin_unlock_irqrestore(&dev->rx_lock, flags); - usb_poison_urb(dev->rx_q.e[next].urb); - spin_lock_irqsave(&dev->rx_lock, flags); - } - - spin_unlock_irqrestore(&dev->rx_lock, flags); + for (i = 0; i < dev->rx_q.entries; i++) + usb_poison_urb(dev->rx_q.e[i].urb); }
static int mt7601u_submit_rx_buf(struct mt7601u_dev *dev,
[ Upstream commit bc53d3d777f81385c1bb08b07bd1c06450ecc2c1 ]
Without 'set -e', shell scripts continue running even after any error occurs. The missed 'set -e' is a typical bug in shell scripting.
For example, when a disk space shortage occurs while this script is running, it actually ends up with generating a truncated capflags.c.
Yet, mkcapflags.sh continues running and exits with 0. So, the build system assumes it has succeeded.
It will not be re-generated in the next invocation of Make since its timestamp is newer than that of any of the source files.
Add 'set -e' so that any error in this script is caught and propagated to the build system.
Since 9c2af1c7377a ("kbuild: add .DELETE_ON_ERROR special target"), make automatically deletes the target on any failure. So, the broken capflags.c will be deleted automatically.
Signed-off-by: Masahiro Yamada yamada.masahiro@socionext.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Cc: "H. Peter Anvin" hpa@zytor.com Cc: Borislav Petkov bp@alien8.de Link: https://lkml.kernel.org/r/20190625072622.17679-1-yamada.masahiro@socionext.c... Signed-off-by: Sasha Levin sashal@kernel.org --- arch/x86/kernel/cpu/mkcapflags.sh | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/arch/x86/kernel/cpu/mkcapflags.sh b/arch/x86/kernel/cpu/mkcapflags.sh index 6988c74409a8..711b74e0e623 100644 --- a/arch/x86/kernel/cpu/mkcapflags.sh +++ b/arch/x86/kernel/cpu/mkcapflags.sh @@ -3,6 +3,8 @@ # Generate the x86_cap/bug_flags[] arrays from include/asm/cpufeatures.h #
+set -e + IN=$1 OUT=$2
[ Upstream commit 23377c200b2eb48a60d0f228b2a2e75ed6ee6060 ]
When the device is disconnected while passing traffic it is possible to receive out of order urbs causing a memory leak since the skb linked to the current tx urb is not removed. Fix the issue deallocating the skb cleaning up the tx ring. Moreover this patch fixes the following kernel warning
[ 57.480771] usb 1-1: USB disconnect, device number 2 [ 57.483451] ------------[ cut here ]------------ [ 57.483462] TX urb mismatch [ 57.483481] WARNING: CPU: 1 PID: 32 at drivers/net/wireless/mediatek/mt7601u/dma.c:245 mt7601u_complete_tx+0x165/00 [ 57.483483] Modules linked in: [ 57.483496] CPU: 1 PID: 32 Comm: kworker/1:1 Not tainted 5.2.0-rc1+ #72 [ 57.483498] Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS 1.12.0-2.fc30 04/01/2014 [ 57.483502] Workqueue: usb_hub_wq hub_event [ 57.483507] RIP: 0010:mt7601u_complete_tx+0x165/0x1e0 [ 57.483510] Code: 8b b5 10 04 00 00 8b 8d 14 04 00 00 eb 8b 80 3d b1 cb e1 00 00 75 9e 48 c7 c7 a4 ea 05 82 c6 05 f [ 57.483513] RSP: 0000:ffffc900000a0d28 EFLAGS: 00010092 [ 57.483516] RAX: 000000000000000f RBX: ffff88802c0a62c0 RCX: ffffc900000a0c2c [ 57.483518] RDX: 0000000000000000 RSI: 0000000000000000 RDI: ffffffff810a8371 [ 57.483520] RBP: ffff88803ced6858 R08: 0000000000000000 R09: 0000000000000001 [ 57.483540] R10: 0000000000000002 R11: 0000000000000000 R12: 0000000000000046 [ 57.483542] R13: ffff88802c0a6c88 R14: ffff88803baab540 R15: ffff88803a0cc078 [ 57.483548] FS: 0000000000000000(0000) GS:ffff88803eb00000(0000) knlGS:0000000000000000 [ 57.483550] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 57.483552] CR2: 000055e7f6780100 CR3: 0000000028c86000 CR4: 00000000000006a0 [ 57.483554] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 [ 57.483556] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 [ 57.483559] Call Trace: [ 57.483561] <IRQ> [ 57.483565] __usb_hcd_giveback_urb+0x77/0xe0 [ 57.483570] xhci_giveback_urb_in_irq.isra.0+0x8b/0x140 [ 57.483574] handle_cmd_completion+0xf5b/0x12c0 [ 57.483577] xhci_irq+0x1f6/0x1810 [ 57.483581] ? lockdep_hardirqs_on+0x9e/0x180 [ 57.483584] ? _raw_spin_unlock_irq+0x24/0x30 [ 57.483588] __handle_irq_event_percpu+0x3a/0x260 [ 57.483592] handle_irq_event_percpu+0x1c/0x60 [ 57.483595] handle_irq_event+0x2f/0x4c [ 57.483599] handle_edge_irq+0x7e/0x1a0 [ 57.483603] handle_irq+0x17/0x20 [ 57.483607] do_IRQ+0x54/0x110 [ 57.483610] common_interrupt+0xf/0xf [ 57.483612] </IRQ>
Acked-by: Jakub Kicinski kubakici@wp.pl Signed-off-by: Lorenzo Bianconi lorenzo@kernel.org Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/mediatek/mt7601u/dma.c | 21 ++++++++++++++++----- drivers/net/wireless/mediatek/mt7601u/tx.c | 4 ++-- 2 files changed, 18 insertions(+), 7 deletions(-)
diff --git a/drivers/net/wireless/mediatek/mt7601u/dma.c b/drivers/net/wireless/mediatek/mt7601u/dma.c index 6ba30129a3d8..3d0b9324d5bf 100644 --- a/drivers/net/wireless/mediatek/mt7601u/dma.c +++ b/drivers/net/wireless/mediatek/mt7601u/dma.c @@ -241,14 +241,25 @@ static void mt7601u_complete_tx(struct urb *urb) struct sk_buff *skb; unsigned long flags;
- spin_lock_irqsave(&dev->tx_lock, flags); + switch (urb->status) { + case -ECONNRESET: + case -ESHUTDOWN: + case -ENOENT: + return; + default: + dev_err_ratelimited(dev->dev, "tx urb failed: %d\n", + urb->status); + /* fall through */ + case 0: + break; + }
- if (mt7601u_urb_has_error(urb)) - dev_err(dev->dev, "Error: TX urb failed:%d\n", urb->status); + spin_lock_irqsave(&dev->tx_lock, flags); if (WARN_ONCE(q->e[q->start].urb != urb, "TX urb mismatch")) goto out;
skb = q->e[q->start].skb; + q->e[q->start].skb = NULL; trace_mt_tx_dma_done(dev, skb);
__skb_queue_tail(&dev->tx_skb_done, skb); @@ -448,10 +459,10 @@ static void mt7601u_free_tx_queue(struct mt7601u_tx_queue *q) { int i;
- WARN_ON(q->used); - for (i = 0; i < q->entries; i++) { usb_poison_urb(q->e[i].urb); + if (q->e[i].skb) + mt7601u_tx_status(q->dev, q->e[i].skb); usb_free_urb(q->e[i].urb); } } diff --git a/drivers/net/wireless/mediatek/mt7601u/tx.c b/drivers/net/wireless/mediatek/mt7601u/tx.c index a0a33dc8f6bc..a1b6db2a8937 100644 --- a/drivers/net/wireless/mediatek/mt7601u/tx.c +++ b/drivers/net/wireless/mediatek/mt7601u/tx.c @@ -117,9 +117,9 @@ void mt7601u_tx_status(struct mt7601u_dev *dev, struct sk_buff *skb) info->status.rates[0].idx = -1; info->flags |= IEEE80211_TX_STAT_ACK;
- spin_lock(&dev->mac_lock); + spin_lock_bh(&dev->mac_lock); ieee80211_tx_status(dev->hw, skb); - spin_unlock(&dev->mac_lock); + spin_unlock_bh(&dev->mac_lock); }
static int mt7601u_skb_rooms(struct mt7601u_dev *dev, struct sk_buff *skb)
[ Upstream commit 011d4111c8c602ea829fa4917af1818eb0500a90 ]
Observed PCIE device wake up failed after ~120 iterations of soft-reboot test. The error message is "ath10k_pci 0000:01:00.0: failed to wake up device : -110"
The call trace as below: ath10k_pci_probe -> ath10k_pci_force_wake -> ath10k_pci_wake_wait -> ath10k_pci_is_awake
Once trigger the device to wake up, we will continuously check the RTC state until it returns RTC_STATE_V_ON or timeout.
But for QCA99x0 chips, we use wrong value for RTC_STATE_V_ON. Occasionally, we get 0x7 on the fist read, we thought as a failure case, but actually is the right value, also verified with the spec. So fix the issue by changing RTC_STATE_V_ON from 0x5 to 0x7, passed ~2000 iterations.
Tested HW: QCA9984
Signed-off-by: Miaoqing Pan miaoqing@codeaurora.org Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/ath/ath10k/hw.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/net/wireless/ath/ath10k/hw.c b/drivers/net/wireless/ath/ath10k/hw.c index 7b84d08a5154..12d6549e45a1 100644 --- a/drivers/net/wireless/ath/ath10k/hw.c +++ b/drivers/net/wireless/ath/ath10k/hw.c @@ -128,7 +128,7 @@ const struct ath10k_hw_values qca6174_values = { };
const struct ath10k_hw_values qca99x0_values = { - .rtc_state_val_on = 5, + .rtc_state_val_on = 7, .ce_count = 12, .msi_assign_ce_max = 12, .num_target_ce_config_wlan = 10,
[ Upstream commit 2034a42d1747fc1e1eeef2c6f1789c4d0762cb9c ]
The decoding of shortenend codes is broken. It only works as expected if there are no erasures.
When decoding with erasures, Lambda (the error and erasure locator polynomial) is initialized from the given erasure positions. The pad parameter is not accounted for by the initialisation code, and hence Lambda is initialized from incorrect erasure positions.
The fix is to adjust the erasure positions by the supplied pad.
Signed-off-by: Ferdinand Blomqvist ferdinand.blomqvist@gmail.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Link: https://lkml.kernel.org/r/20190620141039.9874-3-ferdinand.blomqvist@gmail.co... Signed-off-by: Sasha Levin sashal@kernel.org --- lib/reed_solomon/decode_rs.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/lib/reed_solomon/decode_rs.c b/lib/reed_solomon/decode_rs.c index 0ec3f257ffdf..8eed0f9ac495 100644 --- a/lib/reed_solomon/decode_rs.c +++ b/lib/reed_solomon/decode_rs.c @@ -99,9 +99,9 @@ if (no_eras > 0) { /* Init lambda to be the erasure locator polynomial */ lambda[1] = alpha_to[rs_modnn(rs, - prim * (nn - 1 - eras_pos[0]))]; + prim * (nn - 1 - (eras_pos[0] + pad)))]; for (i = 1; i < no_eras; i++) { - u = rs_modnn(rs, prim * (nn - 1 - eras_pos[i])); + u = rs_modnn(rs, prim * (nn - 1 - (eras_pos[i] + pad))); for (j = i + 1; j > 0; j--) { tmp = index_of[lambda[j - 1]]; if (tmp != nn) {
[ Upstream commit ef4d6a8556b637ad27c8c2a2cff1dda3da38e9a9 ]
Check if the syndrome provided by the caller is zero, and act accordingly.
Signed-off-by: Ferdinand Blomqvist ferdinand.blomqvist@gmail.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Link: https://lkml.kernel.org/r/20190620141039.9874-6-ferdinand.blomqvist@gmail.co... Signed-off-by: Sasha Levin sashal@kernel.org --- lib/reed_solomon/decode_rs.c | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-)
diff --git a/lib/reed_solomon/decode_rs.c b/lib/reed_solomon/decode_rs.c index 8eed0f9ac495..a5d313381539 100644 --- a/lib/reed_solomon/decode_rs.c +++ b/lib/reed_solomon/decode_rs.c @@ -42,8 +42,18 @@ BUG_ON(pad < 0 || pad >= nn);
/* Does the caller provide the syndrome ? */ - if (s != NULL) - goto decode; + if (s != NULL) { + for (i = 0; i < nroots; i++) { + /* The syndrome is in index form, + * so nn represents zero + */ + if (s[i] != nn) + goto decode; + } + + /* syndrome is zero, no errors to correct */ + return 0; + }
/* form the syndromes; i.e., evaluate data(x) at roots of * g(x) */
[ Upstream commit 655c91414579d7bb115a4f7898ee726fc18e0984 ]
Some transceivers may comply with SFF-8472 but not implement the Digital Diagnostic Monitoring (DDM) interface described in it. The existence of such area is specified by bit 6 of byte 92, set to 1 if implemented.
Currently, due to not checking this bit ixgbe fails trying to read SFP module's eeprom with the follow message:
ethtool -m enP51p1s0f0 Cannot get Module EEPROM data: Input/output error
Because it fails to read the additional 256 bytes in which it was assumed to exist the DDM data.
This issue was noticed using a Mellanox Passive DAC PN 01FT738. The eeprom data was confirmed by Mellanox as correct and present in other Passive DACs in from other manufacturers.
Signed-off-by: "Mauro S. M. Rodrigues" maurosr@linux.vnet.ibm.com Reviewed-by: Jesse Brandeburg jesse.brandeburg@intel.com Tested-by: Andrew Bowers andrewx.bowers@intel.com Signed-off-by: Jeff Kirsher jeffrey.t.kirsher@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c | 3 ++- drivers/net/ethernet/intel/ixgbe/ixgbe_phy.h | 1 + 2 files changed, 3 insertions(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c b/drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c index d681273bd39d..9d38634071a4 100644 --- a/drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c +++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_ethtool.c @@ -3133,7 +3133,8 @@ static int ixgbe_get_module_info(struct net_device *dev, page_swap = true; }
- if (sff8472_rev == IXGBE_SFF_SFF_8472_UNSUP || page_swap) { + if (sff8472_rev == IXGBE_SFF_SFF_8472_UNSUP || page_swap || + !(addr_mode & IXGBE_SFF_DDM_IMPLEMENTED)) { /* We have a SFP, but it does not support SFF-8472 */ modinfo->type = ETH_MODULE_SFF_8079; modinfo->eeprom_len = ETH_MODULE_SFF_8079_LEN; diff --git a/drivers/net/ethernet/intel/ixgbe/ixgbe_phy.h b/drivers/net/ethernet/intel/ixgbe/ixgbe_phy.h index 5abd66c84d00..7b7dc6d7d159 100644 --- a/drivers/net/ethernet/intel/ixgbe/ixgbe_phy.h +++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_phy.h @@ -70,6 +70,7 @@ #define IXGBE_SFF_SOFT_RS_SELECT_10G 0x8 #define IXGBE_SFF_SOFT_RS_SELECT_1G 0x0 #define IXGBE_SFF_ADDRESSING_MODE 0x4 +#define IXGBE_SFF_DDM_IMPLEMENTED 0x40 #define IXGBE_SFF_QSFP_DA_ACTIVE_CABLE 0x1 #define IXGBE_SFF_QSFP_DA_PASSIVE_CABLE 0x8 #define IXGBE_SFF_QSFP_CONNECTOR_NOT_SEPARABLE 0x23
[ Upstream commit d8655e7630dafa88bc37f101640e39c736399771 ]
Commit 9da21b1509d8 ("EDAC: Poll timeout cannot be zero, p2") assumes edac_mc_poll_msec to be unsigned long, but the type of the variable still remained as int. Setting edac_mc_poll_msec can trigger out-of-bounds write.
Reproducer:
# echo 1001 > /sys/module/edac_core/parameters/edac_mc_poll_msec
KASAN report:
BUG: KASAN: global-out-of-bounds in edac_set_poll_msec+0x140/0x150 Write of size 8 at addr ffffffffb91b2d00 by task bash/1996
CPU: 1 PID: 1996 Comm: bash Not tainted 5.2.0-rc6+ #23 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.12.0-2.fc30 04/01/2014 Call Trace: dump_stack+0xca/0x13e print_address_description.cold+0x5/0x246 __kasan_report.cold+0x75/0x9a ? edac_set_poll_msec+0x140/0x150 kasan_report+0xe/0x20 edac_set_poll_msec+0x140/0x150 ? dimmdev_location_show+0x30/0x30 ? vfs_lock_file+0xe0/0xe0 ? _raw_spin_lock+0x87/0xe0 param_attr_store+0x1b5/0x310 ? param_array_set+0x4f0/0x4f0 module_attr_store+0x58/0x80 ? module_attr_show+0x80/0x80 sysfs_kf_write+0x13d/0x1a0 kernfs_fop_write+0x2bc/0x460 ? sysfs_kf_bin_read+0x270/0x270 ? kernfs_notify+0x1f0/0x1f0 __vfs_write+0x81/0x100 vfs_write+0x1e1/0x560 ksys_write+0x126/0x250 ? __ia32_sys_read+0xb0/0xb0 ? do_syscall_64+0x1f/0x390 do_syscall_64+0xc1/0x390 entry_SYSCALL_64_after_hwframe+0x49/0xbe RIP: 0033:0x7fa7caa5e970 Code: 73 01 c3 48 8b 0d 28 d5 2b 00 f7 d8 64 89 01 48 83 c8 ff c3 66 0f 1f 44 00 00 83 3d 99 2d 2c 00 00 75 10 b8 01 00 00 00 04 RSP: 002b:00007fff6acfdfe8 EFLAGS: 00000246 ORIG_RAX: 0000000000000001 RAX: ffffffffffffffda RBX: 0000000000000005 RCX: 00007fa7caa5e970 RDX: 0000000000000005 RSI: 0000000000e95c08 RDI: 0000000000000001 RBP: 0000000000e95c08 R08: 00007fa7cad1e760 R09: 00007fa7cb36a700 R10: 0000000000000073 R11: 0000000000000246 R12: 0000000000000005 R13: 0000000000000001 R14: 00007fa7cad1d600 R15: 0000000000000005
The buggy address belongs to the variable: edac_mc_poll_msec+0x0/0x40
Memory state around the buggy address: ffffffffb91b2c00: 00 00 00 00 fa fa fa fa 00 00 00 00 fa fa fa fa ffffffffb91b2c80: 00 00 00 00 fa fa fa fa 00 00 00 00 fa fa fa fa
ffffffffb91b2d00: 04 fa fa fa fa fa fa fa 04 fa fa fa fa fa fa fa
^ ffffffffb91b2d80: 04 fa fa fa fa fa fa fa 00 00 00 00 00 00 00 00 ffffffffb91b2e00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
Fix it by changing the type of edac_mc_poll_msec to unsigned int. The reason why this patch adopts unsigned int rather than unsigned long is msecs_to_jiffies() assumes arg to be unsigned int. We can avoid integer conversion bugs and unsigned int will be large enough for edac_mc_poll_msec.
Reviewed-by: James Morse james.morse@arm.com Fixes: 9da21b1509d8 ("EDAC: Poll timeout cannot be zero, p2") Signed-off-by: Eiichi Tsukata devel@etsukata.com Signed-off-by: Tony Luck tony.luck@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/edac/edac_mc_sysfs.c | 16 ++++++++-------- drivers/edac/edac_module.h | 2 +- 2 files changed, 9 insertions(+), 9 deletions(-)
diff --git a/drivers/edac/edac_mc_sysfs.c b/drivers/edac/edac_mc_sysfs.c index 0c53f2d54765..d459cf4b8579 100644 --- a/drivers/edac/edac_mc_sysfs.c +++ b/drivers/edac/edac_mc_sysfs.c @@ -26,7 +26,7 @@ static int edac_mc_log_ue = 1; static int edac_mc_log_ce = 1; static int edac_mc_panic_on_ue; -static int edac_mc_poll_msec = 1000; +static unsigned int edac_mc_poll_msec = 1000;
/* Getter functions for above */ int edac_mc_get_log_ue(void) @@ -45,30 +45,30 @@ int edac_mc_get_panic_on_ue(void) }
/* this is temporary */ -int edac_mc_get_poll_msec(void) +unsigned int edac_mc_get_poll_msec(void) { return edac_mc_poll_msec; }
static int edac_set_poll_msec(const char *val, struct kernel_param *kp) { - unsigned long l; + unsigned int i; int ret;
if (!val) return -EINVAL;
- ret = kstrtoul(val, 0, &l); + ret = kstrtouint(val, 0, &i); if (ret) return ret;
- if (l < 1000) + if (i < 1000) return -EINVAL;
- *((unsigned long *)kp->arg) = l; + *((unsigned int *)kp->arg) = i;
/* notify edac_mc engine to reset the poll period */ - edac_mc_reset_delay_period(l); + edac_mc_reset_delay_period(i);
return 0; } @@ -82,7 +82,7 @@ MODULE_PARM_DESC(edac_mc_log_ue, module_param(edac_mc_log_ce, int, 0644); MODULE_PARM_DESC(edac_mc_log_ce, "Log correctable error to console: 0=off 1=on"); -module_param_call(edac_mc_poll_msec, edac_set_poll_msec, param_get_int, +module_param_call(edac_mc_poll_msec, edac_set_poll_msec, param_get_uint, &edac_mc_poll_msec, 0644); MODULE_PARM_DESC(edac_mc_poll_msec, "Polling period in milliseconds");
diff --git a/drivers/edac/edac_module.h b/drivers/edac/edac_module.h index b95a48fc723d..c7a7a0891eb6 100644 --- a/drivers/edac/edac_module.h +++ b/drivers/edac/edac_module.h @@ -33,7 +33,7 @@ extern int edac_mc_get_log_ue(void); extern int edac_mc_get_log_ce(void); extern int edac_mc_get_panic_on_ue(void); extern int edac_get_poll_msec(void); -extern int edac_mc_get_poll_msec(void); +extern unsigned int edac_mc_get_poll_msec(void);
unsigned edac_dimm_info_location(struct dimm_info *dimm, char *buf, unsigned len);
[ Upstream commit b387e9b58679c60f5b1e4313939bd4878204fc37 ]
When system memory is in heavy pressure, bch_gc_thread_start() from run_cache_set() may fail due to out of memory. In such condition, c->gc_thread is assigned to -ENOMEM, not NULL pointer. Then in following failure code path bch_cache_set_error(), when cache_set_flush() gets called, the code piece to stop c->gc_thread is broken, if (!IS_ERR_OR_NULL(c->gc_thread)) kthread_stop(c->gc_thread);
And KASAN catches such NULL pointer deference problem, with the warning information:
[ 561.207881] ================================================================== [ 561.207900] BUG: KASAN: null-ptr-deref in kthread_stop+0x3b/0x440 [ 561.207904] Write of size 4 at addr 000000000000001c by task kworker/15:1/313
[ 561.207913] CPU: 15 PID: 313 Comm: kworker/15:1 Tainted: G W 5.0.0-vanilla+ #3 [ 561.207916] Hardware name: Lenovo ThinkSystem SR650 -[7X05CTO1WW]-/-[7X05CTO1WW]-, BIOS -[IVE136T-2.10]- 03/22/2019 [ 561.207935] Workqueue: events cache_set_flush [bcache] [ 561.207940] Call Trace: [ 561.207948] dump_stack+0x9a/0xeb [ 561.207955] ? kthread_stop+0x3b/0x440 [ 561.207960] ? kthread_stop+0x3b/0x440 [ 561.207965] kasan_report+0x176/0x192 [ 561.207973] ? kthread_stop+0x3b/0x440 [ 561.207981] kthread_stop+0x3b/0x440 [ 561.207995] cache_set_flush+0xd4/0x6d0 [bcache] [ 561.208008] process_one_work+0x856/0x1620 [ 561.208015] ? find_held_lock+0x39/0x1d0 [ 561.208028] ? drain_workqueue+0x380/0x380 [ 561.208048] worker_thread+0x87/0xb80 [ 561.208058] ? __kthread_parkme+0xb6/0x180 [ 561.208067] ? process_one_work+0x1620/0x1620 [ 561.208072] kthread+0x326/0x3e0 [ 561.208079] ? kthread_create_worker_on_cpu+0xc0/0xc0 [ 561.208090] ret_from_fork+0x3a/0x50 [ 561.208110] ================================================================== [ 561.208113] Disabling lock debugging due to kernel taint [ 561.208115] irq event stamp: 11800231 [ 561.208126] hardirqs last enabled at (11800231): [<ffffffff83008538>] do_syscall_64+0x18/0x410 [ 561.208127] BUG: unable to handle kernel NULL pointer dereference at 000000000000001c [ 561.208129] #PF error: [WRITE] [ 561.312253] hardirqs last disabled at (11800230): [<ffffffff830052ff>] trace_hardirqs_off_thunk+0x1a/0x1c [ 561.312259] softirqs last enabled at (11799832): [<ffffffff850005c7>] __do_softirq+0x5c7/0x8c3 [ 561.405975] PGD 0 P4D 0 [ 561.442494] softirqs last disabled at (11799821): [<ffffffff831add2c>] irq_exit+0x1ac/0x1e0 [ 561.791359] Oops: 0002 [#1] SMP KASAN NOPTI [ 561.791362] CPU: 15 PID: 313 Comm: kworker/15:1 Tainted: G B W 5.0.0-vanilla+ #3 [ 561.791363] Hardware name: Lenovo ThinkSystem SR650 -[7X05CTO1WW]-/-[7X05CTO1WW]-, BIOS -[IVE136T-2.10]- 03/22/2019 [ 561.791371] Workqueue: events cache_set_flush [bcache] [ 561.791374] RIP: 0010:kthread_stop+0x3b/0x440 [ 561.791376] Code: 00 00 65 8b 05 26 d5 e0 7c 89 c0 48 0f a3 05 ec aa df 02 0f 82 dc 02 00 00 4c 8d 63 20 be 04 00 00 00 4c 89 e7 e8 65 c5 53 00 <f0> ff 43 20 48 8d 7b 24 48 b8 00 00 00 00 00 fc ff df 48 89 fa 48 [ 561.791377] RSP: 0018:ffff88872fc8fd10 EFLAGS: 00010286 [ 561.838895] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 561.838916] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 561.838934] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 561.838948] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 561.838966] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 561.838979] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 561.838996] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 563.067028] RAX: 0000000000000000 RBX: fffffffffffffffc RCX: ffffffff832dd314 [ 563.067030] RDX: 0000000000000000 RSI: 0000000000000004 RDI: 0000000000000297 [ 563.067032] RBP: ffff88872fc8fe88 R08: fffffbfff0b8213d R09: fffffbfff0b8213d [ 563.067034] R10: 0000000000000001 R11: fffffbfff0b8213c R12: 000000000000001c [ 563.408618] R13: ffff88dc61cc0f68 R14: ffff888102b94900 R15: ffff88dc61cc0f68 [ 563.408620] FS: 0000000000000000(0000) GS:ffff888f7dc00000(0000) knlGS:0000000000000000 [ 563.408622] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 563.408623] CR2: 000000000000001c CR3: 0000000f48a1a004 CR4: 00000000007606e0 [ 563.408625] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 [ 563.408627] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 [ 563.904795] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 563.915796] PKRU: 55555554 [ 563.915797] Call Trace: [ 563.915807] cache_set_flush+0xd4/0x6d0 [bcache] [ 563.915812] process_one_work+0x856/0x1620 [ 564.001226] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 564.033563] ? find_held_lock+0x39/0x1d0 [ 564.033567] ? drain_workqueue+0x380/0x380 [ 564.033574] worker_thread+0x87/0xb80 [ 564.062823] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 564.118042] ? __kthread_parkme+0xb6/0x180 [ 564.118046] ? process_one_work+0x1620/0x1620 [ 564.118048] kthread+0x326/0x3e0 [ 564.118050] ? kthread_create_worker_on_cpu+0xc0/0xc0 [ 564.167066] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 564.252441] ret_from_fork+0x3a/0x50 [ 564.252447] Modules linked in: msr rpcrdma sunrpc rdma_ucm ib_iser ib_umad rdma_cm ib_ipoib i40iw configfs iw_cm ib_cm libiscsi scsi_transport_iscsi mlx4_ib ib_uverbs mlx4_en ib_core nls_iso8859_1 nls_cp437 vfat fat intel_rapl skx_edac x86_pkg_temp_thermal coretemp iTCO_wdt iTCO_vendor_support crct10dif_pclmul crc32_pclmul crc32c_intel ghash_clmulni_intel ses raid0 aesni_intel cdc_ether enclosure usbnet ipmi_ssif joydev aes_x86_64 i40e scsi_transport_sas mii bcache md_mod crypto_simd mei_me ioatdma crc64 ptp cryptd pcspkr i2c_i801 mlx4_core glue_helper pps_core mei lpc_ich dca wmi ipmi_si ipmi_devintf nd_pmem dax_pmem nd_btt ipmi_msghandler device_dax pcc_cpufreq button hid_generic usbhid mgag200 i2c_algo_bit drm_kms_helper syscopyarea sysfillrect xhci_pci sysimgblt fb_sys_fops xhci_hcd ttm megaraid_sas drm usbcore nfit libnvdimm sg dm_multipath dm_mod scsi_dh_rdac scsi_dh_emc scsi_dh_alua efivarfs [ 564.299390] bcache: bch_count_io_errors() nvme0n1: IO error on writing btree. [ 564.348360] CR2: 000000000000001c [ 564.348362] ---[ end trace b7f0e5cc7b2103b0 ]---
Therefore, it is not enough to only check whether c->gc_thread is NULL, we should use IS_ERR_OR_NULL() to check both NULL pointer and error value.
This patch changes the above buggy code piece in this way, if (!IS_ERR_OR_NULL(c->gc_thread)) kthread_stop(c->gc_thread);
Signed-off-by: Coly Li colyli@suse.de Signed-off-by: Jens Axboe axboe@kernel.dk Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/md/bcache/super.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/md/bcache/super.c b/drivers/md/bcache/super.c index 02757b90e402..e42092146083 100644 --- a/drivers/md/bcache/super.c +++ b/drivers/md/bcache/super.c @@ -1403,7 +1403,7 @@ static void cache_set_flush(struct closure *cl) kobject_put(&c->internal); kobject_del(&c->kobj);
- if (c->gc_thread) + if (!IS_ERR_OR_NULL(c->gc_thread)) kthread_stop(c->gc_thread);
if (!IS_ERR_OR_NULL(c->root))
[ Upstream commit 4ce9146e0370fcd573f0372d9b4e5a211112567c ]
Syzkaller found that it is possible to provoke a memory leak by never freeing rx_skb in struct bcsp_struct.
Fix by freeing in bcsp_close()
Signed-off-by: Tomas Bortoli tomasbortoli@gmail.com Reported-by: syzbot+98162c885993b72f19c4@syzkaller.appspotmail.com Signed-off-by: Marcel Holtmann marcel@holtmann.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/bluetooth/hci_bcsp.c | 5 +++++ 1 file changed, 5 insertions(+)
diff --git a/drivers/bluetooth/hci_bcsp.c b/drivers/bluetooth/hci_bcsp.c index d0b615a932d1..9833b53a8b50 100644 --- a/drivers/bluetooth/hci_bcsp.c +++ b/drivers/bluetooth/hci_bcsp.c @@ -729,6 +729,11 @@ static int bcsp_close(struct hci_uart *hu) skb_queue_purge(&bcsp->rel); skb_queue_purge(&bcsp->unrel);
+ if (bcsp->rx_skb) { + kfree_skb(bcsp->rx_skb); + bcsp->rx_skb = NULL; + } + kfree(bcsp); return 0; }
[ Upstream commit b188b03270b7f8568fc714101ce82fbf5e811c5a ]
Handle overlooked case where the target address is assigned to a peer and neither route nor gateway exist.
For one peer, no checks are performed to see if it is meant to receive packets for a given address.
As soon as there is a second peer however, checks are performed to deal with routes and gateways for handling complex setups with multiple hops to a target address. This logic assumed that no route and no gateway imply that the destination address can not be reached, which is false in case of a direct peer.
Acked-by: Jukka Rissanen jukka.rissanen@linux.intel.com Tested-by: Michael Scott mike@foundries.io Signed-off-by: Josua Mayer josua.mayer@jm0.eu Signed-off-by: Marcel Holtmann marcel@holtmann.org Signed-off-by: Sasha Levin sashal@kernel.org --- net/bluetooth/6lowpan.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-)
diff --git a/net/bluetooth/6lowpan.c b/net/bluetooth/6lowpan.c index 795ddd8b2f77..4cd6b8d811ff 100644 --- a/net/bluetooth/6lowpan.c +++ b/net/bluetooth/6lowpan.c @@ -184,10 +184,16 @@ static inline struct lowpan_peer *peer_lookup_dst(struct lowpan_dev *dev, }
if (!rt) { - nexthop = &lowpan_cb(skb)->gw; - - if (ipv6_addr_any(nexthop)) - return NULL; + if (ipv6_addr_any(&lowpan_cb(skb)->gw)) { + /* There is neither route nor gateway, + * probably the destination is a direct peer. + */ + nexthop = daddr; + } else { + /* There is a known gateway + */ + nexthop = &lowpan_cb(skb)->gw; + } } else { nexthop = rt6_nexthop(rt, daddr);
[ Upstream commit 28261da8a26f4915aa257d12d506c6ba179d961f ]
Because of both sides doing L2CAP disconnection at the same time, it was possible to receive L2CAP Disconnection Response with CID that was already freed. That caused problems if CID was already reused and L2CAP Connection Request with same CID was sent out. Before this patch kernel deleted channel context regardless of the state of the channel.
Example where leftover Disconnection Response (frame #402) causes local device to delete L2CAP channel which was not yet connected. This in turn confuses remote device's stack because same CID is re-used without properly disconnecting.
Btmon capture before patch: ** snip **
ACL Data RX: Handle 43 flags 0x02 dlen 8 #394 [hci1] 10.748949
Channel: 65 len 4 [PSM 3 mode 0] {chan 2} RFCOMM: Disconnect (DISC) (0x43) Address: 0x03 cr 1 dlci 0x00 Control: 0x53 poll/final 1 Length: 0 FCS: 0xfd < ACL Data TX: Handle 43 flags 0x00 dlen 8 #395 [hci1] 10.749062 Channel: 65 len 4 [PSM 3 mode 0] {chan 2} RFCOMM: Unnumbered Ack (UA) (0x63) Address: 0x03 cr 1 dlci 0x00 Control: 0x73 poll/final 1 Length: 0 FCS: 0xd7 < ACL Data TX: Handle 43 flags 0x00 dlen 12 #396 [hci1] 10.749073 L2CAP: Disconnection Request (0x06) ident 17 len 4 Destination CID: 65 Source CID: 65
HCI Event: Number of Completed Packets (0x13) plen 5 #397 [hci1] 10.752391
Num handles: 1 Handle: 43 Count: 1
HCI Event: Number of Completed Packets (0x13) plen 5 #398 [hci1] 10.753394
Num handles: 1 Handle: 43 Count: 1
ACL Data RX: Handle 43 flags 0x02 dlen 12 #399 [hci1] 10.756499
L2CAP: Disconnection Request (0x06) ident 26 len 4 Destination CID: 65 Source CID: 65 < ACL Data TX: Handle 43 flags 0x00 dlen 12 #400 [hci1] 10.756548 L2CAP: Disconnection Response (0x07) ident 26 len 4 Destination CID: 65 Source CID: 65 < ACL Data TX: Handle 43 flags 0x00 dlen 12 #401 [hci1] 10.757459 L2CAP: Connection Request (0x02) ident 18 len 4 PSM: 1 (0x0001) Source CID: 65
ACL Data RX: Handle 43 flags 0x02 dlen 12 #402 [hci1] 10.759148
L2CAP: Disconnection Response (0x07) ident 17 len 4 Destination CID: 65 Source CID: 65 = bluetoothd: 00:1E:AB:4C:56:54: error updating services: Input/o.. 10.759447
HCI Event: Number of Completed Packets (0x13) plen 5 #403 [hci1] 10.759386
Num handles: 1 Handle: 43 Count: 1
ACL Data RX: Handle 43 flags 0x02 dlen 12 #404 [hci1] 10.760397
L2CAP: Connection Request (0x02) ident 27 len 4 PSM: 3 (0x0003) Source CID: 65 < ACL Data TX: Handle 43 flags 0x00 dlen 16 #405 [hci1] 10.760441 L2CAP: Connection Response (0x03) ident 27 len 8 Destination CID: 65 Source CID: 65 Result: Connection successful (0x0000) Status: No further information available (0x0000) < ACL Data TX: Handle 43 flags 0x00 dlen 27 #406 [hci1] 10.760449 L2CAP: Configure Request (0x04) ident 19 len 19 Destination CID: 65 Flags: 0x0000 Option: Maximum Transmission Unit (0x01) [mandatory] MTU: 1013 Option: Retransmission and Flow Control (0x04) [mandatory] Mode: Basic (0x00) TX window size: 0 Max transmit: 0 Retransmission timeout: 0 Monitor timeout: 0 Maximum PDU size: 0
HCI Event: Number of Completed Packets (0x13) plen 5 #407 [hci1] 10.761399
Num handles: 1 Handle: 43 Count: 1
ACL Data RX: Handle 43 flags 0x02 dlen 16 #408 [hci1] 10.762942
L2CAP: Connection Response (0x03) ident 18 len 8 Destination CID: 66 Source CID: 65 Result: Connection successful (0x0000) Status: No further information available (0x0000) *snip*
Similar case after the patch: *snip*
ACL Data RX: Handle 43 flags 0x02 dlen 8 #22702 [hci0] 1664.411056
Channel: 65 len 4 [PSM 3 mode 0] {chan 3} RFCOMM: Disconnect (DISC) (0x43) Address: 0x03 cr 1 dlci 0x00 Control: 0x53 poll/final 1 Length: 0 FCS: 0xfd < ACL Data TX: Handle 43 flags 0x00 dlen 8 #22703 [hci0] 1664.411136 Channel: 65 len 4 [PSM 3 mode 0] {chan 3} RFCOMM: Unnumbered Ack (UA) (0x63) Address: 0x03 cr 1 dlci 0x00 Control: 0x73 poll/final 1 Length: 0 FCS: 0xd7 < ACL Data TX: Handle 43 flags 0x00 dlen 12 #22704 [hci0] 1664.411143 L2CAP: Disconnection Request (0x06) ident 11 len 4 Destination CID: 65 Source CID: 65
HCI Event: Number of Completed Pac.. (0x13) plen 5 #22705 [hci0] 1664.414009
Num handles: 1 Handle: 43 Count: 1
HCI Event: Number of Completed Pac.. (0x13) plen 5 #22706 [hci0] 1664.415007
Num handles: 1 Handle: 43 Count: 1
ACL Data RX: Handle 43 flags 0x02 dlen 12 #22707 [hci0] 1664.418674
L2CAP: Disconnection Request (0x06) ident 17 len 4 Destination CID: 65 Source CID: 65 < ACL Data TX: Handle 43 flags 0x00 dlen 12 #22708 [hci0] 1664.418762 L2CAP: Disconnection Response (0x07) ident 17 len 4 Destination CID: 65 Source CID: 65 < ACL Data TX: Handle 43 flags 0x00 dlen 12 #22709 [hci0] 1664.421073 L2CAP: Connection Request (0x02) ident 12 len 4 PSM: 1 (0x0001) Source CID: 65
ACL Data RX: Handle 43 flags 0x02 dlen 12 #22710 [hci0] 1664.421371
L2CAP: Disconnection Response (0x07) ident 11 len 4 Destination CID: 65 Source CID: 65
HCI Event: Number of Completed Pac.. (0x13) plen 5 #22711 [hci0] 1664.424082
Num handles: 1 Handle: 43 Count: 1
HCI Event: Number of Completed Pac.. (0x13) plen 5 #22712 [hci0] 1664.425040
Num handles: 1 Handle: 43 Count: 1
ACL Data RX: Handle 43 flags 0x02 dlen 12 #22713 [hci0] 1664.426103
L2CAP: Connection Request (0x02) ident 18 len 4 PSM: 3 (0x0003) Source CID: 65 < ACL Data TX: Handle 43 flags 0x00 dlen 16 #22714 [hci0] 1664.426186 L2CAP: Connection Response (0x03) ident 18 len 8 Destination CID: 66 Source CID: 65 Result: Connection successful (0x0000) Status: No further information available (0x0000) < ACL Data TX: Handle 43 flags 0x00 dlen 27 #22715 [hci0] 1664.426196 L2CAP: Configure Request (0x04) ident 13 len 19 Destination CID: 65 Flags: 0x0000 Option: Maximum Transmission Unit (0x01) [mandatory] MTU: 1013 Option: Retransmission and Flow Control (0x04) [mandatory] Mode: Basic (0x00) TX window size: 0 Max transmit: 0 Retransmission timeout: 0 Monitor timeout: 0 Maximum PDU size: 0
ACL Data RX: Handle 43 flags 0x02 dlen 16 #22716 [hci0] 1664.428804
L2CAP: Connection Response (0x03) ident 12 len 8 Destination CID: 66 Source CID: 65 Result: Connection successful (0x0000) Status: No further information available (0x0000) *snip*
Fix is to check that channel is in state BT_DISCONN before deleting the channel.
This bug was found while fuzzing Bluez's OBEX implementation using Synopsys Defensics.
Reported-by: Matti Kamunen matti.kamunen@synopsys.com Reported-by: Ari Timonen ari.timonen@synopsys.com Signed-off-by: Matias Karhumaa matias.karhumaa@gmail.com Signed-off-by: Marcel Holtmann marcel@holtmann.org Signed-off-by: Sasha Levin sashal@kernel.org --- net/bluetooth/l2cap_core.c | 6 ++++++ 1 file changed, 6 insertions(+)
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c index 46afd560f242..c25f1e4846cd 100644 --- a/net/bluetooth/l2cap_core.c +++ b/net/bluetooth/l2cap_core.c @@ -4363,6 +4363,12 @@ static inline int l2cap_disconnect_rsp(struct l2cap_conn *conn,
l2cap_chan_lock(chan);
+ if (chan->state != BT_DISCONN) { + l2cap_chan_unlock(chan); + mutex_unlock(&conn->chan_lock); + return 0; + } + l2cap_chan_hold(chan); l2cap_chan_del(chan, 0);
[ Upstream commit c49a8682fc5d298d44e8d911f4fa14690ea9485e ]
Problem: The Linux Bluetooth stack yields complete control over the BLE connection interval to the remote device.
The Linux Bluetooth stack provides access to the BLE connection interval min and max values through /sys/kernel/debug/bluetooth/hci0/ conn_min_interval and /sys/kernel/debug/bluetooth/hci0/conn_max_interval. These values are used for initial BLE connections, but the remote device has the ability to request a connection parameter update. In the event that the remote side requests to change the connection interval, the Linux kernel currently only validates that the desired value is within the acceptable range in the Bluetooth specification (6 - 3200, corresponding to 7.5ms - 4000ms). There is currently no validation that the desired value requested by the remote device is within the min/max limits specified in the conn_min_interval/conn_max_interval configurations. This essentially leads to Linux yielding complete control over the connection interval to the remote device.
The proposed patch adds a verification step to the connection parameter update mechanism, ensuring that the desired value is within the min/max bounds of the current connection. If the desired value is outside of the current connection min/max values, then the connection parameter update request is rejected and the negative response is returned to the remote device. Recall that the initial connection is established using the local conn_min_interval/conn_max_interval values, so this allows the Linux administrator to retain control over the BLE connection interval.
The one downside that I see is that the current default Linux values for conn_min_interval and conn_max_interval typically correspond to 30ms and 50ms respectively. If this change were accepted, then it is feasible that some devices would no longer be able to negotiate to their desired connection interval values. This might be remedied by setting the default Linux conn_min_interval and conn_max_interval values to the widest supported range (6 - 3200 / 7.5ms - 4000ms). This could lead to the same behavior as the current implementation, where the remote device could request to change the connection interval value to any value that is permitted by the Bluetooth specification, and Linux would accept the desired value.
Signed-off-by: Carey Sonsino csonsino@gmail.com Signed-off-by: Marcel Holtmann marcel@holtmann.org Signed-off-by: Sasha Levin sashal@kernel.org --- net/bluetooth/hci_event.c | 5 +++++ net/bluetooth/l2cap_core.c | 9 ++++++++- 2 files changed, 13 insertions(+), 1 deletion(-)
diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c index 37fe2b158c2a..c4e94f34d048 100644 --- a/net/bluetooth/hci_event.c +++ b/net/bluetooth/hci_event.c @@ -5062,6 +5062,11 @@ static void hci_le_remote_conn_param_req_evt(struct hci_dev *hdev, return send_conn_param_neg_reply(hdev, handle, HCI_ERROR_UNKNOWN_CONN_ID);
+ if (min < hcon->le_conn_min_interval || + max > hcon->le_conn_max_interval) + return send_conn_param_neg_reply(hdev, handle, + HCI_ERROR_INVALID_LL_PARAMS); + if (hci_check_conn_params(min, max, latency, timeout)) return send_conn_param_neg_reply(hdev, handle, HCI_ERROR_INVALID_LL_PARAMS); diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c index c25f1e4846cd..8cfba78d26f6 100644 --- a/net/bluetooth/l2cap_core.c +++ b/net/bluetooth/l2cap_core.c @@ -5266,7 +5266,14 @@ static inline int l2cap_conn_param_update_req(struct l2cap_conn *conn,
memset(&rsp, 0, sizeof(rsp));
- err = hci_check_conn_params(min, max, latency, to_multiplier); + if (min < hcon->le_conn_min_interval || + max > hcon->le_conn_max_interval) { + BT_DBG("requested connection interval exceeds current bounds."); + err = -EINVAL; + } else { + err = hci_check_conn_params(min, max, latency, to_multiplier); + } + if (err) rsp.result = cpu_to_le16(L2CAP_CONN_PARAM_REJECTED); else
From: Eric Biggers ebiggers@google.com
commit 5c6bc4dfa515738149998bb0db2481a4fdead979 upstream.
Changing ghash_mod_init() to be subsys_initcall made it start running before the alignment fault handler has been installed on ARM. In kernel builds where the keys in the ghash test vectors happened to be misaligned in the kernel image, this exposed the longstanding bug that ghash_setkey() is incorrectly casting the key buffer (which can have any alignment) to be128 for passing to gf128mul_init_4k_lle().
Fix this by memcpy()ing the key to a temporary buffer.
Don't fix it by setting an alignmask on the algorithm instead because that would unnecessarily force alignment of the data too.
Fixes: 2cdc6899a88e ("crypto: ghash - Add GHASH digest algorithm for GCM") Reported-by: Peter Robinson pbrobinson@gmail.com Cc: stable@vger.kernel.org Signed-off-by: Eric Biggers ebiggers@google.com Tested-by: Peter Robinson pbrobinson@gmail.com Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- crypto/ghash-generic.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
--- a/crypto/ghash-generic.c +++ b/crypto/ghash-generic.c @@ -34,6 +34,7 @@ static int ghash_setkey(struct crypto_sh const u8 *key, unsigned int keylen) { struct ghash_ctx *ctx = crypto_shash_ctx(tfm); + be128 k;
if (keylen != GHASH_BLOCK_SIZE) { crypto_shash_set_flags(tfm, CRYPTO_TFM_RES_BAD_KEY_LEN); @@ -42,7 +43,12 @@ static int ghash_setkey(struct crypto_sh
if (ctx->gf128) gf128mul_free_4k(ctx->gf128); - ctx->gf128 = gf128mul_init_4k_lle((be128 *)key); + + BUILD_BUG_ON(sizeof(k) != GHASH_BLOCK_SIZE); + memcpy(&k, key, GHASH_BLOCK_SIZE); /* avoid violating alignment rules */ + ctx->gf128 = gf128mul_init_4k_lle(&k); + memzero_explicit(&k, GHASH_BLOCK_SIZE); + if (!ctx->gf128) return -ENOMEM;
From: Elena Petrova lenaptr@google.com
commit 1d4aaf16defa86d2665ae7db0259d6cb07e2091f upstream.
The sha1-ce finup implementation for ARM64 produces wrong digest for empty input (len=0). Expected: da39a3ee..., result: 67452301... (initial value of SHA internal state). The error is in sha1_ce_finup: for empty data `finalize` will be 1, so the code is relying on sha1_ce_transform to make the final round. However, in sha1_base_do_update, the block function will not be called when len == 0.
Fix it by setting finalize to 0 if data is empty.
Fixes: 07eb54d306f4 ("crypto: arm64/sha1-ce - move SHA-1 ARMv8 implementation to base layer") Cc: stable@vger.kernel.org Signed-off-by: Elena Petrova lenaptr@google.com Reviewed-by: Ard Biesheuvel ard.biesheuvel@linaro.org Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/arm64/crypto/sha1-ce-glue.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/arch/arm64/crypto/sha1-ce-glue.c +++ b/arch/arm64/crypto/sha1-ce-glue.c @@ -50,7 +50,7 @@ static int sha1_ce_finup(struct shash_de unsigned int len, u8 *out) { struct sha1_ce_state *sctx = shash_desc_ctx(desc); - bool finalize = !sctx->sst.count && !(len % SHA1_BLOCK_SIZE); + bool finalize = !sctx->sst.count && !(len % SHA1_BLOCK_SIZE) && len;
/* * Allow the asm code to perform the finalization if there is no
From: Elena Petrova lenaptr@google.com
commit 6bd934de1e393466b319d29c4427598fda096c57 upstream.
The sha256-ce finup implementation for ARM64 produces wrong digest for empty input (len=0). Expected: the actual digest, result: initial value of SHA internal state. The error is in sha256_ce_finup: for empty data `finalize` will be 1, so the code is relying on sha2_ce_transform to make the final round. However, in sha256_base_do_update, the block function will not be called when len == 0.
Fix it by setting finalize to 0 if data is empty.
Fixes: 03802f6a80b3a ("crypto: arm64/sha2-ce - move SHA-224/256 ARMv8 implementation to base layer") Cc: stable@vger.kernel.org Signed-off-by: Elena Petrova lenaptr@google.com Reviewed-by: Ard Biesheuvel ard.biesheuvel@linaro.org Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/arm64/crypto/sha2-ce-glue.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/arch/arm64/crypto/sha2-ce-glue.c +++ b/arch/arm64/crypto/sha2-ce-glue.c @@ -52,7 +52,7 @@ static int sha256_ce_finup(struct shash_ unsigned int len, u8 *out) { struct sha256_ce_state *sctx = shash_desc_ctx(desc); - bool finalize = !sctx->sst.count && !(len % SHA256_BLOCK_SIZE); + bool finalize = !sctx->sst.count && !(len % SHA256_BLOCK_SIZE) && len;
/* * Allow the asm code to perform the finalization if there is no
From: Grant Hernandez granthernandez@google.com
commit 2a017fd82c5402b3c8df5e3d6e5165d9e6147dc1 upstream.
The GTCO tablet input driver configures itself from an HID report sent via USB during the initial enumeration process. Some debugging messages are generated during the parsing. A debugging message indentation counter is not bounds checked, leading to the ability for a specially crafted HID report to cause '-' and null bytes be written past the end of the indentation array. As long as the kernel has CONFIG_DYNAMIC_DEBUG enabled, this code will not be optimized out. This was discovered during code review after a previous syzkaller bug was found in this driver.
Signed-off-by: Grant Hernandez granthernandez@google.com Cc: stable@vger.kernel.org Signed-off-by: Dmitry Torokhov dmitry.torokhov@gmail.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/input/tablet/gtco.c | 20 +++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-)
--- a/drivers/input/tablet/gtco.c +++ b/drivers/input/tablet/gtco.c @@ -78,6 +78,7 @@ Scott Hill shill@gtcocalcomp.com
/* Max size of a single report */ #define REPORT_MAX_SIZE 10 +#define MAX_COLLECTION_LEVELS 10
/* Bitmask whether pen is in range */ @@ -224,8 +225,7 @@ static void parse_hid_report_descriptor( char maintype = 'x'; char globtype[12]; int indent = 0; - char indentstr[10] = ""; - + char indentstr[MAX_COLLECTION_LEVELS + 1] = { 0 };
dev_dbg(ddev, "======>>>>>>PARSE<<<<<<======\n");
@@ -351,6 +351,13 @@ static void parse_hid_report_descriptor( case TAG_MAIN_COL_START: maintype = 'S';
+ if (indent == MAX_COLLECTION_LEVELS) { + dev_err(ddev, "Collection level %d would exceed limit of %d\n", + indent + 1, + MAX_COLLECTION_LEVELS); + break; + } + if (data == 0) { dev_dbg(ddev, "======>>>>>> Physical\n"); strcpy(globtype, "Physical"); @@ -370,8 +377,15 @@ static void parse_hid_report_descriptor( break;
case TAG_MAIN_COL_END: - dev_dbg(ddev, "<<<<<<======\n"); maintype = 'E'; + + if (indent == 0) { + dev_err(ddev, "Collection level already at zero\n"); + break; + } + + dev_dbg(ddev, "<<<<<<======\n"); + indent--; for (x = 0; x < indent; x++) indentstr[x] = '-';
From: Krzysztof Kozlowski krzk@kernel.org
commit 16da0eb5ab6ef2dd1d33431199126e63db9997cc upstream.
On S2MPS11 device, the buck7 and buck8 regulator voltages start at 750 mV, not 600 mV. Using wrong minimal value caused shifting of these regulator values by 150 mV (e.g. buck7 usually configured to v1.35 V was reported as 1.2 V).
On most of the boards these regulators are left in default state so this was only affecting reported voltage. However if any driver wanted to change them, then effectively it would set voltage 150 mV higher than intended.
Cc: stable@vger.kernel.org Fixes: cb74685ecb39 ("regulator: s2mps11: Add samsung s2mps11 regulator driver") Signed-off-by: Krzysztof Kozlowski krzk@kernel.org Signed-off-by: Mark Brown broonie@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/regulator/s2mps11.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
--- a/drivers/regulator/s2mps11.c +++ b/drivers/regulator/s2mps11.c @@ -382,8 +382,8 @@ static const struct regulator_desc s2mps regulator_desc_s2mps11_buck1_4(4), regulator_desc_s2mps11_buck5, regulator_desc_s2mps11_buck67810(6, MIN_600_MV, STEP_6_25_MV), - regulator_desc_s2mps11_buck67810(7, MIN_600_MV, STEP_12_5_MV), - regulator_desc_s2mps11_buck67810(8, MIN_600_MV, STEP_12_5_MV), + regulator_desc_s2mps11_buck67810(7, MIN_750_MV, STEP_12_5_MV), + regulator_desc_s2mps11_buck67810(8, MIN_750_MV, STEP_12_5_MV), regulator_desc_s2mps11_buck9, regulator_desc_s2mps11_buck67810(10, MIN_750_MV, STEP_12_5_MV), };
From: Eiichi Tsukata devel@etsukata.com
commit 46cc0b44428d0f0e81f11ea98217fc0edfbeab07 upstream.
Current snapshot implementation swaps two ring_buffers even though their sizes are different from each other, that can cause an inconsistency between the contents of buffer_size_kb file and the current buffer size.
For example:
# cat buffer_size_kb 7 (expanded: 1408) # echo 1 > events/enable # grep bytes per_cpu/cpu0/stats bytes: 1441020 # echo 1 > snapshot // current:1408, spare:1408 # echo 123 > buffer_size_kb // current:123, spare:1408 # echo 1 > snapshot // current:1408, spare:123 # grep bytes per_cpu/cpu0/stats bytes: 1443700 # cat buffer_size_kb 123 // != current:1408
And also, a similar per-cpu case hits the following WARNING:
Reproducer:
# echo 1 > per_cpu/cpu0/snapshot # echo 123 > buffer_size_kb # echo 1 > per_cpu/cpu0/snapshot
WARNING:
WARNING: CPU: 0 PID: 1946 at kernel/trace/trace.c:1607 update_max_tr_single.part.0+0x2b8/0x380 Modules linked in: CPU: 0 PID: 1946 Comm: bash Not tainted 5.2.0-rc6 #20 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.12.0-2.fc30 04/01/2014 RIP: 0010:update_max_tr_single.part.0+0x2b8/0x380 Code: ff e8 dc da f9 ff 0f 0b e9 88 fe ff ff e8 d0 da f9 ff 44 89 ee bf f5 ff ff ff e8 33 dc f9 ff 41 83 fd f5 74 96 e8 b8 da f9 ff <0f> 0b eb 8d e8 af da f9 ff 0f 0b e9 bf fd ff ff e8 a3 da f9 ff 48 RSP: 0018:ffff888063e4fca0 EFLAGS: 00010093 RAX: ffff888066214380 RBX: ffffffff99850fe0 RCX: ffffffff964298a8 RDX: 0000000000000000 RSI: 00000000fffffff5 RDI: 0000000000000005 RBP: 1ffff1100c7c9f96 R08: ffff888066214380 R09: ffffed100c7c9f9b R10: ffffed100c7c9f9a R11: 0000000000000003 R12: 0000000000000000 R13: 00000000ffffffea R14: ffff888066214380 R15: ffffffff99851060 FS: 00007f9f8173c700(0000) GS:ffff88806d000000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 0000000000714dc0 CR3: 0000000066fa6000 CR4: 00000000000006f0 Call Trace: ? trace_array_printk_buf+0x140/0x140 ? __mutex_lock_slowpath+0x10/0x10 tracing_snapshot_write+0x4c8/0x7f0 ? trace_printk_init_buffers+0x60/0x60 ? selinux_file_permission+0x3b/0x540 ? tracer_preempt_off+0x38/0x506 ? trace_printk_init_buffers+0x60/0x60 __vfs_write+0x81/0x100 vfs_write+0x1e1/0x560 ksys_write+0x126/0x250 ? __ia32_sys_read+0xb0/0xb0 ? do_syscall_64+0x1f/0x390 do_syscall_64+0xc1/0x390 entry_SYSCALL_64_after_hwframe+0x49/0xbe
This patch adds resize_buffer_duplicate_size() to check if there is a difference between current/spare buffer sizes and resize a spare buffer if necessary.
Link: http://lkml.kernel.org/r/20190625012910.13109-1-devel@etsukata.com
Cc: stable@vger.kernel.org Fixes: ad909e21bbe69 ("tracing: Add internal tracing_snapshot() functions") Signed-off-by: Eiichi Tsukata devel@etsukata.com Signed-off-by: Steven Rostedt (VMware) rostedt@goodmis.org Signed-off-by: Nobuhiro Iwamatsu nobuhiro1.iwamatsu@toshiba.co.jp Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- kernel/trace/trace.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-)
--- a/kernel/trace/trace.c +++ b/kernel/trace/trace.c @@ -5406,11 +5406,15 @@ tracing_snapshot_write(struct file *filp break; } #endif - if (!tr->allocated_snapshot) { + if (!tr->allocated_snapshot) + ret = resize_buffer_duplicate_size(&tr->max_buffer, + &tr->trace_buffer, iter->cpu_file); + else ret = alloc_snapshot(tr); - if (ret < 0) - break; - } + + if (ret < 0) + break; + local_irq_disable(); /* Now, we're going to swap */ if (iter->cpu_file == RING_BUFFER_ALL_CPUS)
From: Trond Myklebust trond.myklebust@hammerspace.com
commit 44942b4e457beda00981f616402a1a791e8c616e upstream.
According to the open() manpage, Linux reserves the access mode 3 to mean "check for read and write permission on the file and return a file descriptor that can't be used for reading or writing."
Currently, the NFSv4 code will ask the server to open the file, and will use an incorrect share access mode of 0. Since it has an incorrect share access mode, the client later forgets to send a corresponding close, meaning it can leak stateids on the server.
Fixes: ce4ef7c0a8a05 ("NFS: Split out NFS v4 file operations") Cc: stable@vger.kernel.org # 3.6+ Signed-off-by: Trond Myklebust trond.myklebust@hammerspace.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- fs/nfs/inode.c | 1 + fs/nfs/nfs4file.c | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-)
--- a/fs/nfs/inode.c +++ b/fs/nfs/inode.c @@ -935,6 +935,7 @@ int nfs_open(struct inode *inode, struct nfs_fscache_open_file(inode, filp); return 0; } +EXPORT_SYMBOL_GPL(nfs_open);
/* * This function is called whenever some part of NFS notices that --- a/fs/nfs/nfs4file.c +++ b/fs/nfs/nfs4file.c @@ -49,7 +49,7 @@ nfs4_file_open(struct inode *inode, stru return err;
if ((openflags & O_ACCMODE) == 3) - openflags--; + return nfs_open(inode, filp);
/* We can't create new files here */ openflags &= ~(O_CREAT|O_EXCL);
From: Christophe Leroy christophe.leroy@c-s.fr
commit aeb87246537a83c2aff482f3f34a2e0991e02cbc upstream.
All mapping iterator logic is based on the assumption that sg->offset is always lower than PAGE_SIZE.
But there are situations where sg->offset is such that the SG item is on the second page. In that case sg_copy_to_buffer() fails properly copying the data into the buffer. One of the reason is that the data will be outside the kmapped area used to access that data.
This patch fixes the issue by adjusting the mapping iterator offset and pgoffset fields such that offset is always lower than PAGE_SIZE.
Signed-off-by: Christophe Leroy christophe.leroy@c-s.fr Fixes: 4225fc8555a9 ("lib/scatterlist: use page iterator in the mapping iterator") Cc: stable@vger.kernel.org Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- lib/scatterlist.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-)
--- a/lib/scatterlist.c +++ b/lib/scatterlist.c @@ -496,17 +496,18 @@ static bool sg_miter_get_next_page(struc { if (!miter->__remaining) { struct scatterlist *sg; - unsigned long pgoffset;
if (!__sg_page_iter_next(&miter->piter)) return false;
sg = miter->piter.sg; - pgoffset = miter->piter.sg_pgoffset;
- miter->__offset = pgoffset ? 0 : sg->offset; + miter->__offset = miter->piter.sg_pgoffset ? 0 : sg->offset; + miter->piter.sg_pgoffset += miter->__offset >> PAGE_SHIFT; + miter->__offset &= PAGE_SIZE - 1; miter->__remaining = sg->offset + sg->length - - (pgoffset << PAGE_SHIFT) - miter->__offset; + (miter->piter.sg_pgoffset << PAGE_SHIFT) - + miter->__offset; miter->__remaining = min_t(unsigned long, miter->__remaining, PAGE_SIZE - miter->__offset); }
From: Takashi Iwai tiwai@suse.de
commit ede34f397ddb063b145b9e7d79c6026f819ded13 upstream.
The fix for the racy writes and ioctls to sequencer widened the application of client->ioctl_mutex to the whole write loop. Although it does unlock/relock for the lengthy operation like the event dup, the loop keeps the ioctl_mutex for the whole time in other situations. This may take quite long time if the user-space would give a huge buffer, and this is a likely cause of some weird behavior spotted by syzcaller fuzzer.
This patch puts a simple workaround, just adding a mutex break in the loop when a large number of events have been processed. This shouldn't hit any performance drop because the threshold is set high enough for usual operations.
Fixes: 7bd800915677 ("ALSA: seq: More protection for concurrent write and ioctl races") Reported-by: syzbot+97aae04ce27e39cbfca9@syzkaller.appspotmail.com Reported-by: syzbot+4c595632b98bb8ffcc66@syzkaller.appspotmail.com Cc: stable@vger.kernel.org Signed-off-by: Takashi Iwai tiwai@suse.de Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- sound/core/seq/seq_clientmgr.c | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-)
--- a/sound/core/seq/seq_clientmgr.c +++ b/sound/core/seq/seq_clientmgr.c @@ -1014,7 +1014,7 @@ static ssize_t snd_seq_write(struct file { struct snd_seq_client *client = file->private_data; int written = 0, len; - int err; + int err, handled; struct snd_seq_event event;
if (!(snd_seq_file_flags(file) & SNDRV_SEQ_LFLG_OUTPUT)) @@ -1027,6 +1027,8 @@ static ssize_t snd_seq_write(struct file if (!client->accept_output || client->pool == NULL) return -ENXIO;
+ repeat: + handled = 0; /* allocate the pool now if the pool is not allocated yet */ mutex_lock(&client->ioctl_mutex); if (client->pool->size > 0 && !snd_seq_write_pool_allocated(client)) { @@ -1086,12 +1088,19 @@ static ssize_t snd_seq_write(struct file 0, 0, &client->ioctl_mutex); if (err < 0) break; + handled++;
__skip_event: /* Update pointers and counts */ count -= len; buf += len; written += len; + + /* let's have a coffee break if too many events are queued */ + if (++handled >= 200) { + mutex_unlock(&client->ioctl_mutex); + goto repeat; + } }
out:
From: Boris Brezillon boris.brezillon@collabora.com
commit 07d89227a983df957a6a7c56f7c040cde9ac571f upstream.
cfg->type can be overridden by v4l2_ctrl_fill() and the new value is stored in the local type var. Fix the tests to use this local var.
Fixes: 0996517cf8ea ("V4L/DVB: v4l2: Add new control handling framework") Cc: stable@vger.kernel.org Signed-off-by: Boris Brezillon boris.brezillon@collabora.com [hverkuil-cisco@xs4all.nl: change to !qmenu and !qmenu_int (checkpatch)] Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/media/v4l2-core/v4l2-ctrls.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-)
--- a/drivers/media/v4l2-core/v4l2-ctrls.c +++ b/drivers/media/v4l2-core/v4l2-ctrls.c @@ -2073,16 +2073,15 @@ struct v4l2_ctrl *v4l2_ctrl_new_custom(s v4l2_ctrl_fill(cfg->id, &name, &type, &min, &max, &step, &def, &flags);
- is_menu = (cfg->type == V4L2_CTRL_TYPE_MENU || - cfg->type == V4L2_CTRL_TYPE_INTEGER_MENU); + is_menu = (type == V4L2_CTRL_TYPE_MENU || + type == V4L2_CTRL_TYPE_INTEGER_MENU); if (is_menu) WARN_ON(step); else WARN_ON(cfg->menu_skip_mask); - if (cfg->type == V4L2_CTRL_TYPE_MENU && qmenu == NULL) + if (type == V4L2_CTRL_TYPE_MENU && !qmenu) { qmenu = v4l2_ctrl_get_menu(cfg->id); - else if (cfg->type == V4L2_CTRL_TYPE_INTEGER_MENU && - qmenu_int == NULL) { + } else if (type == V4L2_CTRL_TYPE_INTEGER_MENU && !qmenu_int) { handler_set_err(hdl, -EINVAL); return NULL; }
From: Ezequiel Garcia ezequiel@collabora.com
commit 766b9b168f6c75c350dd87c3e0bc6a9b322f0013 upstream.
The mutex unlock in the threaded interrupt handler is not paired with any mutex lock. Remove it.
This bug has been here for a really long time, so it applies to any stable repo.
Reviewed-by: Philipp Zabel p.zabel@pengutronix.de Signed-off-by: Ezequiel Garcia ezequiel@collabora.com Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Cc: stable@vger.kernel.org Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/media/platform/coda/coda-bit.c | 1 - 1 file changed, 1 deletion(-)
--- a/drivers/media/platform/coda/coda-bit.c +++ b/drivers/media/platform/coda/coda-bit.c @@ -2107,7 +2107,6 @@ irqreturn_t coda_irq_handler(int irq, vo if (ctx == NULL) { v4l2_err(&dev->v4l2_dev, "Instance released before the end of transaction\n"); - mutex_unlock(&dev->coda_mutex); return IRQ_HANDLED; }
From: Like Xu like.xu@linux.intel.com
commit 6fc3977ccc5d3c22e851f2dce2d3ce2a0a843842 upstream.
If a perf_event creation fails due to any reason of the host perf subsystem, it has no chance to log the corresponding event for guest which may cause abnormal sampling data in guest result. In debug mode, this message helps to understand the state of vPMC and we may not limit the number of occurrences but not in a spamming style.
Suggested-by: Joe Perches joe@perches.com Signed-off-by: Like Xu like.xu@linux.intel.com Cc: stable@vger.kernel.org Signed-off-by: Paolo Bonzini pbonzini@redhat.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/x86/kvm/pmu.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
--- a/arch/x86/kvm/pmu.c +++ b/arch/x86/kvm/pmu.c @@ -124,8 +124,8 @@ static void pmc_reprogram_counter(struct intr ? kvm_perf_overflow_intr : kvm_perf_overflow, pmc); if (IS_ERR(event)) { - printk_once("kvm_pmu: event creation failed %ld\n", - PTR_ERR(event)); + pr_debug_ratelimited("kvm_pmu: event creation failed %ld for pmc->idx = %d\n", + PTR_ERR(event), pmc->idx); return; }
From: Lyude Paul lyude@redhat.com
commit 7cb95eeea6706c790571042a06782e378b2561ea upstream.
It turns out that while disabling i2c bus access from software when the GPU is suspended was a step in the right direction with:
commit 342406e4fbba ("drm/nouveau/i2c: Disable i2c bus access after ->fini()")
We also ended up accidentally breaking the vbios init scripts on some older Tesla GPUs, as apparently said scripts can actually use the i2c bus. Since these scripts are executed before initializing any subdevices, we end up failing to acquire access to the i2c bus which has left a number of cards with their fan controllers uninitialized. Luckily this doesn't break hardware - it just means the fan gets stuck at 100%.
This also means that we've always been using our i2c busses before initializing them during the init scripts for older GPUs, we just didn't notice it until we started preventing them from being used until init. It's pretty impressive this never caused us any issues before!
So, fix this by initializing our i2c pad and busses during subdev pre-init. We skip initializing aux busses during pre-init, as those are guaranteed to only ever be used by nouveau for DP aux transactions.
Signed-off-by: Lyude Paul lyude@redhat.com Tested-by: Marc Meledandri m.meledandri@gmail.com Fixes: 342406e4fbba ("drm/nouveau/i2c: Disable i2c bus access after ->fini()") Cc: stable@vger.kernel.org Signed-off-by: Ben Skeggs bskeggs@redhat.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/gpu/drm/nouveau/nvkm/subdev/i2c/base.c | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+)
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/base.c +++ b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/base.c @@ -185,6 +185,25 @@ nvkm_i2c_fini(struct nvkm_subdev *subdev }
static int +nvkm_i2c_preinit(struct nvkm_subdev *subdev) +{ + struct nvkm_i2c *i2c = nvkm_i2c(subdev); + struct nvkm_i2c_bus *bus; + struct nvkm_i2c_pad *pad; + + /* + * We init our i2c busses as early as possible, since they may be + * needed by the vbios init scripts on some cards + */ + list_for_each_entry(pad, &i2c->pad, head) + nvkm_i2c_pad_init(pad); + list_for_each_entry(bus, &i2c->bus, head) + nvkm_i2c_bus_init(bus); + + return 0; +} + +static int nvkm_i2c_init(struct nvkm_subdev *subdev) { struct nvkm_i2c *i2c = nvkm_i2c(subdev); @@ -238,6 +257,7 @@ nvkm_i2c_dtor(struct nvkm_subdev *subdev static const struct nvkm_subdev_func nvkm_i2c = { .dtor = nvkm_i2c_dtor, + .preinit = nvkm_i2c_preinit, .init = nvkm_i2c_init, .fini = nvkm_i2c_fini, .intr = nvkm_i2c_intr,
From: Daniel Jordan daniel.m.jordan@oracle.com
commit cf144f81a99d1a3928f90b0936accfd3f45c9a0a upstream.
Testing padata with the tcrypt module on a 5.2 kernel...
# modprobe tcrypt alg="pcrypt(rfc4106(gcm(aes)))" type=3 # modprobe tcrypt mode=211 sec=1
...produces this splat:
INFO: task modprobe:10075 blocked for more than 120 seconds. Not tainted 5.2.0-base+ #16 modprobe D 0 10075 10064 0x80004080 Call Trace: ? __schedule+0x4dd/0x610 ? ring_buffer_unlock_commit+0x23/0x100 schedule+0x6c/0x90 schedule_timeout+0x3b/0x320 ? trace_buffer_unlock_commit_regs+0x4f/0x1f0 wait_for_common+0x160/0x1a0 ? wake_up_q+0x80/0x80 { crypto_wait_req } # entries in braces added by hand { do_one_aead_op } { test_aead_jiffies } test_aead_speed.constprop.17+0x681/0xf30 [tcrypt] do_test+0x4053/0x6a2b [tcrypt] ? 0xffffffffa00f4000 tcrypt_mod_init+0x50/0x1000 [tcrypt] ...
The second modprobe command never finishes because in padata_reorder, CPU0's load of reorder_objects is executed before the unlocking store in spin_unlock_bh(pd->lock), causing CPU0 to miss CPU1's increment:
CPU0 CPU1
padata_reorder padata_do_serial LOAD reorder_objects // 0 INC reorder_objects // 1 padata_reorder TRYLOCK pd->lock // failed UNLOCK pd->lock
CPU0 deletes the timer before returning from padata_reorder and since no other job is submitted to padata, modprobe waits indefinitely.
Add a pair of full barriers to guarantee proper ordering:
CPU0 CPU1
padata_reorder padata_do_serial UNLOCK pd->lock smp_mb() LOAD reorder_objects INC reorder_objects smp_mb__after_atomic() padata_reorder TRYLOCK pd->lock
smp_mb__after_atomic is needed so the read part of the trylock operation comes after the INC, as Andrea points out. Thanks also to Andrea for help with writing a litmus test.
Fixes: 16295bec6398 ("padata: Generic parallelization/serialization interface") Signed-off-by: Daniel Jordan daniel.m.jordan@oracle.com Cc: stable@vger.kernel.org Cc: Andrea Parri andrea.parri@amarulasolutions.com Cc: Boqun Feng boqun.feng@gmail.com Cc: Herbert Xu herbert@gondor.apana.org.au Cc: Paul E. McKenney paulmck@linux.ibm.com Cc: Peter Zijlstra peterz@infradead.org Cc: Steffen Klassert steffen.klassert@secunet.com Cc: linux-arch@vger.kernel.org Cc: linux-crypto@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- kernel/padata.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
--- a/kernel/padata.c +++ b/kernel/padata.c @@ -273,7 +273,12 @@ static void padata_reorder(struct parall * The next object that needs serialization might have arrived to * the reorder queues in the meantime, we will be called again * from the timer function if no one else cares for it. + * + * Ensure reorder_objects is read after pd->lock is dropped so we see + * an increment from another task in padata_do_serial. Pairs with + * smp_mb__after_atomic in padata_do_serial. */ + smp_mb(); if (atomic_read(&pd->reorder_objects) && !(pinst->flags & PADATA_RESET)) mod_timer(&pd->timer, jiffies + HZ); @@ -342,6 +347,13 @@ void padata_do_serial(struct padata_priv list_add_tail(&padata->list, &pqueue->reorder.list); spin_unlock(&pqueue->reorder.lock);
+ /* + * Ensure the atomic_inc of reorder_objects above is ordered correctly + * with the trylock of pd->lock in padata_reorder. Pairs with smp_mb + * in padata_reorder. + */ + smp_mb__after_atomic(); + put_cpu();
padata_reorder(pd);
From: YueHaibing yuehaibing@huawei.com
commit d4548543fc4ece56c6f04b8586f435fb4fd84c20 upstream.
KASAN report this:
BUG: unable to handle kernel paging request at ffffffffa0097000 PGD 3870067 P4D 3870067 PUD 3871063 PMD 2326e2067 PTE 0 Oops: 0000 [#1 CPU: 0 PID: 5340 Comm: modprobe Not tainted 5.1.0-rc7+ #25 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.9.3-0-ge2fc41e-prebuilt.qemu-project.org 04/01/2014 RIP: 0010:__list_add_valid+0x10/0x70 Code: c3 48 8b 06 55 48 89 e5 5d 48 39 07 0f 94 c0 0f b6 c0 c3 90 90 90 90 90 90 90 55 48 89 d0 48 8b 52 08 48 89 e5 48 39 f2 75 19 <48> 8b 32 48 39 f0 75 3a
RSP: 0018:ffffc90000e23c68 EFLAGS: 00010246 RAX: ffffffffa00ad000 RBX: ffffffffa009d000 RCX: 0000000000000000 RDX: ffffffffa0097000 RSI: ffffffffa0097000 RDI: ffffffffa009d000 RBP: ffffc90000e23c68 R08: 0000000000000001 R09: 0000000000000000 R10: 0000000000000000 R11: 0000000000000000 R12: ffffffffa0097000 R13: ffff888231797180 R14: 0000000000000000 R15: ffffc90000e23e78 FS: 00007fb215285540(0000) GS:ffff888237a00000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: ffffffffa0097000 CR3: 000000022f144000 CR4: 00000000000006f0 Call Trace: v9fs_register_trans+0x2f/0x60 [9pnet ? 0xffffffffa0087000 p9_virtio_init+0x25/0x1000 [9pnet_virtio do_one_initcall+0x6c/0x3cc ? kmem_cache_alloc_trace+0x248/0x3b0 do_init_module+0x5b/0x1f1 load_module+0x1db1/0x2690 ? m_show+0x1d0/0x1d0 __do_sys_finit_module+0xc5/0xd0 __x64_sys_finit_module+0x15/0x20 do_syscall_64+0x6b/0x1d0 entry_SYSCALL_64_after_hwframe+0x49/0xbe RIP: 0033:0x7fb214d8e839 Code: 00 f3 c3 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 40 00 48 89 f8 48 89 f7 48 89 d6 48 89 ca 4d 89 c2 4d 89 c8 4c 8b 4c 24 08 0f 05 <48> 3d 01 f0 ff ff 73 01
RSP: 002b:00007ffc96554278 EFLAGS: 00000246 ORIG_RAX: 0000000000000139 RAX: ffffffffffffffda RBX: 000055e67eed2aa0 RCX: 00007fb214d8e839 RDX: 0000000000000000 RSI: 000055e67ce95c2e RDI: 0000000000000003 RBP: 000055e67ce95c2e R08: 0000000000000000 R09: 000055e67eed2aa0 R10: 0000000000000003 R11: 0000000000000246 R12: 0000000000000000 R13: 000055e67eeda500 R14: 0000000000040000 R15: 000055e67eed2aa0 Modules linked in: 9pnet_virtio(+) 9pnet gre rfkill vmw_vsock_virtio_transport_common vsock [last unloaded: 9pnet_virtio CR2: ffffffffa0097000 ---[ end trace 4a52bb13ff07b761
If register_virtio_driver() fails in p9_virtio_init, we should call v9fs_unregister_trans() to do cleanup.
Link: http://lkml.kernel.org/r/20190430115942.41840-1-yuehaibing@huawei.com Cc: stable@vger.kernel.org Reported-by: Hulk Robot hulkci@huawei.com Fixes: b530cc794024 ("9p: add virtio transport") Signed-off-by: YueHaibing yuehaibing@huawei.com Signed-off-by: Dominique Martinet dominique.martinet@cea.fr Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- net/9p/trans_virtio.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
--- a/net/9p/trans_virtio.c +++ b/net/9p/trans_virtio.c @@ -767,10 +767,16 @@ static struct p9_trans_module p9_virtio_ /* The standard init function */ static int __init p9_virtio_init(void) { + int rc; + INIT_LIST_HEAD(&virtio_chan_list);
v9fs_register_trans(&p9_virtio_trans); - return register_virtio_driver(&p9_virtio_drv); + rc = register_virtio_driver(&p9_virtio_drv); + if (rc) + v9fs_unregister_trans(&p9_virtio_trans); + + return rc; }
static void __exit p9_virtio_cleanup(void)
From: Mika Westerberg mika.westerberg@linux.intel.com
commit 000dd5316e1c756a1c028f22e01d06a38249dd4d upstream.
PME polling does not take into account that a device that is directly connected to the host bridge may go into D3cold as well. This leads to a situation where the PME poll thread reads from a config space of a device that is in D3cold and gets incorrect information because the config space is not accessible.
Here is an example from Intel Ice Lake system where two PCIe root ports are in D3cold (I've instrumented the kernel to log the PMCSR register contents):
[ 62.971442] pcieport 0000:00:07.1: Check PME status, PMCSR=0xffff [ 62.971504] pcieport 0000:00:07.0: Check PME status, PMCSR=0xffff
Since 0xffff is interpreted so that PME is pending, the root ports will be runtime resumed. This repeats over and over again essentially blocking all runtime power management.
Prevent this from happening by checking whether the device is in D3cold before its PME status is read.
Fixes: 71a83bd727cc ("PCI/PM: add runtime PM support to PCIe port") Signed-off-by: Mika Westerberg mika.westerberg@linux.intel.com Reviewed-by: Lukas Wunner lukas@wunner.de Cc: 3.6+ stable@vger.kernel.org # v3.6+ Signed-off-by: Rafael J. Wysocki rafael.j.wysocki@intel.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/pci/pci.c | 7 +++++++ 1 file changed, 7 insertions(+)
--- a/drivers/pci/pci.c +++ b/drivers/pci/pci.c @@ -1736,6 +1736,13 @@ static void pci_pme_list_scan(struct wor */ if (bridge && bridge->current_state != PCI_D0) continue; + /* + * If the device is in D3cold it should not be + * polled either. + */ + if (pme_dev->dev->current_state == PCI_D3cold) + continue; + pci_pme_wakeup(pme_dev->dev, NULL); } else { list_del(&pme_dev->list);
[ Upstream commit 229b53c9bf4e1132a4aa6feb9632a7a1f1d08c5c ]
all other drivers recognizing those ioctls are very much *not* biarch.
Signed-off-by: Al Viro viro@zeniv.linux.org.uk Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- block/compat_ioctl.c | 340 ------------------------------------------------- drivers/block/floppy.c | 328 +++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 328 insertions(+), 340 deletions(-)
--- a/block/compat_ioctl.c +++ b/block/compat_ioctl.c @@ -4,7 +4,6 @@ #include <linux/cdrom.h> #include <linux/compat.h> #include <linux/elevator.h> -#include <linux/fd.h> #include <linux/hdreg.h> #include <linux/slab.h> #include <linux/syscalls.h> @@ -209,318 +208,6 @@ static int compat_blkpg_ioctl(struct blo #define BLKBSZSET_32 _IOW(0x12, 113, int) #define BLKGETSIZE64_32 _IOR(0x12, 114, int)
-struct compat_floppy_drive_params { - char cmos; - compat_ulong_t max_dtr; - compat_ulong_t hlt; - compat_ulong_t hut; - compat_ulong_t srt; - compat_ulong_t spinup; - compat_ulong_t spindown; - unsigned char spindown_offset; - unsigned char select_delay; - unsigned char rps; - unsigned char tracks; - compat_ulong_t timeout; - unsigned char interleave_sect; - struct floppy_max_errors max_errors; - char flags; - char read_track; - short autodetect[8]; - compat_int_t checkfreq; - compat_int_t native_format; -}; - -struct compat_floppy_drive_struct { - signed char flags; - compat_ulong_t spinup_date; - compat_ulong_t select_date; - compat_ulong_t first_read_date; - short probed_format; - short track; - short maxblock; - short maxtrack; - compat_int_t generation; - compat_int_t keep_data; - compat_int_t fd_ref; - compat_int_t fd_device; - compat_int_t last_checked; - compat_caddr_t dmabuf; - compat_int_t bufblocks; -}; - -struct compat_floppy_fdc_state { - compat_int_t spec1; - compat_int_t spec2; - compat_int_t dtr; - unsigned char version; - unsigned char dor; - compat_ulong_t address; - unsigned int rawcmd:2; - unsigned int reset:1; - unsigned int need_configure:1; - unsigned int perp_mode:2; - unsigned int has_fifo:1; - unsigned int driver_version; - unsigned char track[4]; -}; - -struct compat_floppy_write_errors { - unsigned int write_errors; - compat_ulong_t first_error_sector; - compat_int_t first_error_generation; - compat_ulong_t last_error_sector; - compat_int_t last_error_generation; - compat_uint_t badness; -}; - -#define FDSETPRM32 _IOW(2, 0x42, struct compat_floppy_struct) -#define FDDEFPRM32 _IOW(2, 0x43, struct compat_floppy_struct) -#define FDSETDRVPRM32 _IOW(2, 0x90, struct compat_floppy_drive_params) -#define FDGETDRVPRM32 _IOR(2, 0x11, struct compat_floppy_drive_params) -#define FDGETDRVSTAT32 _IOR(2, 0x12, struct compat_floppy_drive_struct) -#define FDPOLLDRVSTAT32 _IOR(2, 0x13, struct compat_floppy_drive_struct) -#define FDGETFDCSTAT32 _IOR(2, 0x15, struct compat_floppy_fdc_state) -#define FDWERRORGET32 _IOR(2, 0x17, struct compat_floppy_write_errors) - -static struct { - unsigned int cmd32; - unsigned int cmd; -} fd_ioctl_trans_table[] = { - { FDSETPRM32, FDSETPRM }, - { FDDEFPRM32, FDDEFPRM }, - { FDGETPRM32, FDGETPRM }, - { FDSETDRVPRM32, FDSETDRVPRM }, - { FDGETDRVPRM32, FDGETDRVPRM }, - { FDGETDRVSTAT32, FDGETDRVSTAT }, - { FDPOLLDRVSTAT32, FDPOLLDRVSTAT }, - { FDGETFDCSTAT32, FDGETFDCSTAT }, - { FDWERRORGET32, FDWERRORGET } -}; - -#define NR_FD_IOCTL_TRANS ARRAY_SIZE(fd_ioctl_trans_table) - -static int compat_fd_ioctl(struct block_device *bdev, fmode_t mode, - unsigned int cmd, unsigned long arg) -{ - mm_segment_t old_fs = get_fs(); - void *karg = NULL; - unsigned int kcmd = 0; - int i, err; - - for (i = 0; i < NR_FD_IOCTL_TRANS; i++) - if (cmd == fd_ioctl_trans_table[i].cmd32) { - kcmd = fd_ioctl_trans_table[i].cmd; - break; - } - if (!kcmd) - return -EINVAL; - - switch (cmd) { - case FDSETPRM32: - case FDDEFPRM32: - case FDGETPRM32: - { - compat_uptr_t name; - struct compat_floppy_struct __user *uf; - struct floppy_struct *f; - - uf = compat_ptr(arg); - f = karg = kmalloc(sizeof(struct floppy_struct), GFP_KERNEL); - if (!karg) - return -ENOMEM; - if (cmd == FDGETPRM32) - break; - err = __get_user(f->size, &uf->size); - err |= __get_user(f->sect, &uf->sect); - err |= __get_user(f->head, &uf->head); - err |= __get_user(f->track, &uf->track); - err |= __get_user(f->stretch, &uf->stretch); - err |= __get_user(f->gap, &uf->gap); - err |= __get_user(f->rate, &uf->rate); - err |= __get_user(f->spec1, &uf->spec1); - err |= __get_user(f->fmt_gap, &uf->fmt_gap); - err |= __get_user(name, &uf->name); - f->name = compat_ptr(name); - if (err) { - err = -EFAULT; - goto out; - } - break; - } - case FDSETDRVPRM32: - case FDGETDRVPRM32: - { - struct compat_floppy_drive_params __user *uf; - struct floppy_drive_params *f; - - uf = compat_ptr(arg); - f = karg = kmalloc(sizeof(struct floppy_drive_params), GFP_KERNEL); - if (!karg) - return -ENOMEM; - if (cmd == FDGETDRVPRM32) - break; - err = __get_user(f->cmos, &uf->cmos); - err |= __get_user(f->max_dtr, &uf->max_dtr); - err |= __get_user(f->hlt, &uf->hlt); - err |= __get_user(f->hut, &uf->hut); - err |= __get_user(f->srt, &uf->srt); - err |= __get_user(f->spinup, &uf->spinup); - err |= __get_user(f->spindown, &uf->spindown); - err |= __get_user(f->spindown_offset, &uf->spindown_offset); - err |= __get_user(f->select_delay, &uf->select_delay); - err |= __get_user(f->rps, &uf->rps); - err |= __get_user(f->tracks, &uf->tracks); - err |= __get_user(f->timeout, &uf->timeout); - err |= __get_user(f->interleave_sect, &uf->interleave_sect); - err |= __copy_from_user(&f->max_errors, &uf->max_errors, sizeof(f->max_errors)); - err |= __get_user(f->flags, &uf->flags); - err |= __get_user(f->read_track, &uf->read_track); - err |= __copy_from_user(f->autodetect, uf->autodetect, sizeof(f->autodetect)); - err |= __get_user(f->checkfreq, &uf->checkfreq); - err |= __get_user(f->native_format, &uf->native_format); - if (err) { - err = -EFAULT; - goto out; - } - break; - } - case FDGETDRVSTAT32: - case FDPOLLDRVSTAT32: - karg = kmalloc(sizeof(struct floppy_drive_struct), GFP_KERNEL); - if (!karg) - return -ENOMEM; - break; - case FDGETFDCSTAT32: - karg = kmalloc(sizeof(struct floppy_fdc_state), GFP_KERNEL); - if (!karg) - return -ENOMEM; - break; - case FDWERRORGET32: - karg = kmalloc(sizeof(struct floppy_write_errors), GFP_KERNEL); - if (!karg) - return -ENOMEM; - break; - default: - return -EINVAL; - } - set_fs(KERNEL_DS); - err = __blkdev_driver_ioctl(bdev, mode, kcmd, (unsigned long)karg); - set_fs(old_fs); - if (err) - goto out; - switch (cmd) { - case FDGETPRM32: - { - struct floppy_struct *f = karg; - struct compat_floppy_struct __user *uf = compat_ptr(arg); - - err = __put_user(f->size, &uf->size); - err |= __put_user(f->sect, &uf->sect); - err |= __put_user(f->head, &uf->head); - err |= __put_user(f->track, &uf->track); - err |= __put_user(f->stretch, &uf->stretch); - err |= __put_user(f->gap, &uf->gap); - err |= __put_user(f->rate, &uf->rate); - err |= __put_user(f->spec1, &uf->spec1); - err |= __put_user(f->fmt_gap, &uf->fmt_gap); - err |= __put_user((u64)f->name, (compat_caddr_t __user *)&uf->name); - break; - } - case FDGETDRVPRM32: - { - struct compat_floppy_drive_params __user *uf; - struct floppy_drive_params *f = karg; - - uf = compat_ptr(arg); - err = __put_user(f->cmos, &uf->cmos); - err |= __put_user(f->max_dtr, &uf->max_dtr); - err |= __put_user(f->hlt, &uf->hlt); - err |= __put_user(f->hut, &uf->hut); - err |= __put_user(f->srt, &uf->srt); - err |= __put_user(f->spinup, &uf->spinup); - err |= __put_user(f->spindown, &uf->spindown); - err |= __put_user(f->spindown_offset, &uf->spindown_offset); - err |= __put_user(f->select_delay, &uf->select_delay); - err |= __put_user(f->rps, &uf->rps); - err |= __put_user(f->tracks, &uf->tracks); - err |= __put_user(f->timeout, &uf->timeout); - err |= __put_user(f->interleave_sect, &uf->interleave_sect); - err |= __copy_to_user(&uf->max_errors, &f->max_errors, sizeof(f->max_errors)); - err |= __put_user(f->flags, &uf->flags); - err |= __put_user(f->read_track, &uf->read_track); - err |= __copy_to_user(uf->autodetect, f->autodetect, sizeof(f->autodetect)); - err |= __put_user(f->checkfreq, &uf->checkfreq); - err |= __put_user(f->native_format, &uf->native_format); - break; - } - case FDGETDRVSTAT32: - case FDPOLLDRVSTAT32: - { - struct compat_floppy_drive_struct __user *uf; - struct floppy_drive_struct *f = karg; - - uf = compat_ptr(arg); - err = __put_user(f->flags, &uf->flags); - err |= __put_user(f->spinup_date, &uf->spinup_date); - err |= __put_user(f->select_date, &uf->select_date); - err |= __put_user(f->first_read_date, &uf->first_read_date); - err |= __put_user(f->probed_format, &uf->probed_format); - err |= __put_user(f->track, &uf->track); - err |= __put_user(f->maxblock, &uf->maxblock); - err |= __put_user(f->maxtrack, &uf->maxtrack); - err |= __put_user(f->generation, &uf->generation); - err |= __put_user(f->keep_data, &uf->keep_data); - err |= __put_user(f->fd_ref, &uf->fd_ref); - err |= __put_user(f->fd_device, &uf->fd_device); - err |= __put_user(f->last_checked, &uf->last_checked); - err |= __put_user((u64)f->dmabuf, &uf->dmabuf); - err |= __put_user((u64)f->bufblocks, &uf->bufblocks); - break; - } - case FDGETFDCSTAT32: - { - struct compat_floppy_fdc_state __user *uf; - struct floppy_fdc_state *f = karg; - - uf = compat_ptr(arg); - err = __put_user(f->spec1, &uf->spec1); - err |= __put_user(f->spec2, &uf->spec2); - err |= __put_user(f->dtr, &uf->dtr); - err |= __put_user(f->version, &uf->version); - err |= __put_user(f->dor, &uf->dor); - err |= __put_user(f->address, &uf->address); - err |= __copy_to_user((char __user *)&uf->address + sizeof(uf->address), - (char *)&f->address + sizeof(f->address), sizeof(int)); - err |= __put_user(f->driver_version, &uf->driver_version); - err |= __copy_to_user(uf->track, f->track, sizeof(f->track)); - break; - } - case FDWERRORGET32: - { - struct compat_floppy_write_errors __user *uf; - struct floppy_write_errors *f = karg; - - uf = compat_ptr(arg); - err = __put_user(f->write_errors, &uf->write_errors); - err |= __put_user(f->first_error_sector, &uf->first_error_sector); - err |= __put_user(f->first_error_generation, &uf->first_error_generation); - err |= __put_user(f->last_error_sector, &uf->last_error_sector); - err |= __put_user(f->last_error_generation, &uf->last_error_generation); - err |= __put_user(f->badness, &uf->badness); - break; - } - default: - break; - } - if (err) - err = -EFAULT; - -out: - kfree(karg); - return err; -} - static int compat_blkdev_driver_ioctl(struct block_device *bdev, fmode_t mode, unsigned cmd, unsigned long arg) { @@ -537,16 +224,6 @@ static int compat_blkdev_driver_ioctl(st case HDIO_GET_ADDRESS: case HDIO_GET_BUSSTATE: return compat_hdio_ioctl(bdev, mode, cmd, arg); - case FDSETPRM32: - case FDDEFPRM32: - case FDGETPRM32: - case FDSETDRVPRM32: - case FDGETDRVPRM32: - case FDGETDRVSTAT32: - case FDPOLLDRVSTAT32: - case FDGETFDCSTAT32: - case FDWERRORGET32: - return compat_fd_ioctl(bdev, mode, cmd, arg); case CDROMREADAUDIO: return compat_cdrom_read_audio(bdev, mode, cmd, arg); case CDROM_SEND_PACKET: @@ -566,23 +243,6 @@ static int compat_blkdev_driver_ioctl(st case HDIO_DRIVE_CMD: /* 0x330 is reserved -- it used to be HDIO_GETGEO_BIG */ case 0x330: - /* 0x02 -- Floppy ioctls */ - case FDMSGON: - case FDMSGOFF: - case FDSETEMSGTRESH: - case FDFLUSH: - case FDWERRORCLR: - case FDSETMAXERRS: - case FDGETMAXERRS: - case FDGETDRVTYP: - case FDEJECT: - case FDCLRPRM: - case FDFMTBEG: - case FDFMTEND: - case FDRESET: - case FDTWADDLE: - case FDFMTTRK: - case FDRAWCMD: /* CDROM stuff */ case CDROMPAUSE: case CDROMRESUME: --- a/drivers/block/floppy.c +++ b/drivers/block/floppy.c @@ -192,6 +192,7 @@ static int print_unex = 1; #include <linux/io.h> #include <linux/uaccess.h> #include <linux/async.h> +#include <linux/compat.h>
/* * PS/2 floppies have much slower step rates than regular floppies. @@ -3569,6 +3570,330 @@ static int fd_ioctl(struct block_device return ret; }
+#ifdef CONFIG_COMPAT + +struct compat_floppy_drive_params { + char cmos; + compat_ulong_t max_dtr; + compat_ulong_t hlt; + compat_ulong_t hut; + compat_ulong_t srt; + compat_ulong_t spinup; + compat_ulong_t spindown; + unsigned char spindown_offset; + unsigned char select_delay; + unsigned char rps; + unsigned char tracks; + compat_ulong_t timeout; + unsigned char interleave_sect; + struct floppy_max_errors max_errors; + char flags; + char read_track; + short autodetect[8]; + compat_int_t checkfreq; + compat_int_t native_format; +}; + +struct compat_floppy_drive_struct { + signed char flags; + compat_ulong_t spinup_date; + compat_ulong_t select_date; + compat_ulong_t first_read_date; + short probed_format; + short track; + short maxblock; + short maxtrack; + compat_int_t generation; + compat_int_t keep_data; + compat_int_t fd_ref; + compat_int_t fd_device; + compat_int_t last_checked; + compat_caddr_t dmabuf; + compat_int_t bufblocks; +}; + +struct compat_floppy_fdc_state { + compat_int_t spec1; + compat_int_t spec2; + compat_int_t dtr; + unsigned char version; + unsigned char dor; + compat_ulong_t address; + unsigned int rawcmd:2; + unsigned int reset:1; + unsigned int need_configure:1; + unsigned int perp_mode:2; + unsigned int has_fifo:1; + unsigned int driver_version; + unsigned char track[4]; +}; + +struct compat_floppy_write_errors { + unsigned int write_errors; + compat_ulong_t first_error_sector; + compat_int_t first_error_generation; + compat_ulong_t last_error_sector; + compat_int_t last_error_generation; + compat_uint_t badness; +}; + +#define FDSETPRM32 _IOW(2, 0x42, struct compat_floppy_struct) +#define FDDEFPRM32 _IOW(2, 0x43, struct compat_floppy_struct) +#define FDSETDRVPRM32 _IOW(2, 0x90, struct compat_floppy_drive_params) +#define FDGETDRVPRM32 _IOR(2, 0x11, struct compat_floppy_drive_params) +#define FDGETDRVSTAT32 _IOR(2, 0x12, struct compat_floppy_drive_struct) +#define FDPOLLDRVSTAT32 _IOR(2, 0x13, struct compat_floppy_drive_struct) +#define FDGETFDCSTAT32 _IOR(2, 0x15, struct compat_floppy_fdc_state) +#define FDWERRORGET32 _IOR(2, 0x17, struct compat_floppy_write_errors) + +static int compat_set_geometry(struct block_device *bdev, fmode_t mode, unsigned int cmd, + struct compat_floppy_struct __user *arg) +{ + struct floppy_struct v; + int drive, type; + int err; + + BUILD_BUG_ON(offsetof(struct floppy_struct, name) != + offsetof(struct compat_floppy_struct, name)); + + if (!(mode & (FMODE_WRITE | FMODE_WRITE_IOCTL))) + return -EPERM; + + memset(&v, 0, sizeof(struct floppy_struct)); + if (copy_from_user(&v, arg, offsetof(struct floppy_struct, name))) + return -EFAULT; + + mutex_lock(&floppy_mutex); + drive = (long)bdev->bd_disk->private_data; + type = ITYPE(UDRS->fd_device); + err = set_geometry(cmd == FDSETPRM32 ? FDSETPRM : FDDEFPRM, + &v, drive, type, bdev); + mutex_unlock(&floppy_mutex); + return err; +} + +static int compat_get_prm(int drive, + struct compat_floppy_struct __user *arg) +{ + struct compat_floppy_struct v; + struct floppy_struct *p; + int err; + + memset(&v, 0, sizeof(v)); + mutex_lock(&floppy_mutex); + err = get_floppy_geometry(drive, ITYPE(UDRS->fd_device), &p); + if (err) { + mutex_unlock(&floppy_mutex); + return err; + } + memcpy(&v, p, offsetof(struct floppy_struct, name)); + mutex_unlock(&floppy_mutex); + if (copy_to_user(arg, &v, sizeof(struct compat_floppy_struct))) + return -EFAULT; + return 0; +} + +static int compat_setdrvprm(int drive, + struct compat_floppy_drive_params __user *arg) +{ + struct compat_floppy_drive_params v; + + if (!capable(CAP_SYS_ADMIN)) + return -EPERM; + if (copy_from_user(&v, arg, sizeof(struct compat_floppy_drive_params))) + return -EFAULT; + mutex_lock(&floppy_mutex); + UDP->cmos = v.cmos; + UDP->max_dtr = v.max_dtr; + UDP->hlt = v.hlt; + UDP->hut = v.hut; + UDP->srt = v.srt; + UDP->spinup = v.spinup; + UDP->spindown = v.spindown; + UDP->spindown_offset = v.spindown_offset; + UDP->select_delay = v.select_delay; + UDP->rps = v.rps; + UDP->tracks = v.tracks; + UDP->timeout = v.timeout; + UDP->interleave_sect = v.interleave_sect; + UDP->max_errors = v.max_errors; + UDP->flags = v.flags; + UDP->read_track = v.read_track; + memcpy(UDP->autodetect, v.autodetect, sizeof(v.autodetect)); + UDP->checkfreq = v.checkfreq; + UDP->native_format = v.native_format; + mutex_unlock(&floppy_mutex); + return 0; +} + +static int compat_getdrvprm(int drive, + struct compat_floppy_drive_params __user *arg) +{ + struct compat_floppy_drive_params v; + + memset(&v, 0, sizeof(struct compat_floppy_drive_params)); + mutex_lock(&floppy_mutex); + v.cmos = UDP->cmos; + v.max_dtr = UDP->max_dtr; + v.hlt = UDP->hlt; + v.hut = UDP->hut; + v.srt = UDP->srt; + v.spinup = UDP->spinup; + v.spindown = UDP->spindown; + v.spindown_offset = UDP->spindown_offset; + v.select_delay = UDP->select_delay; + v.rps = UDP->rps; + v.tracks = UDP->tracks; + v.timeout = UDP->timeout; + v.interleave_sect = UDP->interleave_sect; + v.max_errors = UDP->max_errors; + v.flags = UDP->flags; + v.read_track = UDP->read_track; + memcpy(v.autodetect, UDP->autodetect, sizeof(v.autodetect)); + v.checkfreq = UDP->checkfreq; + v.native_format = UDP->native_format; + mutex_unlock(&floppy_mutex); + + if (copy_from_user(arg, &v, sizeof(struct compat_floppy_drive_params))) + return -EFAULT; + return 0; +} + +static int compat_getdrvstat(int drive, bool poll, + struct compat_floppy_drive_struct __user *arg) +{ + struct compat_floppy_drive_struct v; + + memset(&v, 0, sizeof(struct compat_floppy_drive_struct)); + mutex_lock(&floppy_mutex); + + if (poll) { + if (lock_fdc(drive, true)) + goto Eintr; + if (poll_drive(true, FD_RAW_NEED_DISK) == -EINTR) + goto Eintr; + process_fd_request(); + } + v.spinup_date = UDRS->spinup_date; + v.select_date = UDRS->select_date; + v.first_read_date = UDRS->first_read_date; + v.probed_format = UDRS->probed_format; + v.track = UDRS->track; + v.maxblock = UDRS->maxblock; + v.maxtrack = UDRS->maxtrack; + v.generation = UDRS->generation; + v.keep_data = UDRS->keep_data; + v.fd_ref = UDRS->fd_ref; + v.fd_device = UDRS->fd_device; + v.last_checked = UDRS->last_checked; + v.dmabuf = (uintptr_t)UDRS->dmabuf; + v.bufblocks = UDRS->bufblocks; + mutex_unlock(&floppy_mutex); + + if (copy_from_user(arg, &v, sizeof(struct compat_floppy_drive_struct))) + return -EFAULT; + return 0; +Eintr: + mutex_unlock(&floppy_mutex); + return -EINTR; +} + +static int compat_getfdcstat(int drive, + struct compat_floppy_fdc_state __user *arg) +{ + struct compat_floppy_fdc_state v32; + struct floppy_fdc_state v; + + mutex_lock(&floppy_mutex); + v = *UFDCS; + mutex_unlock(&floppy_mutex); + + memset(&v32, 0, sizeof(struct compat_floppy_fdc_state)); + v32.spec1 = v.spec1; + v32.spec2 = v.spec2; + v32.dtr = v.dtr; + v32.version = v.version; + v32.dor = v.dor; + v32.address = v.address; + v32.rawcmd = v.rawcmd; + v32.reset = v.reset; + v32.need_configure = v.need_configure; + v32.perp_mode = v.perp_mode; + v32.has_fifo = v.has_fifo; + v32.driver_version = v.driver_version; + memcpy(v32.track, v.track, 4); + if (copy_to_user(arg, &v32, sizeof(struct compat_floppy_fdc_state))) + return -EFAULT; + return 0; +} + +static int compat_werrorget(int drive, + struct compat_floppy_write_errors __user *arg) +{ + struct compat_floppy_write_errors v32; + struct floppy_write_errors v; + + memset(&v32, 0, sizeof(struct compat_floppy_write_errors)); + mutex_lock(&floppy_mutex); + v = *UDRWE; + mutex_unlock(&floppy_mutex); + v32.write_errors = v.write_errors; + v32.first_error_sector = v.first_error_sector; + v32.first_error_generation = v.first_error_generation; + v32.last_error_sector = v.last_error_sector; + v32.last_error_generation = v.last_error_generation; + v32.badness = v.badness; + if (copy_to_user(arg, &v32, sizeof(struct compat_floppy_write_errors))) + return -EFAULT; + return 0; +} + +static int fd_compat_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, + unsigned long param) +{ + int drive = (long)bdev->bd_disk->private_data; + switch (cmd) { + case FDMSGON: + case FDMSGOFF: + case FDSETEMSGTRESH: + case FDFLUSH: + case FDWERRORCLR: + case FDEJECT: + case FDCLRPRM: + case FDFMTBEG: + case FDRESET: + case FDTWADDLE: + return fd_ioctl(bdev, mode, cmd, param); + case FDSETMAXERRS: + case FDGETMAXERRS: + case FDGETDRVTYP: + case FDFMTEND: + case FDFMTTRK: + case FDRAWCMD: + return fd_ioctl(bdev, mode, cmd, + (unsigned long)compat_ptr(param)); + case FDSETPRM32: + case FDDEFPRM32: + return compat_set_geometry(bdev, mode, cmd, compat_ptr(param)); + case FDGETPRM32: + return compat_get_prm(drive, compat_ptr(param)); + case FDSETDRVPRM32: + return compat_setdrvprm(drive, compat_ptr(param)); + case FDGETDRVPRM32: + return compat_getdrvprm(drive, compat_ptr(param)); + case FDPOLLDRVSTAT32: + return compat_getdrvstat(drive, true, compat_ptr(param)); + case FDGETDRVSTAT32: + return compat_getdrvstat(drive, false, compat_ptr(param)); + case FDGETFDCSTAT32: + return compat_getfdcstat(drive, compat_ptr(param)); + case FDWERRORGET32: + return compat_werrorget(drive, compat_ptr(param)); + } + return -EINVAL; +} +#endif + static void __init config_types(void) { bool has_drive = false; @@ -3885,6 +4210,9 @@ static const struct block_device_operati .getgeo = fd_getgeo, .check_events = floppy_check_events, .revalidate_disk = floppy_revalidate, +#ifdef CONFIG_COMPAT + .compat_ioctl = fd_compat_ioctl, +#endif };
/*
[ Upstream commit f3554aeb991214cbfafd17d55e2bfddb50282e32 ]
This fixes a divide by zero error in the setup_format_params function of the floppy driver.
Two consecutive ioctls can trigger the bug: The first one should set the drive geometry with such .sect and .rate values for the F_SECT_PER_TRACK to become zero. Next, the floppy format operation should be called.
A floppy disk is not required to be inserted. An unprivileged user could trigger the bug if the device is accessible.
The patch checks F_SECT_PER_TRACK for a non-zero value in the set_geometry function. The proper check should involve a reasonable upper limit for the .sect and .rate fields, but it could change the UAPI.
The patch also checks F_SECT_PER_TRACK in the setup_format_params, and cancels the formatting operation in case of zero.
The bug was found by syzkaller.
Signed-off-by: Denis Efremov efremov@ispras.ru Tested-by: Willy Tarreau w@1wt.eu Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/block/floppy.c | 5 +++++ 1 file changed, 5 insertions(+)
--- a/drivers/block/floppy.c +++ b/drivers/block/floppy.c @@ -2114,6 +2114,9 @@ static void setup_format_params(int trac raw_cmd->kernel_data = floppy_track_buffer; raw_cmd->length = 4 * F_SECT_PER_TRACK;
+ if (!F_SECT_PER_TRACK) + return; + /* allow for about 30ms for data transport per track */ head_shift = (F_SECT_PER_TRACK + 5) / 6;
@@ -3236,6 +3239,8 @@ static int set_geometry(unsigned int cmd /* sanity checking for parameters. */ if (g->sect <= 0 || g->head <= 0 || + /* check for zero in F_SECT_PER_TRACK */ + (unsigned char)((g->sect << 2) >> FD_SIZECODE(g)) == 0 || g->track <= 0 || g->track > UDP->tracks >> STRETCH(g) || /* check if reserved bits are set */ (g->stretch & ~(FD_STRETCH | FD_SWAPSIDES | FD_SECTBASEMASK)) != 0)
[ Upstream commit 5635f897ed83fd539df78e98ba69ee91592f9bb8 ]
This fixes a global out-of-bounds read access in the next_valid_format function of the floppy driver.
The values from autodetect field of the struct floppy_drive_params are used as indices for the floppy_type array in the next_valid_format function 'floppy_type[DP->autodetect[probed_format]].sect'.
To trigger the bug, one could use a value out of range and set the drive parameters with the FDSETDRVPRM ioctl. A floppy disk is not required to be inserted.
CAP_SYS_ADMIN is required to call FDSETDRVPRM.
The patch adds the check for values of the autodetect field to be in the '0 <= x < ARRAY_SIZE(floppy_type)' range of the floppy_type array indices.
The bug was found by syzkaller.
Signed-off-by: Denis Efremov efremov@ispras.ru Tested-by: Willy Tarreau w@1wt.eu Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/block/floppy.c | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+)
--- a/drivers/block/floppy.c +++ b/drivers/block/floppy.c @@ -3384,6 +3384,20 @@ static int fd_getgeo(struct block_device return 0; }
+static bool valid_floppy_drive_params(const short autodetect[8]) +{ + size_t floppy_type_size = ARRAY_SIZE(floppy_type); + size_t i = 0; + + for (i = 0; i < 8; ++i) { + if (autodetect[i] < 0 || + autodetect[i] >= floppy_type_size) + return false; + } + + return true; +} + static int fd_locked_ioctl(struct block_device *bdev, fmode_t mode, unsigned int cmd, unsigned long param) { @@ -3510,6 +3524,8 @@ static int fd_locked_ioctl(struct block_ SUPBOUND(size, strlen((const char *)outparam) + 1); break; case FDSETDRVPRM: + if (!valid_floppy_drive_params(inparam.dp.autodetect)) + return -EINVAL; *UDP = inparam.dp; break; case FDGETDRVPRM: @@ -3707,6 +3723,8 @@ static int compat_setdrvprm(int drive, return -EPERM; if (copy_from_user(&v, arg, sizeof(struct compat_floppy_drive_params))) return -EFAULT; + if (!valid_floppy_drive_params(v.autodetect)) + return -EINVAL; mutex_lock(&floppy_mutex); UDP->cmos = v.cmos; UDP->max_dtr = v.max_dtr;
[ Upstream commit 9b04609b784027968348796a18f601aed9db3789 ]
This fixes the invalid pointer dereference in the drive_name function of the floppy driver.
The native_format field of the struct floppy_drive_params is used as floppy_type array index in the drive_name function. Thus, the field should be checked the same way as the autodetect field.
To trigger the bug, one could use a value out of range and set the drive parameters with the FDSETDRVPRM ioctl. Next, FDGETDRVTYP ioctl should be used to call the drive_name. A floppy disk is not required to be inserted.
CAP_SYS_ADMIN is required to call FDSETDRVPRM.
The patch adds the check for a value of the native_format field to be in the '0 <= x < ARRAY_SIZE(floppy_type)' range of the floppy_type array indices.
The bug was found by syzkaller.
Signed-off-by: Denis Efremov efremov@ispras.ru Tested-by: Willy Tarreau w@1wt.eu Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/block/floppy.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-)
--- a/drivers/block/floppy.c +++ b/drivers/block/floppy.c @@ -3384,7 +3384,8 @@ static int fd_getgeo(struct block_device return 0; }
-static bool valid_floppy_drive_params(const short autodetect[8]) +static bool valid_floppy_drive_params(const short autodetect[8], + int native_format) { size_t floppy_type_size = ARRAY_SIZE(floppy_type); size_t i = 0; @@ -3395,6 +3396,9 @@ static bool valid_floppy_drive_params(co return false; }
+ if (native_format < 0 || native_format >= floppy_type_size) + return false; + return true; }
@@ -3524,7 +3528,8 @@ static int fd_locked_ioctl(struct block_ SUPBOUND(size, strlen((const char *)outparam) + 1); break; case FDSETDRVPRM: - if (!valid_floppy_drive_params(inparam.dp.autodetect)) + if (!valid_floppy_drive_params(inparam.dp.autodetect, + inparam.dp.native_format)) return -EINVAL; *UDP = inparam.dp; break; @@ -3723,7 +3728,7 @@ static int compat_setdrvprm(int drive, return -EPERM; if (copy_from_user(&v, arg, sizeof(struct compat_floppy_drive_params))) return -EFAULT; - if (!valid_floppy_drive_params(v.autodetect)) + if (!valid_floppy_drive_params(v.autodetect, v.native_format)) return -EINVAL; mutex_lock(&floppy_mutex); UDP->cmos = v.cmos;
[ Upstream commit da99466ac243f15fbba65bd261bfc75ffa1532b6 ]
This fixes a global out-of-bounds read access in the copy_buffer function of the floppy driver.
The FDDEFPRM ioctl allows one to set the geometry of a disk. The sect and head fields (unsigned int) of the floppy_drive structure are used to compute the max_sector (int) in the make_raw_rw_request function. It is possible to overflow the max_sector. Next, max_sector is passed to the copy_buffer function and used in one of the memcpy calls.
An unprivileged user could trigger the bug if the device is accessible, but requires a floppy disk to be inserted.
The patch adds the check for the .sect * .head multiplication for not overflowing in the set_geometry function.
The bug was found by syzkaller.
Signed-off-by: Denis Efremov efremov@ispras.ru Tested-by: Willy Tarreau w@1wt.eu Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/block/floppy.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
--- a/drivers/block/floppy.c +++ b/drivers/block/floppy.c @@ -3237,8 +3237,10 @@ static int set_geometry(unsigned int cmd int cnt;
/* sanity checking for parameters. */ - if (g->sect <= 0 || - g->head <= 0 || + if ((int)g->sect <= 0 || + (int)g->head <= 0 || + /* check for overflow in max_sector */ + (int)(g->sect * g->head) <= 0 || /* check for zero in F_SECT_PER_TRACK */ (unsigned char)((g->sect << 2) >> FD_SIZECODE(g)) == 0 || g->track <= 0 || g->track > UDP->tracks >> STRETCH(g) ||
From: Jan Harkes jaharkes@cs.cmu.edu
commit 7fa0a1da3dadfd9216df7745a1331fdaa0940d1c upstream.
Patch series "Coda updates".
The following patch series is a collection of various fixes for Coda, most of which were collected from linux-fsdevel or linux-kernel but which have as yet not found their way upstream.
This patch (of 22):
Various file systems expect that vma->vm_file points at their own file handle, several use file_inode(vma->vm_file) to get at their inode or use vma->vm_file->private_data. However the way Coda wrapped mmap on a host file broke this assumption, vm_file was still pointing at the Coda file and the host file systems would scribble over Coda's inode and private file data.
This patch fixes the incorrect expectation and wraps vm_ops->open and vm_ops->close to allow Coda to track when the vm_area_struct is destroyed so we still release the reference on the Coda file handle at the right time.
[This patch differs from the original upstream patch because older stable kernels do not have the call_mmap vfs helper so we call f_ops->mmap directly.]
Link: http://lkml.kernel.org/r/0e850c6e59c0b147dc2dcd51a3af004c948c3697.1558117389... Signed-off-by: Jan Harkes jaharkes@cs.cmu.edu Cc: Arnd Bergmann arnd@arndb.de Cc: Colin Ian King colin.king@canonical.com Cc: Dan Carpenter dan.carpenter@oracle.com Cc: David Howells dhowells@redhat.com Cc: Fabian Frederick fabf@skynet.be Cc: Mikko Rapeli mikko.rapeli@iki.fi Cc: Sam Protsenko semen.protsenko@linaro.org Cc: Yann Droneaud ydroneaud@opteya.com Cc: Zhouyang Jia jiazhouyang09@gmail.com Cc: stable@vger.kernel.org Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Jan Harkes jaharkes@cs.cmu.edu Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- fs/coda/file.c | 69 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 68 insertions(+), 1 deletion(-)
--- a/fs/coda/file.c +++ b/fs/coda/file.c @@ -81,6 +81,41 @@ coda_file_write_iter(struct kiocb *iocb, return ret; }
+struct coda_vm_ops { + atomic_t refcnt; + struct file *coda_file; + const struct vm_operations_struct *host_vm_ops; + struct vm_operations_struct vm_ops; +}; + +static void +coda_vm_open(struct vm_area_struct *vma) +{ + struct coda_vm_ops *cvm_ops = + container_of(vma->vm_ops, struct coda_vm_ops, vm_ops); + + atomic_inc(&cvm_ops->refcnt); + + if (cvm_ops->host_vm_ops && cvm_ops->host_vm_ops->open) + cvm_ops->host_vm_ops->open(vma); +} + +static void +coda_vm_close(struct vm_area_struct *vma) +{ + struct coda_vm_ops *cvm_ops = + container_of(vma->vm_ops, struct coda_vm_ops, vm_ops); + + if (cvm_ops->host_vm_ops && cvm_ops->host_vm_ops->close) + cvm_ops->host_vm_ops->close(vma); + + if (atomic_dec_and_test(&cvm_ops->refcnt)) { + vma->vm_ops = cvm_ops->host_vm_ops; + fput(cvm_ops->coda_file); + kfree(cvm_ops); + } +} + static int coda_file_mmap(struct file *coda_file, struct vm_area_struct *vma) { @@ -88,6 +123,8 @@ coda_file_mmap(struct file *coda_file, s struct coda_inode_info *cii; struct file *host_file; struct inode *coda_inode, *host_inode; + struct coda_vm_ops *cvm_ops; + int ret;
cfi = CODA_FTOC(coda_file); BUG_ON(!cfi || cfi->cfi_magic != CODA_MAGIC); @@ -96,6 +133,13 @@ coda_file_mmap(struct file *coda_file, s if (!host_file->f_op->mmap) return -ENODEV;
+ if (WARN_ON(coda_file != vma->vm_file)) + return -EIO; + + cvm_ops = kmalloc(sizeof(struct coda_vm_ops), GFP_KERNEL); + if (!cvm_ops) + return -ENOMEM; + coda_inode = file_inode(coda_file); host_inode = file_inode(host_file);
@@ -109,6 +153,7 @@ coda_file_mmap(struct file *coda_file, s * the container file on us! */ else if (coda_inode->i_mapping != host_inode->i_mapping) { spin_unlock(&cii->c_lock); + kfree(cvm_ops); return -EBUSY; }
@@ -117,7 +162,29 @@ coda_file_mmap(struct file *coda_file, s cfi->cfi_mapcount++; spin_unlock(&cii->c_lock);
- return host_file->f_op->mmap(host_file, vma); + vma->vm_file = get_file(host_file); + ret = host_file->f_op->mmap(host_file, vma); + + if (ret) { + /* if call_mmap fails, our caller will put coda_file so we + * should drop the reference to the host_file that we got. + */ + fput(host_file); + kfree(cvm_ops); + } else { + /* here we add redirects for the open/close vm_operations */ + cvm_ops->host_vm_ops = vma->vm_ops; + if (vma->vm_ops) + cvm_ops->vm_ops = *vma->vm_ops; + + cvm_ops->vm_ops.open = coda_vm_open; + cvm_ops->vm_ops.close = coda_vm_close; + cvm_ops->coda_file = coda_file; + atomic_set(&cvm_ops->refcnt, 1); + + vma->vm_ops = &cvm_ops->vm_ops; + } + return ret; }
int coda_open(struct inode *coda_inode, struct file *coda_file)
From: Steve Longerbeam slongerbeam@gmail.com
commit 3d1f62c686acdedf5ed9642b763f3808d6a47d1e upstream.
The saturation bit was being set at bit 9 in the second 32-bit word of the TPMEM CSC. This isn't correct, the saturation bit is bit 42, which is bit 10 of the second word.
Fixes: 1aa8ea0d2bd5d ("gpu: ipu-v3: Add Image Converter unit")
Signed-off-by: Steve Longerbeam slongerbeam@gmail.com Reviewed-by: Philipp Zabel p.zabel@pengutronix.de Cc: stable@vger.kernel.org Signed-off-by: Philipp Zabel p.zabel@pengutronix.de Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/gpu/ipu-v3/ipu-ic.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/drivers/gpu/ipu-v3/ipu-ic.c +++ b/drivers/gpu/ipu-v3/ipu-ic.c @@ -255,7 +255,7 @@ static int init_csc(struct ipu_ic *ic, writel(param, base++);
param = ((a[0] & 0x1fe0) >> 5) | (params->scale << 8) | - (params->sat << 9); + (params->sat << 10); writel(param, base++);
param = ((a[1] & 0x1f) << 27) | ((c[0][1] & 0x1ff) << 18) |
From: Helge Deller deller@gmx.de
commit 10835c854685393a921b68f529bf740fa7c9984d upstream.
On parisc the privilege level of a process is stored in the lowest two bits of the instruction pointers (IAOQ0 and IAOQ1). On Linux we use privilege level 0 for the kernel and privilege level 3 for user-space. So userspace should not be allowed to modify IAOQ0 or IAOQ1 of a ptraced process to change it's privilege level to e.g. 0 to try to gain kernel privileges.
This patch prevents such modifications by always setting the two lowest bits to one (which relates to privilege level 3 for user-space) if IAOQ0 or IAOQ1 are modified via ptrace calls in the native and compat ptrace paths.
Link: https://bugs.gentoo.org/481768 Reported-by: Jeroen Roovers jer@gentoo.org Cc: stable@vger.kernel.org Tested-by: Rolf Eike Beer eike-kernel@sf-tec.de Signed-off-by: Helge Deller deller@gmx.de Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/parisc/kernel/ptrace.c | 28 ++++++++++++++++++---------- 1 file changed, 18 insertions(+), 10 deletions(-)
--- a/arch/parisc/kernel/ptrace.c +++ b/arch/parisc/kernel/ptrace.c @@ -156,6 +156,9 @@ long arch_ptrace(struct task_struct *chi if ((addr & (sizeof(unsigned long)-1)) || addr >= sizeof(struct pt_regs)) break; + if (addr == PT_IAOQ0 || addr == PT_IAOQ1) { + data |= 3; /* ensure userspace privilege */ + } if ((addr >= PT_GR1 && addr <= PT_GR31) || addr == PT_IAOQ0 || addr == PT_IAOQ1 || (addr >= PT_FR0 && addr <= PT_FR31 + 4) || @@ -189,16 +192,18 @@ long arch_ptrace(struct task_struct *chi
static compat_ulong_t translate_usr_offset(compat_ulong_t offset) { - if (offset < 0) - return sizeof(struct pt_regs); - else if (offset <= 32*4) /* gr[0..31] */ - return offset * 2 + 4; - else if (offset <= 32*4+32*8) /* gr[0..31] + fr[0..31] */ - return offset + 32*4; - else if (offset < sizeof(struct pt_regs)/2 + 32*4) - return offset * 2 + 4 - 32*8; + compat_ulong_t pos; + + if (offset < 32*4) /* gr[0..31] */ + pos = offset * 2 + 4; + else if (offset < 32*4+32*8) /* fr[0] ... fr[31] */ + pos = (offset - 32*4) + PT_FR0; + else if (offset < sizeof(struct pt_regs)/2 + 32*4) /* sr[0] ... ipsw */ + pos = (offset - 32*4 - 32*8) * 2 + PT_SR0 + 4; else - return sizeof(struct pt_regs); + pos = sizeof(struct pt_regs); + + return pos; }
long compat_arch_ptrace(struct task_struct *child, compat_long_t request, @@ -242,9 +247,12 @@ long compat_arch_ptrace(struct task_stru addr = translate_usr_offset(addr); if (addr >= sizeof(struct pt_regs)) break; + if (addr == PT_IAOQ0+4 || addr == PT_IAOQ1+4) { + data |= 3; /* ensure userspace privilege */ + } if (addr >= PT_FR0 && addr <= PT_FR31 + 4) { /* Special case, fp regs are 64 bits anyway */ - *(__u64 *) ((char *) task_regs(child) + addr) = data; + *(__u32 *) ((char *) task_regs(child) + addr) = data; ret = 0; } else if ((addr >= PT_GR1+4 && addr <= PT_GR31+4) ||
From: Christophe Leroy christophe.leroy@c-s.fr
commit 6ecb78ef56e08d2119d337ae23cb951a640dc52d upstream.
Previously, only IBAT1 and IBAT2 were used to map kernel linear mem. Since commit 63b2bc619565 ("powerpc/mm/32s: Use BATs for STRICT_KERNEL_RWX"), we may have all 8 BATs used for mapping kernel text. But the suspend/restore functions only save/restore BATs 0 to 3, and clears BATs 4 to 7.
Make suspend and restore functions respectively save and reload the 8 BATs on CPUs having MMU_FTR_USE_HIGH_BATS feature.
Reported-by: Andreas Schwab schwab@linux-m68k.org Cc: stable@vger.kernel.org Signed-off-by: Christophe Leroy christophe.leroy@c-s.fr Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/powerpc/kernel/swsusp_32.S | 73 ++++++++++++++++++++++++++++---- arch/powerpc/platforms/powermac/sleep.S | 68 +++++++++++++++++++++++++++-- 2 files changed, 128 insertions(+), 13 deletions(-)
--- a/arch/powerpc/kernel/swsusp_32.S +++ b/arch/powerpc/kernel/swsusp_32.S @@ -23,11 +23,19 @@ #define SL_IBAT2 0x48 #define SL_DBAT3 0x50 #define SL_IBAT3 0x58 -#define SL_TB 0x60 -#define SL_R2 0x68 -#define SL_CR 0x6c -#define SL_LR 0x70 -#define SL_R12 0x74 /* r12 to r31 */ +#define SL_DBAT4 0x60 +#define SL_IBAT4 0x68 +#define SL_DBAT5 0x70 +#define SL_IBAT5 0x78 +#define SL_DBAT6 0x80 +#define SL_IBAT6 0x88 +#define SL_DBAT7 0x90 +#define SL_IBAT7 0x98 +#define SL_TB 0xa0 +#define SL_R2 0xa8 +#define SL_CR 0xac +#define SL_LR 0xb0 +#define SL_R12 0xb4 /* r12 to r31 */ #define SL_SIZE (SL_R12 + 80)
.section .data @@ -112,6 +120,41 @@ _GLOBAL(swsusp_arch_suspend) mfibatl r4,3 stw r4,SL_IBAT3+4(r11)
+BEGIN_MMU_FTR_SECTION + mfspr r4,SPRN_DBAT4U + stw r4,SL_DBAT4(r11) + mfspr r4,SPRN_DBAT4L + stw r4,SL_DBAT4+4(r11) + mfspr r4,SPRN_DBAT5U + stw r4,SL_DBAT5(r11) + mfspr r4,SPRN_DBAT5L + stw r4,SL_DBAT5+4(r11) + mfspr r4,SPRN_DBAT6U + stw r4,SL_DBAT6(r11) + mfspr r4,SPRN_DBAT6L + stw r4,SL_DBAT6+4(r11) + mfspr r4,SPRN_DBAT7U + stw r4,SL_DBAT7(r11) + mfspr r4,SPRN_DBAT7L + stw r4,SL_DBAT7+4(r11) + mfspr r4,SPRN_IBAT4U + stw r4,SL_IBAT4(r11) + mfspr r4,SPRN_IBAT4L + stw r4,SL_IBAT4+4(r11) + mfspr r4,SPRN_IBAT5U + stw r4,SL_IBAT5(r11) + mfspr r4,SPRN_IBAT5L + stw r4,SL_IBAT5+4(r11) + mfspr r4,SPRN_IBAT6U + stw r4,SL_IBAT6(r11) + mfspr r4,SPRN_IBAT6L + stw r4,SL_IBAT6+4(r11) + mfspr r4,SPRN_IBAT7U + stw r4,SL_IBAT7(r11) + mfspr r4,SPRN_IBAT7L + stw r4,SL_IBAT7+4(r11) +END_MMU_FTR_SECTION_IFSET(MMU_FTR_USE_HIGH_BATS) + #if 0 /* Backup various CPU config stuffs */ bl __save_cpu_setup @@ -277,27 +320,41 @@ END_FTR_SECTION_IFSET(CPU_FTR_ALTIVEC) mtibatu 3,r4 lwz r4,SL_IBAT3+4(r11) mtibatl 3,r4 -#endif - BEGIN_MMU_FTR_SECTION - li r4,0 + lwz r4,SL_DBAT4(r11) mtspr SPRN_DBAT4U,r4 + lwz r4,SL_DBAT4+4(r11) mtspr SPRN_DBAT4L,r4 + lwz r4,SL_DBAT5(r11) mtspr SPRN_DBAT5U,r4 + lwz r4,SL_DBAT5+4(r11) mtspr SPRN_DBAT5L,r4 + lwz r4,SL_DBAT6(r11) mtspr SPRN_DBAT6U,r4 + lwz r4,SL_DBAT6+4(r11) mtspr SPRN_DBAT6L,r4 + lwz r4,SL_DBAT7(r11) mtspr SPRN_DBAT7U,r4 + lwz r4,SL_DBAT7+4(r11) mtspr SPRN_DBAT7L,r4 + lwz r4,SL_IBAT4(r11) mtspr SPRN_IBAT4U,r4 + lwz r4,SL_IBAT4+4(r11) mtspr SPRN_IBAT4L,r4 + lwz r4,SL_IBAT5(r11) mtspr SPRN_IBAT5U,r4 + lwz r4,SL_IBAT5+4(r11) mtspr SPRN_IBAT5L,r4 + lwz r4,SL_IBAT6(r11) mtspr SPRN_IBAT6U,r4 + lwz r4,SL_IBAT6+4(r11) mtspr SPRN_IBAT6L,r4 + lwz r4,SL_IBAT7(r11) mtspr SPRN_IBAT7U,r4 + lwz r4,SL_IBAT7+4(r11) mtspr SPRN_IBAT7L,r4 END_MMU_FTR_SECTION_IFSET(MMU_FTR_USE_HIGH_BATS) +#endif
/* Flush all TLBs */ lis r4,0x1000 --- a/arch/powerpc/platforms/powermac/sleep.S +++ b/arch/powerpc/platforms/powermac/sleep.S @@ -37,10 +37,18 @@ #define SL_IBAT2 0x48 #define SL_DBAT3 0x50 #define SL_IBAT3 0x58 -#define SL_TB 0x60 -#define SL_R2 0x68 -#define SL_CR 0x6c -#define SL_R12 0x70 /* r12 to r31 */ +#define SL_DBAT4 0x60 +#define SL_IBAT4 0x68 +#define SL_DBAT5 0x70 +#define SL_IBAT5 0x78 +#define SL_DBAT6 0x80 +#define SL_IBAT6 0x88 +#define SL_DBAT7 0x90 +#define SL_IBAT7 0x98 +#define SL_TB 0xa0 +#define SL_R2 0xa8 +#define SL_CR 0xac +#define SL_R12 0xb0 /* r12 to r31 */ #define SL_SIZE (SL_R12 + 80)
.section .text @@ -125,6 +133,41 @@ _GLOBAL(low_sleep_handler) mfibatl r4,3 stw r4,SL_IBAT3+4(r1)
+BEGIN_MMU_FTR_SECTION + mfspr r4,SPRN_DBAT4U + stw r4,SL_DBAT4(r1) + mfspr r4,SPRN_DBAT4L + stw r4,SL_DBAT4+4(r1) + mfspr r4,SPRN_DBAT5U + stw r4,SL_DBAT5(r1) + mfspr r4,SPRN_DBAT5L + stw r4,SL_DBAT5+4(r1) + mfspr r4,SPRN_DBAT6U + stw r4,SL_DBAT6(r1) + mfspr r4,SPRN_DBAT6L + stw r4,SL_DBAT6+4(r1) + mfspr r4,SPRN_DBAT7U + stw r4,SL_DBAT7(r1) + mfspr r4,SPRN_DBAT7L + stw r4,SL_DBAT7+4(r1) + mfspr r4,SPRN_IBAT4U + stw r4,SL_IBAT4(r1) + mfspr r4,SPRN_IBAT4L + stw r4,SL_IBAT4+4(r1) + mfspr r4,SPRN_IBAT5U + stw r4,SL_IBAT5(r1) + mfspr r4,SPRN_IBAT5L + stw r4,SL_IBAT5+4(r1) + mfspr r4,SPRN_IBAT6U + stw r4,SL_IBAT6(r1) + mfspr r4,SPRN_IBAT6L + stw r4,SL_IBAT6+4(r1) + mfspr r4,SPRN_IBAT7U + stw r4,SL_IBAT7(r1) + mfspr r4,SPRN_IBAT7L + stw r4,SL_IBAT7+4(r1) +END_MMU_FTR_SECTION_IFSET(MMU_FTR_USE_HIGH_BATS) + /* Backup various CPU config stuffs */ bl __save_cpu_setup
@@ -325,22 +368,37 @@ grackle_wake_up: mtibatl 3,r4
BEGIN_MMU_FTR_SECTION - li r4,0 + lwz r4,SL_DBAT4(r1) mtspr SPRN_DBAT4U,r4 + lwz r4,SL_DBAT4+4(r1) mtspr SPRN_DBAT4L,r4 + lwz r4,SL_DBAT5(r1) mtspr SPRN_DBAT5U,r4 + lwz r4,SL_DBAT5+4(r1) mtspr SPRN_DBAT5L,r4 + lwz r4,SL_DBAT6(r1) mtspr SPRN_DBAT6U,r4 + lwz r4,SL_DBAT6+4(r1) mtspr SPRN_DBAT6L,r4 + lwz r4,SL_DBAT7(r1) mtspr SPRN_DBAT7U,r4 + lwz r4,SL_DBAT7+4(r1) mtspr SPRN_DBAT7L,r4 + lwz r4,SL_IBAT4(r1) mtspr SPRN_IBAT4U,r4 + lwz r4,SL_IBAT4+4(r1) mtspr SPRN_IBAT4L,r4 + lwz r4,SL_IBAT5(r1) mtspr SPRN_IBAT5U,r4 + lwz r4,SL_IBAT5+4(r1) mtspr SPRN_IBAT5L,r4 + lwz r4,SL_IBAT6(r1) mtspr SPRN_IBAT6U,r4 + lwz r4,SL_IBAT6+4(r1) mtspr SPRN_IBAT6L,r4 + lwz r4,SL_IBAT7(r1) mtspr SPRN_IBAT7U,r4 + lwz r4,SL_IBAT7+4(r1) mtspr SPRN_IBAT7L,r4 END_MMU_FTR_SECTION_IFSET(MMU_FTR_USE_HIGH_BATS)
From: Ravi Bangoria ravi.bangoria@linux.ibm.com
commit f474c28fbcbe42faca4eb415172c07d76adcb819 upstream.
powerpc hardware triggers watchpoint before executing the instruction. To make trigger-after-execute behavior, kernel emulates the instruction. If the instruction is 'load something into non-volatile register', exception handler should restore emulated register state while returning back, otherwise there will be register state corruption. eg, adding a watchpoint on a list can corrput the list:
# cat /proc/kallsyms | grep kthread_create_list c00000000121c8b8 d kthread_create_list
Add watchpoint on kthread_create_list->prev:
# perf record -e mem:0xc00000000121c8c0
Run some workload such that new kthread gets invoked. eg, I just logged out from console:
list_add corruption. next->prev should be prev (c000000001214e00), \ but was c00000000121c8b8. (next=c00000000121c8b8). WARNING: CPU: 59 PID: 309 at lib/list_debug.c:25 __list_add_valid+0xb4/0xc0 CPU: 59 PID: 309 Comm: kworker/59:0 Kdump: loaded Not tainted 5.1.0-rc7+ #69 ... NIP __list_add_valid+0xb4/0xc0 LR __list_add_valid+0xb0/0xc0 Call Trace: __list_add_valid+0xb0/0xc0 (unreliable) __kthread_create_on_node+0xe0/0x260 kthread_create_on_node+0x34/0x50 create_worker+0xe8/0x260 worker_thread+0x444/0x560 kthread+0x160/0x1a0 ret_from_kernel_thread+0x5c/0x70
List corruption happened because it uses 'load into non-volatile register' instruction:
Snippet from __kthread_create_on_node:
c000000000136be8: addis r29,r2,-19 c000000000136bec: ld r29,31424(r29) if (!__list_add_valid(new, prev, next)) c000000000136bf0: mr r3,r30 c000000000136bf4: mr r5,r28 c000000000136bf8: mr r4,r29 c000000000136bfc: bl c00000000059a2f8 <__list_add_valid+0x8>
Register state from WARN_ON():
GPR00: c00000000059a3a0 c000007ff23afb50 c000000001344e00 0000000000000075 GPR04: 0000000000000000 0000000000000000 0000001852af8bc1 0000000000000000 GPR08: 0000000000000001 0000000000000007 0000000000000006 00000000000004aa GPR12: 0000000000000000 c000007ffffeb080 c000000000137038 c000005ff62aaa00 GPR16: 0000000000000000 0000000000000000 c000007fffbe7600 c000007fffbe7370 GPR20: c000007fffbe7320 c000007fffbe7300 c000000001373a00 0000000000000000 GPR24: fffffffffffffef7 c00000000012e320 c000007ff23afcb0 c000000000cb8628 GPR28: c00000000121c8b8 c000000001214e00 c000007fef5b17e8 c000007fef5b17c0
Watchpoint hit at 0xc000000000136bec.
addis r29,r2,-19 => r29 = 0xc000000001344e00 + (-19 << 16) => r29 = 0xc000000001214e00
ld r29,31424(r29) => r29 = *(0xc000000001214e00 + 31424) => r29 = *(0xc00000000121c8c0)
0xc00000000121c8c0 is where we placed a watchpoint and thus this instruction was emulated by emulate_step. But because handle_dabr_fault did not restore emulated register state, r29 still contains stale value in above register state.
Fixes: 5aae8a5370802 ("powerpc, hw_breakpoints: Implement hw_breakpoints for 64-bit server processors") Signed-off-by: Ravi Bangoria ravi.bangoria@linux.ibm.com Cc: stable@vger.kernel.org # 2.6.36+ Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/powerpc/kernel/exceptions-64s.S | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-)
--- a/arch/powerpc/kernel/exceptions-64s.S +++ b/arch/powerpc/kernel/exceptions-64s.S @@ -1719,7 +1719,7 @@ handle_page_fault: addi r3,r1,STACK_FRAME_OVERHEAD bl do_page_fault cmpdi r3,0 - beq+ 12f + beq+ ret_from_except_lite bl save_nvgprs mr r5,r3 addi r3,r1,STACK_FRAME_OVERHEAD @@ -1734,7 +1734,12 @@ handle_dabr_fault: ld r5,_DSISR(r1) addi r3,r1,STACK_FRAME_OVERHEAD bl do_break -12: b ret_from_except_lite + /* + * do_break() may have changed the NV GPRS while handling a breakpoint. + * If so, we need to restore them with their updated values. Don't use + * ret_from_except_lite here. + */ + b ret_from_except
/* We have a page fault that hash_page could handle but HV refused
From: Dan Carpenter dan.carpenter@oracle.com
commit 0bdf8a8245fdea6f075a5fede833a5fcf1b3466c upstream.
ECRYPTFS_SIZE_AND_MARKER_BYTES is type size_t, so if "rc" is negative that gets type promoted to a high positive value and treated as success.
Fixes: 778aeb42a708 ("eCryptfs: Cleanup and optimize ecryptfs_lookup_interpose()") Signed-off-by: Dan Carpenter dan.carpenter@oracle.com [tyhicks: Use "if/else if" rather than "if/if"] Cc: stable@vger.kernel.org Signed-off-by: Tyler Hicks tyhicks@canonical.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- fs/ecryptfs/crypto.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-)
--- a/fs/ecryptfs/crypto.c +++ b/fs/ecryptfs/crypto.c @@ -1041,8 +1041,10 @@ int ecryptfs_read_and_validate_header_re
rc = ecryptfs_read_lower(file_size, 0, ECRYPTFS_SIZE_AND_MARKER_BYTES, inode); - if (rc < ECRYPTFS_SIZE_AND_MARKER_BYTES) - return rc >= 0 ? -EINVAL : rc; + if (rc < 0) + return rc; + else if (rc < ECRYPTFS_SIZE_AND_MARKER_BYTES) + return -EINVAL; rc = ecryptfs_validate_marker(marker); if (!rc) ecryptfs_i_size_init(file_size, inode); @@ -1400,8 +1402,10 @@ int ecryptfs_read_and_validate_xattr_reg rc = ecryptfs_getxattr_lower(ecryptfs_dentry_to_lower(dentry), ECRYPTFS_XATTR_NAME, file_size, ECRYPTFS_SIZE_AND_MARKER_BYTES); - if (rc < ECRYPTFS_SIZE_AND_MARKER_BYTES) - return rc >= 0 ? -EINVAL : rc; + if (rc < 0) + return rc; + else if (rc < ECRYPTFS_SIZE_AND_MARKER_BYTES) + return -EINVAL; rc = ecryptfs_validate_marker(marker); if (!rc) ecryptfs_i_size_init(file_size, inode);
From: Alexander Shishkin alexander.shishkin@linux.intel.com
commit 918b8646497b5dba6ae82d4a7325f01b258972b9 upstream.
Commit 4e0eaf239fb3 ("intel_th: msu: Fix single mode with IOMMU") switched the single mode code to use dma mapping pages obtained from the page allocator, but with IOMMU disabled, that may lead to using SWIOTLB bounce buffers and without additional sync'ing, produces empty trace buffers.
Fix this by using a DMA32 GFP flag to the page allocation in single mode, as the device supports full 32-bit DMA addressing.
Signed-off-by: Alexander Shishkin alexander.shishkin@linux.intel.com Fixes: 4e0eaf239fb3 ("intel_th: msu: Fix single mode with IOMMU") Reviewed-by: Andy Shevchenko andriy.shevchenko@linux.intel.com Reported-by: Ammy Yi ammy.yi@intel.com Cc: stable stable@vger.kernel.org Link: https://lore.kernel.org/r/20190621161930.60785-4-alexander.shishkin@linux.in... Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/hwtracing/intel_th/msu.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/drivers/hwtracing/intel_th/msu.c +++ b/drivers/hwtracing/intel_th/msu.c @@ -625,7 +625,7 @@ static int msc_buffer_contig_alloc(struc goto err_out;
ret = -ENOMEM; - page = alloc_pages(GFP_KERNEL | __GFP_ZERO, order); + page = alloc_pages(GFP_KERNEL | __GFP_ZERO | GFP_DMA32, order); if (!page) goto err_free_sgt;
From: Szymon Janc szymon.janc@codecoup.pl
commit 1d87b88ba26eabd4745e158ecfd87c93a9b51dc2 upstream.
Microsoft Surface Precision Mouse provides bogus identity address when pairing. It connects with Static Random address but provides Public Address in SMP Identity Address Information PDU. Address has same value but type is different. Workaround this by dropping IRK if ID address discrepancy is detected.
HCI Event: LE Meta Event (0x3e) plen 19
LE Connection Complete (0x01) Status: Success (0x00) Handle: 75 Role: Master (0x00) Peer address type: Random (0x01) Peer address: E0:52:33:93:3B:21 (Static) Connection interval: 50.00 msec (0x0028) Connection latency: 0 (0x0000) Supervision timeout: 420 msec (0x002a) Master clock accuracy: 0x00
....
ACL Data RX: Handle 75 flags 0x02 dlen 12
SMP: Identity Address Information (0x09) len 7 Address type: Public (0x00) Address: E0:52:33:93:3B:21
Signed-off-by: Szymon Janc szymon.janc@codecoup.pl Tested-by: Maarten Fonville maarten.fonville@gmail.com Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=199461 Cc: stable@vger.kernel.org Signed-off-by: Marcel Holtmann marcel@holtmann.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- net/bluetooth/smp.c | 13 +++++++++++++ 1 file changed, 13 insertions(+)
--- a/net/bluetooth/smp.c +++ b/net/bluetooth/smp.c @@ -2532,6 +2532,19 @@ static int smp_cmd_ident_addr_info(struc goto distribute; }
+ /* Drop IRK if peer is using identity address during pairing but is + * providing different address as identity information. + * + * Microsoft Surface Precision Mouse is known to have this bug. + */ + if (hci_is_identity_address(&hcon->dst, hcon->dst_type) && + (bacmp(&info->bdaddr, &hcon->dst) || + info->addr_type != hcon->dst_type)) { + bt_dev_err(hcon->hdev, + "ignoring IRK with invalid identity address"); + goto distribute; + } + bacpy(&smp->id_addr, &info->bdaddr); smp->id_addr_type = info->addr_type;
From: Lee, Chiasheng chiasheng.lee@intel.com
commit e244c4699f859cf7149b0781b1894c7996a8a1df upstream.
With Link Power Management (LPM) enabled USB3 links transition to low power U1/U2 link states from U0 state automatically.
Current hub code detects USB3 remote wakeups by checking if the software state still shows suspended, but the link has transitioned from suspended U3 to enabled U0 state.
As it takes some time before the hub thread reads the port link state after a USB3 wake notification, the link may have transitioned from U0 to U1/U2, and wake is not detected by hub code.
Fix this by handling U1/U2 states in the same way as U0 in USB3 wakeup handling
This patch should be added to stable kernels since 4.13 where LPM was kept enabled during suspend/resume
Cc: stable@vger.kernel.org # v4.13+ Signed-off-by: Lee, Chiasheng chiasheng.lee@intel.com Signed-off-by: Mathias Nyman mathias.nyman@linux.intel.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/usb/core/hub.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
--- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c @@ -3479,6 +3479,7 @@ static int hub_handle_remote_wakeup(stru struct usb_device *hdev; struct usb_device *udev; int connect_change = 0; + u16 link_state; int ret;
hdev = hub->hdev; @@ -3488,9 +3489,11 @@ static int hub_handle_remote_wakeup(stru return 0; usb_clear_port_feature(hdev, port, USB_PORT_FEAT_C_SUSPEND); } else { + link_state = portstatus & USB_PORT_STAT_LINK_STATE; if (!udev || udev->state != USB_STATE_SUSPENDED || - (portstatus & USB_PORT_STAT_LINK_STATE) != - USB_SS_PORT_LS_U0) + (link_state != USB_SS_PORT_LS_U0 && + link_state != USB_SS_PORT_LS_U1 && + link_state != USB_SS_PORT_LS_U2)) return 0; }
From: Junxiao Bi junxiao.bi@oracle.com
commit bd293d071ffe65e645b4d8104f9d8fe15ea13862 upstream.
When thin-volume is built on loop device, if available memory is low, the following deadlock can be triggered:
One process P1 allocates memory with GFP_FS flag, direct alloc fails, memory reclaim invokes memory shrinker in dm_bufio, dm_bufio_shrink_scan() runs, mutex dm_bufio_client->lock is acquired, then P1 waits for dm_buffer IO to complete in __try_evict_buffer().
But this IO may never complete if issued to an underlying loop device that forwards it using direct-IO, which allocates memory using GFP_KERNEL (see: do_blockdev_direct_IO()). If allocation fails, memory reclaim will invoke memory shrinker in dm_bufio, dm_bufio_shrink_scan() will be invoked, and since the mutex is already held by P1 the loop thread will hang, and IO will never complete. Resulting in ABBA deadlock.
Cc: stable@vger.kernel.org Signed-off-by: Junxiao Bi junxiao.bi@oracle.com Signed-off-by: Mike Snitzer snitzer@redhat.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/md/dm-bufio.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-)
--- a/drivers/md/dm-bufio.c +++ b/drivers/md/dm-bufio.c @@ -1561,9 +1561,7 @@ dm_bufio_shrink_scan(struct shrinker *sh unsigned long freed;
c = container_of(shrink, struct dm_bufio_client, shrinker); - if (sc->gfp_mask & __GFP_FS) - dm_bufio_lock(c); - else if (!dm_bufio_trylock(c)) + if (!dm_bufio_trylock(c)) return SHRINK_STOP;
freed = __scan(c, sc->nr_to_scan, sc->gfp_mask);
From: Brian King brking@linux.vnet.ibm.com
[ Upstream commit ea811b795df24644a8eb760b493c43fba4450677 ]
This patch fixes an issue seen on Power systems with bnx2x which results in the skb is NULL WARN_ON in bnx2x_free_tx_pkt firing due to the skb pointer getting loaded in bnx2x_free_tx_pkt prior to the hw_cons load in bnx2x_tx_int. Adding a read memory barrier resolves the issue.
Signed-off-by: Brian King brking@linux.vnet.ibm.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c | 3 +++ 1 file changed, 3 insertions(+)
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c +++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c @@ -288,6 +288,9 @@ int bnx2x_tx_int(struct bnx2x *bp, struc hw_cons = le16_to_cpu(*txdata->tx_cons_sb); sw_cons = txdata->tx_pkt_cons;
+ /* Ensure subsequent loads occur after hw_cons */ + smp_rmb(); + while (sw_cons != hw_cons) { u16 pkt_cons;
From: Taehee Yoo ap420073@gmail.com
[ Upstream commit fdd258d49e88a9e0b49ef04a506a796f1c768a8e ]
cfhsi_exit_module() calls unregister_netdev() under rtnl_lock(). but unregister_netdev() internally calls rtnl_lock(). So deadlock would occur.
Fixes: c41254006377 ("caif-hsi: Add rtnl support") Signed-off-by: Taehee Yoo ap420073@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/net/caif/caif_hsi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/drivers/net/caif/caif_hsi.c +++ b/drivers/net/caif/caif_hsi.c @@ -1467,7 +1467,7 @@ static void __exit cfhsi_exit_module(voi rtnl_lock(); list_for_each_safe(list_node, n, &cfhsi_list) { cfhsi = list_entry(list_node, struct cfhsi, list); - unregister_netdev(cfhsi->ndev); + unregister_netdevice(cfhsi->ndev); } rtnl_unlock(); }
From: Matteo Croce mcroce@redhat.com
[ Upstream commit 2e60546368165c2449564d71f6005dda9205b5fb ]
Avoid the situation where an IPV6 only flag is applied to an IPv4 address:
# ip addr add 192.0.2.1/24 dev dummy0 nodad home mngtmpaddr noprefixroute # ip -4 addr show dev dummy0 2: dummy0: <BROADCAST,NOARP,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN group default qlen 1000 inet 192.0.2.1/24 scope global noprefixroute dummy0 valid_lft forever preferred_lft forever
Or worse, by sending a malicious netlink command:
# ip -4 addr show dev dummy0 2: dummy0: <BROADCAST,NOARP,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN group default qlen 1000 inet 192.0.2.1/24 scope global nodad optimistic dadfailed home tentative mngtmpaddr noprefixroute stable-privacy dummy0 valid_lft forever preferred_lft forever
Signed-off-by: Matteo Croce mcroce@redhat.com Reviewed-by: David Ahern dsahern@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/ipv4/devinet.c | 8 ++++++++ 1 file changed, 8 insertions(+)
--- a/net/ipv4/devinet.c +++ b/net/ipv4/devinet.c @@ -67,6 +67,11 @@
#include "fib_lookup.h"
+#define IPV6ONLY_FLAGS \ + (IFA_F_NODAD | IFA_F_OPTIMISTIC | IFA_F_DADFAILED | \ + IFA_F_HOMEADDRESS | IFA_F_TENTATIVE | \ + IFA_F_MANAGETEMPADDR | IFA_F_STABLE_PRIVACY) + static struct ipv4_devconf ipv4_devconf = { .data = { [IPV4_DEVCONF_ACCEPT_REDIRECTS - 1] = 1, @@ -453,6 +458,9 @@ static int __inet_insert_ifa(struct in_i ifa->ifa_flags &= ~IFA_F_SECONDARY; last_primary = &in_dev->ifa_list;
+ /* Don't set IPv6 only flags to IPv4 addresses */ + ifa->ifa_flags &= ~IPV6ONLY_FLAGS; + for (ifap = &in_dev->ifa_list; (ifa1 = *ifap) != NULL; ifap = &ifa1->ifa_next) { if (!(ifa1->ifa_flags & IFA_F_SECONDARY) &&
From: Justin Chen justinpopo6@gmail.com
[ Upstream commit 35cbef9863640f06107144687bd13151bc2e8ce3 ]
Currently we silently ignore filters if we cannot meet the filter requirements. This will lead to the MAC dropping packets that are expected to pass. A better solution would be to set the NIC to promisc mode when the required filters cannot be met.
Also correct the number of MDF filters supported. It should be 17, not 16.
Signed-off-by: Justin Chen justinpopo6@gmail.com Reviewed-by: Florian Fainelli f.fainelli@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/net/ethernet/broadcom/genet/bcmgenet.c | 57 +++++++++++-------------- 1 file changed, 26 insertions(+), 31 deletions(-)
--- a/drivers/net/ethernet/broadcom/genet/bcmgenet.c +++ b/drivers/net/ethernet/broadcom/genet/bcmgenet.c @@ -3090,39 +3090,42 @@ static void bcmgenet_timeout(struct net_ netif_tx_wake_all_queues(dev); }
-#define MAX_MC_COUNT 16 +#define MAX_MDF_FILTER 17
static inline void bcmgenet_set_mdf_addr(struct bcmgenet_priv *priv, unsigned char *addr, - int *i, - int *mc) + int *i) { - u32 reg; - bcmgenet_umac_writel(priv, addr[0] << 8 | addr[1], UMAC_MDF_ADDR + (*i * 4)); bcmgenet_umac_writel(priv, addr[2] << 24 | addr[3] << 16 | addr[4] << 8 | addr[5], UMAC_MDF_ADDR + ((*i + 1) * 4)); - reg = bcmgenet_umac_readl(priv, UMAC_MDF_CTRL); - reg |= (1 << (MAX_MC_COUNT - *mc)); - bcmgenet_umac_writel(priv, reg, UMAC_MDF_CTRL); *i += 2; - (*mc)++; }
static void bcmgenet_set_rx_mode(struct net_device *dev) { struct bcmgenet_priv *priv = netdev_priv(dev); struct netdev_hw_addr *ha; - int i, mc; + int i, nfilter; u32 reg;
netif_dbg(priv, hw, dev, "%s: %08X\n", __func__, dev->flags);
- /* Promiscuous mode */ + /* Number of filters needed */ + nfilter = netdev_uc_count(dev) + netdev_mc_count(dev) + 2; + + /* + * Turn on promicuous mode for three scenarios + * 1. IFF_PROMISC flag is set + * 2. IFF_ALLMULTI flag is set + * 3. The number of filters needed exceeds the number filters + * supported by the hardware. + */ reg = bcmgenet_umac_readl(priv, UMAC_CMD); - if (dev->flags & IFF_PROMISC) { + if ((dev->flags & (IFF_PROMISC | IFF_ALLMULTI)) || + (nfilter > MAX_MDF_FILTER)) { reg |= CMD_PROMISC; bcmgenet_umac_writel(priv, reg, UMAC_CMD); bcmgenet_umac_writel(priv, 0, UMAC_MDF_CTRL); @@ -3132,32 +3135,24 @@ static void bcmgenet_set_rx_mode(struct bcmgenet_umac_writel(priv, reg, UMAC_CMD); }
- /* UniMac doesn't support ALLMULTI */ - if (dev->flags & IFF_ALLMULTI) { - netdev_warn(dev, "ALLMULTI is not supported\n"); - return; - } - /* update MDF filter */ i = 0; - mc = 0; /* Broadcast */ - bcmgenet_set_mdf_addr(priv, dev->broadcast, &i, &mc); + bcmgenet_set_mdf_addr(priv, dev->broadcast, &i); /* my own address.*/ - bcmgenet_set_mdf_addr(priv, dev->dev_addr, &i, &mc); - /* Unicast list*/ - if (netdev_uc_count(dev) > (MAX_MC_COUNT - mc)) - return; + bcmgenet_set_mdf_addr(priv, dev->dev_addr, &i);
- if (!netdev_uc_empty(dev)) - netdev_for_each_uc_addr(ha, dev) - bcmgenet_set_mdf_addr(priv, ha->addr, &i, &mc); - /* Multicast */ - if (netdev_mc_empty(dev) || netdev_mc_count(dev) >= (MAX_MC_COUNT - mc)) - return; + /* Unicast */ + netdev_for_each_uc_addr(ha, dev) + bcmgenet_set_mdf_addr(priv, ha->addr, &i);
+ /* Multicast */ netdev_for_each_mc_addr(ha, dev) - bcmgenet_set_mdf_addr(priv, ha->addr, &i, &mc); + bcmgenet_set_mdf_addr(priv, ha->addr, &i); + + /* Enable filters */ + reg = GENMASK(MAX_MDF_FILTER - 1, MAX_MDF_FILTER - nfilter); + bcmgenet_umac_writel(priv, reg, UMAC_MDF_CTRL); }
/* Set the hardware MAC address. */
From: Lorenzo Bianconi lorenzo.bianconi@redhat.com
[ Upstream commit 071c37983d99da07797294ea78e9da1a6e287144 ]
Neigh timer can be scheduled multiple times from userspace adding multiple neigh entries and forcing the neigh timer scheduling passing NTF_USE in the netlink requests. This will result in a refcount leak and in the following dump stack:
[ 32.465295] NEIGH: BUG, double timer add, state is 8 [ 32.465308] CPU: 0 PID: 416 Comm: double_timer_ad Not tainted 5.2.0+ #65 [ 32.465311] Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS 1.12.0-2.fc30 04/01/2014 [ 32.465313] Call Trace: [ 32.465318] dump_stack+0x7c/0xc0 [ 32.465323] __neigh_event_send+0x20c/0x880 [ 32.465326] ? ___neigh_create+0x846/0xfb0 [ 32.465329] ? neigh_lookup+0x2a9/0x410 [ 32.465332] ? neightbl_fill_info.constprop.0+0x800/0x800 [ 32.465334] neigh_add+0x4f8/0x5e0 [ 32.465337] ? neigh_xmit+0x620/0x620 [ 32.465341] ? find_held_lock+0x85/0xa0 [ 32.465345] rtnetlink_rcv_msg+0x204/0x570 [ 32.465348] ? rtnl_dellink+0x450/0x450 [ 32.465351] ? mark_held_locks+0x90/0x90 [ 32.465354] ? match_held_lock+0x1b/0x230 [ 32.465357] netlink_rcv_skb+0xc4/0x1d0 [ 32.465360] ? rtnl_dellink+0x450/0x450 [ 32.465363] ? netlink_ack+0x420/0x420 [ 32.465366] ? netlink_deliver_tap+0x115/0x560 [ 32.465369] ? __alloc_skb+0xc9/0x2f0 [ 32.465372] netlink_unicast+0x270/0x330 [ 32.465375] ? netlink_attachskb+0x2f0/0x2f0 [ 32.465378] netlink_sendmsg+0x34f/0x5a0 [ 32.465381] ? netlink_unicast+0x330/0x330 [ 32.465385] ? move_addr_to_kernel.part.0+0x20/0x20 [ 32.465388] ? netlink_unicast+0x330/0x330 [ 32.465391] sock_sendmsg+0x91/0xa0 [ 32.465394] ___sys_sendmsg+0x407/0x480 [ 32.465397] ? copy_msghdr_from_user+0x200/0x200 [ 32.465401] ? _raw_spin_unlock_irqrestore+0x37/0x40 [ 32.465404] ? lockdep_hardirqs_on+0x17d/0x250 [ 32.465407] ? __wake_up_common_lock+0xcb/0x110 [ 32.465410] ? __wake_up_common+0x230/0x230 [ 32.465413] ? netlink_bind+0x3e1/0x490 [ 32.465416] ? netlink_setsockopt+0x540/0x540 [ 32.465420] ? __fget_light+0x9c/0xf0 [ 32.465423] ? sockfd_lookup_light+0x8c/0xb0 [ 32.465426] __sys_sendmsg+0xa5/0x110 [ 32.465429] ? __ia32_sys_shutdown+0x30/0x30 [ 32.465432] ? __fd_install+0xe1/0x2c0 [ 32.465435] ? lockdep_hardirqs_off+0xb5/0x100 [ 32.465438] ? mark_held_locks+0x24/0x90 [ 32.465441] ? do_syscall_64+0xf/0x270 [ 32.465444] do_syscall_64+0x63/0x270 [ 32.465448] entry_SYSCALL_64_after_hwframe+0x49/0xbe
Fix the issue unscheduling neigh_timer if selected entry is in 'IN_TIMER' receiving a netlink request with NTF_USE flag set
Reported-by: Marek Majkowski marek@cloudflare.com Fixes: 0c5c2d308906 ("neigh: Allow for user space users of the neighbour table") Signed-off-by: Lorenzo Bianconi lorenzo.bianconi@redhat.com Reviewed-by: David Ahern dsahern@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/core/neighbour.c | 2 ++ 1 file changed, 2 insertions(+)
--- a/net/core/neighbour.c +++ b/net/core/neighbour.c @@ -982,6 +982,7 @@ int __neigh_event_send(struct neighbour
atomic_set(&neigh->probes, NEIGH_VAR(neigh->parms, UCAST_PROBES)); + neigh_del_timer(neigh); neigh->nud_state = NUD_INCOMPLETE; neigh->updated = now; next = now + max(NEIGH_VAR(neigh->parms, RETRANS_TIME), @@ -998,6 +999,7 @@ int __neigh_event_send(struct neighbour } } else if (neigh->nud_state & NUD_STALE) { neigh_dbg(2, "neigh %p is delayed\n", neigh); + neigh_del_timer(neigh); neigh->nud_state = NUD_DELAY; neigh->updated = jiffies; neigh_add_timer(neigh, jiffies +
From: Yang Wei albin_yang@163.com
[ Upstream commit dd006fc434e107ef90f7de0db9907cbc1c521645 ]
The frags_q is not properly initialized, it may result in illegal memory access when conn_info is NULL. The "goto free_exit" should be replaced by "goto exit".
Signed-off-by: Yang Wei albin_yang@163.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/nfc/nci/data.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/net/nfc/nci/data.c +++ b/net/nfc/nci/data.c @@ -119,7 +119,7 @@ static int nci_queue_tx_data_frags(struc conn_info = nci_get_conn_info_by_conn_id(ndev, conn_id); if (!conn_info) { rc = -EPROTO; - goto free_exit; + goto exit; }
__skb_queue_head_init(&frags_q);
From: Takashi Iwai tiwai@suse.de
[ Upstream commit a261e3797506bd561700be643fe1a85bf81e9661 ]
The onboard sky2 NIC on ASUS P6T WS PRO doesn't work after PM resume due to the infamous IRQ problem. Disabling MSI works around it, so let's add it to the blacklist.
Unfortunately the BIOS on the machine doesn't fill the standard DMI_SYS_* entry, so we pick up DMI_BOARD_* entries instead.
BugLink: https://bugzilla.suse.com/show_bug.cgi?id=1142496 Reported-and-tested-by: Marcus Seyfarth m.seyfarth@gmail.com Signed-off-by: Takashi Iwai tiwai@suse.de Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/net/ethernet/marvell/sky2.c | 7 +++++++ 1 file changed, 7 insertions(+)
--- a/drivers/net/ethernet/marvell/sky2.c +++ b/drivers/net/ethernet/marvell/sky2.c @@ -4939,6 +4939,13 @@ static const struct dmi_system_id msi_bl DMI_MATCH(DMI_PRODUCT_NAME, "P-79"), }, }, + { + .ident = "ASUS P6T", + .matches = { + DMI_MATCH(DMI_BOARD_VENDOR, "ASUSTeK Computer INC."), + DMI_MATCH(DMI_BOARD_NAME, "P6T"), + }, + }, {} };
From: Cong Wang xiyou.wangcong@gmail.com
[ Upstream commit c8c8218ec5af5d2598381883acbefbf604e56b5e ]
When the skb is associated with a new sock, just assigning it to skb->sk is not sufficient, we have to set its destructor to free the sock properly too.
Reported-by: syzbot+d6636a36d3c34bd88938@syzkaller.appspotmail.com Signed-off-by: Cong Wang xiyou.wangcong@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/netrom/af_netrom.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
--- a/net/netrom/af_netrom.c +++ b/net/netrom/af_netrom.c @@ -870,7 +870,7 @@ int nr_rx_frame(struct sk_buff *skb, str unsigned short frametype, flags, window, timeout; int ret;
- skb->sk = NULL; /* Initially we don't know who it's for */ + skb_orphan(skb);
/* * skb->data points to the netrom frame start @@ -969,6 +969,7 @@ int nr_rx_frame(struct sk_buff *skb, str window = skb->data[20];
skb->sk = make; + skb->destructor = sock_efree; make->sk_state = TCP_ESTABLISHED;
/* Fill in his circuit details */
From: Cong Wang xiyou.wangcong@gmail.com
[ Upstream commit 4638faac032756f7eab5524be7be56bee77e426b ]
sock_efree() releases the sock refcnt, if we don't hold this refcnt when setting skb->destructor to it, the refcnt would not be balanced. This leads to several bug reports from syzbot.
I have checked other users of sock_efree(), all of them hold the sock refcnt.
Fixes: c8c8218ec5af ("netrom: fix a memory leak in nr_rx_frame()") Reported-and-tested-by: syzbot+622bdabb128acc33427d@syzkaller.appspotmail.com Reported-and-tested-by: syzbot+6eaef7158b19e3fec3a0@syzkaller.appspotmail.com Reported-and-tested-by: syzbot+9399c158fcc09b21d0d2@syzkaller.appspotmail.com Reported-and-tested-by: syzbot+a34e5f3d0300163f0c87@syzkaller.appspotmail.com Cc: Ralf Baechle ralf@linux-mips.org Signed-off-by: Cong Wang xiyou.wangcong@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/netrom/af_netrom.c | 1 + 1 file changed, 1 insertion(+)
--- a/net/netrom/af_netrom.c +++ b/net/netrom/af_netrom.c @@ -968,6 +968,7 @@ int nr_rx_frame(struct sk_buff *skb, str
window = skb->data[20];
+ sock_hold(make); skb->sk = make; skb->destructor = sock_efree; make->sk_state = TCP_ESTABLISHED;
From: Christoph Paasch cpaasch@apple.com
[ Upstream commit e858faf556d4e14c750ba1e8852783c6f9520a0e ]
If an app is playing tricks to reuse a socket via tcp_disconnect(), bytes_acked/received needs to be reset to 0. Otherwise tcp_info will report the sum of the current and the old connection..
Cc: Eric Dumazet edumazet@google.com Fixes: 0df48c26d841 ("tcp: add tcpi_bytes_acked to tcp_info") Fixes: bdd1f9edacb5 ("tcp: add tcpi_bytes_received to tcp_info") Signed-off-by: Christoph Paasch cpaasch@apple.com Signed-off-by: Eric Dumazet edumazet@google.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/ipv4/tcp.c | 2 ++ 1 file changed, 2 insertions(+)
--- a/net/ipv4/tcp.c +++ b/net/ipv4/tcp.c @@ -2272,6 +2272,8 @@ int tcp_disconnect(struct sock *sk, int dst_release(sk->sk_rx_dst); sk->sk_rx_dst = NULL; tcp_saved_syn_free(tp); + tp->bytes_acked = 0; + tp->bytes_received = 0;
WARN_ON(inet->inet_num && !icsk->icsk_bind_hash);
From: Cong Wang xiyou.wangcong@gmail.com
[ Upstream commit 9d1bc24b52fb8c5d859f9a47084bf1179470e04c ]
bond_xmit_roundrobin() checks for IGMP packets but it parses the IP header even before checking skb->protocol.
We should validate the IP header with pskb_may_pull() before using iph->protocol.
Reported-and-tested-by: syzbot+e5be16aa39ad6e755391@syzkaller.appspotmail.com Fixes: a2fd940f4cff ("bonding: fix broken multicast with round-robin mode") Cc: Jay Vosburgh j.vosburgh@gmail.com Cc: Veaceslav Falico vfalico@gmail.com Cc: Andy Gospodarek andy@greyhouse.net Signed-off-by: Cong Wang xiyou.wangcong@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- drivers/net/bonding/bond_main.c | 37 +++++++++++++++++++++++-------------- 1 file changed, 23 insertions(+), 14 deletions(-)
--- a/drivers/net/bonding/bond_main.c +++ b/drivers/net/bonding/bond_main.c @@ -3714,8 +3714,8 @@ static u32 bond_rr_gen_slave_id(struct b static int bond_xmit_roundrobin(struct sk_buff *skb, struct net_device *bond_dev) { struct bonding *bond = netdev_priv(bond_dev); - struct iphdr *iph = ip_hdr(skb); struct slave *slave; + int slave_cnt; u32 slave_id;
/* Start with the curr_active_slave that joined the bond as the @@ -3724,23 +3724,32 @@ static int bond_xmit_roundrobin(struct s * send the join/membership reports. The curr_active_slave found * will send all of this type of traffic. */ - if (iph->protocol == IPPROTO_IGMP && skb->protocol == htons(ETH_P_IP)) { - slave = rcu_dereference(bond->curr_active_slave); - if (slave) - bond_dev_queue_xmit(bond, skb, slave->dev); - else - bond_xmit_slave_id(bond, skb, 0); - } else { - int slave_cnt = ACCESS_ONCE(bond->slave_cnt); + if (skb->protocol == htons(ETH_P_IP)) { + int noff = skb_network_offset(skb); + struct iphdr *iph; + + if (unlikely(!pskb_may_pull(skb, noff + sizeof(*iph)))) + goto non_igmp;
- if (likely(slave_cnt)) { - slave_id = bond_rr_gen_slave_id(bond); - bond_xmit_slave_id(bond, skb, slave_id % slave_cnt); - } else { - bond_tx_drop(bond_dev, skb); + iph = ip_hdr(skb); + if (iph->protocol == IPPROTO_IGMP) { + slave = rcu_dereference(bond->curr_active_slave); + if (slave) + bond_dev_queue_xmit(bond, skb, slave->dev); + else + bond_xmit_slave_id(bond, skb, 0); + return NETDEV_TX_OK; } }
+non_igmp: + slave_cnt = ACCESS_ONCE(bond->slave_cnt); + if (likely(slave_cnt)) { + slave_id = bond_rr_gen_slave_id(bond); + bond_xmit_slave_id(bond, skb, slave_id % slave_cnt); + } else { + bond_tx_drop(bond_dev, skb); + } return NETDEV_TX_OK; }
From: Nikolay Aleksandrov nikolay@cumulusnetworks.com
[ Upstream commit e57f61858b7cf478ed6fa23ed4b3876b1c9625c4 ]
We take a pointer to grec prior to calling pskb_may_pull and use it afterwards to get nsrcs so record nsrcs before the pull when handling igmp3 and we get a pointer to nsrcs and call pskb_may_pull when handling mld2 which again could lead to reading 2 bytes out-of-bounds.
================================================================== BUG: KASAN: use-after-free in br_multicast_rcv+0x480c/0x4ad0 [bridge] Read of size 2 at addr ffff8880421302b4 by task ksoftirqd/1/16
CPU: 1 PID: 16 Comm: ksoftirqd/1 Tainted: G OE 5.2.0-rc6+ #1 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.10.2-1 04/01/2014 Call Trace: dump_stack+0x71/0xab print_address_description+0x6a/0x280 ? br_multicast_rcv+0x480c/0x4ad0 [bridge] __kasan_report+0x152/0x1aa ? br_multicast_rcv+0x480c/0x4ad0 [bridge] ? br_multicast_rcv+0x480c/0x4ad0 [bridge] kasan_report+0xe/0x20 br_multicast_rcv+0x480c/0x4ad0 [bridge] ? br_multicast_disable_port+0x150/0x150 [bridge] ? ktime_get_with_offset+0xb4/0x150 ? __kasan_kmalloc.constprop.6+0xa6/0xf0 ? __netif_receive_skb+0x1b0/0x1b0 ? br_fdb_update+0x10e/0x6e0 [bridge] ? br_handle_frame_finish+0x3c6/0x11d0 [bridge] br_handle_frame_finish+0x3c6/0x11d0 [bridge] ? br_pass_frame_up+0x3a0/0x3a0 [bridge] ? virtnet_probe+0x1c80/0x1c80 [virtio_net] br_handle_frame+0x731/0xd90 [bridge] ? select_idle_sibling+0x25/0x7d0 ? br_handle_frame_finish+0x11d0/0x11d0 [bridge] __netif_receive_skb_core+0xced/0x2d70 ? virtqueue_get_buf_ctx+0x230/0x1130 [virtio_ring] ? do_xdp_generic+0x20/0x20 ? virtqueue_napi_complete+0x39/0x70 [virtio_net] ? virtnet_poll+0x94d/0xc78 [virtio_net] ? receive_buf+0x5120/0x5120 [virtio_net] ? __netif_receive_skb_one_core+0x97/0x1d0 __netif_receive_skb_one_core+0x97/0x1d0 ? __netif_receive_skb_core+0x2d70/0x2d70 ? _raw_write_trylock+0x100/0x100 ? __queue_work+0x41e/0xbe0 process_backlog+0x19c/0x650 ? _raw_read_lock_irq+0x40/0x40 net_rx_action+0x71e/0xbc0 ? __switch_to_asm+0x40/0x70 ? napi_complete_done+0x360/0x360 ? __switch_to_asm+0x34/0x70 ? __switch_to_asm+0x40/0x70 ? __schedule+0x85e/0x14d0 __do_softirq+0x1db/0x5f9 ? takeover_tasklets+0x5f0/0x5f0 run_ksoftirqd+0x26/0x40 smpboot_thread_fn+0x443/0x680 ? sort_range+0x20/0x20 ? schedule+0x94/0x210 ? __kthread_parkme+0x78/0xf0 ? sort_range+0x20/0x20 kthread+0x2ae/0x3a0 ? kthread_create_worker_on_cpu+0xc0/0xc0 ret_from_fork+0x35/0x40
The buggy address belongs to the page: page:ffffea0001084c00 refcount:0 mapcount:-128 mapping:0000000000000000 index:0x0 flags: 0xffffc000000000() raw: 00ffffc000000000 ffffea0000cfca08 ffffea0001098608 0000000000000000 raw: 0000000000000000 0000000000000003 00000000ffffff7f 0000000000000000 page dumped because: kasan: bad access detected
Memory state around the buggy address: ffff888042130180: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ffff888042130200: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
ffff888042130280: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
^ ffff888042130300: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ffff888042130380: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ================================================================== Disabling lock debugging due to kernel taint
Fixes: bc8c20acaea1 ("bridge: multicast: treat igmpv3 report with INCLUDE and no sources as a leave") Reported-by: Martin Weinelt martin@linuxlounge.net Signed-off-by: Nikolay Aleksandrov nikolay@cumulusnetworks.com Tested-by: Martin Weinelt martin@linuxlounge.net Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/bridge/br_multicast.c | 27 ++++++++++++++++----------- 1 file changed, 16 insertions(+), 11 deletions(-)
--- a/net/bridge/br_multicast.c +++ b/net/bridge/br_multicast.c @@ -1011,6 +1011,7 @@ static int br_ip4_multicast_igmp3_report int type; int err = 0; __be32 group; + u16 nsrcs;
ih = igmpv3_report_hdr(skb); num = ntohs(ih->ngrec); @@ -1024,8 +1025,9 @@ static int br_ip4_multicast_igmp3_report grec = (void *)(skb->data + len - sizeof(*grec)); group = grec->grec_mca; type = grec->grec_type; + nsrcs = ntohs(grec->grec_nsrcs);
- len += ntohs(grec->grec_nsrcs) * 4; + len += nsrcs * 4; if (!pskb_may_pull(skb, len)) return -EINVAL;
@@ -1045,7 +1047,7 @@ static int br_ip4_multicast_igmp3_report
if ((type == IGMPV3_CHANGE_TO_INCLUDE || type == IGMPV3_MODE_IS_INCLUDE) && - ntohs(grec->grec_nsrcs) == 0) { + nsrcs == 0) { br_ip4_multicast_leave_group(br, port, group, vid); } else { err = br_ip4_multicast_add_group(br, port, group, vid); @@ -1078,23 +1080,26 @@ static int br_ip6_multicast_mld2_report( len = skb_transport_offset(skb) + sizeof(*icmp6h);
for (i = 0; i < num; i++) { - __be16 *nsrcs, _nsrcs; + __be16 *_nsrcs, __nsrcs; + u16 nsrcs;
- nsrcs = skb_header_pointer(skb, - len + offsetof(struct mld2_grec, - grec_nsrcs), - sizeof(_nsrcs), &_nsrcs); - if (!nsrcs) + _nsrcs = skb_header_pointer(skb, + len + offsetof(struct mld2_grec, + grec_nsrcs), + sizeof(__nsrcs), &__nsrcs); + if (!_nsrcs) return -EINVAL;
+ nsrcs = ntohs(*_nsrcs); + if (!pskb_may_pull(skb, len + sizeof(*grec) + - sizeof(struct in6_addr) * ntohs(*nsrcs))) + sizeof(struct in6_addr) * nsrcs)) return -EINVAL;
grec = (struct mld2_grec *)(skb->data + len); len += sizeof(*grec) + - sizeof(struct in6_addr) * ntohs(*nsrcs); + sizeof(struct in6_addr) * nsrcs;
/* We treat these as MLDv1 reports for now. */ switch (grec->grec_type) { @@ -1112,7 +1117,7 @@ static int br_ip6_multicast_mld2_report(
if ((grec->grec_type == MLD2_CHANGE_TO_INCLUDE || grec->grec_type == MLD2_MODE_IS_INCLUDE) && - ntohs(*nsrcs) == 0) { + nsrcs == 0) { br_ip6_multicast_leave_group(br, port, &grec->grec_mca, vid); } else {
From: Nikolay Aleksandrov nikolay@cumulusnetworks.com
[ Upstream commit 3b26a5d03d35d8f732d75951218983c0f7f68dff ]
We get a pointer to the ipv6 hdr in br_ip6_multicast_query but we may call pskb_may_pull afterwards and end up using a stale pointer. So use the header directly, it's just 1 place where it's needed.
Fixes: 08b202b67264 ("bridge br_multicast: IPv6 MLD support.") Signed-off-by: Nikolay Aleksandrov nikolay@cumulusnetworks.com Tested-by: Martin Weinelt martin@linuxlounge.net Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/bridge/br_multicast.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
--- a/net/bridge/br_multicast.c +++ b/net/bridge/br_multicast.c @@ -1353,7 +1353,6 @@ static int br_ip6_multicast_query(struct struct sk_buff *skb, u16 vid) { - const struct ipv6hdr *ip6h = ipv6_hdr(skb); struct mld_msg *mld; struct net_bridge_mdb_entry *mp; struct mld2_query *mld2q; @@ -1397,7 +1396,7 @@ static int br_ip6_multicast_query(struct
if (is_general_query) { saddr.proto = htons(ETH_P_IPV6); - saddr.u.ip6 = ip6h->saddr; + saddr.u.ip6 = ipv6_hdr(skb)->saddr;
br_multicast_query_received(br, port, &br->ip6_other_query, &saddr, max_delay);
From: Nikolay Aleksandrov nikolay@cumulusnetworks.com
[ Upstream commit 2446a68ae6a8cee6d480e2f5b52f5007c7c41312 ]
Don't cache eth dest pointer before calling pskb_may_pull.
Fixes: cf0f02d04a83 ("[BRIDGE]: use llc for receiving STP packets") Signed-off-by: Nikolay Aleksandrov nikolay@cumulusnetworks.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/bridge/br_stp_bpdu.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
--- a/net/bridge/br_stp_bpdu.c +++ b/net/bridge/br_stp_bpdu.c @@ -147,7 +147,6 @@ void br_send_tcn_bpdu(struct net_bridge_ void br_stp_rcv(const struct stp_proto *proto, struct sk_buff *skb, struct net_device *dev) { - const unsigned char *dest = eth_hdr(skb)->h_dest; struct net_bridge_port *p; struct net_bridge *br; const unsigned char *buf; @@ -176,7 +175,7 @@ void br_stp_rcv(const struct stp_proto * if (p->state == BR_STATE_DISABLED) goto out;
- if (!ether_addr_equal(dest, br->group_addr)) + if (!ether_addr_equal(eth_hdr(skb)->h_dest, br->group_addr)) goto out;
if (p->flags & BR_BPDU_GUARD) {
From: Eric Biggers ebiggers@google.com
commit 9bd2bbc01d17ddd567cc0f81f77fe1163e497462 upstream.
gcc 7.1 reports the following warning:
block/elevator.c: In function ‘elv_register’: block/elevator.c:898:5: warning: ‘snprintf’ output may be truncated before the last format character [-Wformat-truncation=] "%s_io_cq", e->elevator_name); ^~~~~~~~~~ block/elevator.c:897:3: note: ‘snprintf’ output between 7 and 22 bytes into a destination of size 21 snprintf(e->icq_cache_name, sizeof(e->icq_cache_name), ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ "%s_io_cq", e->elevator_name); ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The bug is that the name of the icq_cache is 6 characters longer than the elevator name, but only ELV_NAME_MAX + 5 characters were reserved for it --- so in the case of a maximum-length elevator name, the 'q' character in "_io_cq" would be truncated by snprintf(). Fix it by reserving ELV_NAME_MAX + 6 characters instead.
Signed-off-by: Eric Biggers ebiggers@google.com Reviewed-by: Bart Van Assche Bart.VanAssche@sandisk.com Signed-off-by: Jens Axboe axboe@fb.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- include/linux/elevator.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/include/linux/elevator.h +++ b/include/linux/elevator.h @@ -97,7 +97,7 @@ struct elevator_type struct module *elevator_owner;
/* managed by elevator core */ - char icq_cache_name[ELV_NAME_MAX + 5]; /* elvname + "_io_cq" */ + char icq_cache_name[ELV_NAME_MAX + 6]; /* elvname + "_io_cq" */ struct list_head list; };
[ Upstream commit 8fd1ab747d2b1ec7ec663ad0b41a32eaa35117a8 ]
If the server that does not implement NFSv4.1 persistent session semantics reboots while we are performing an exclusive create, then the return value of NFS4ERR_DELAY when we replay the open during the grace period causes us to lose the verifier. When the grace period expires, and we present a new verifier, the server will then correctly reply NFS4ERR_EXIST.
This commit ensures that we always present the same verifier when replaying the OPEN.
Reported-by: Tigran Mkrtchyan tigran.mkrtchyan@desy.de Signed-off-by: Trond Myklebust trond.myklebust@primarydata.com Signed-off-by: Anna Schumaker Anna.Schumaker@Netapp.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/nfs/nfs4proc.c | 41 ++++++++++++++++++++++++++--------------- 1 file changed, 26 insertions(+), 15 deletions(-)
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index 41c8ddbc80dc..d1816ee0c11b 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -997,6 +997,12 @@ struct nfs4_opendata { int cancelled; };
+struct nfs4_open_createattrs { + struct nfs4_label *label; + struct iattr *sattr; + const __u32 verf[2]; +}; + static bool nfs4_clear_cap_atomic_open_v1(struct nfs_server *server, int err, struct nfs4_exception *exception) { @@ -1066,8 +1072,7 @@ static void nfs4_init_opendata_res(struct nfs4_opendata *p)
static struct nfs4_opendata *nfs4_opendata_alloc(struct dentry *dentry, struct nfs4_state_owner *sp, fmode_t fmode, int flags, - const struct iattr *attrs, - struct nfs4_label *label, + const struct nfs4_open_createattrs *c, enum open_claim_type4 claim, gfp_t gfp_mask) { @@ -1075,6 +1080,7 @@ static struct nfs4_opendata *nfs4_opendata_alloc(struct dentry *dentry, struct inode *dir = d_inode(parent); struct nfs_server *server = NFS_SERVER(dir); struct nfs_seqid *(*alloc_seqid)(struct nfs_seqid_counter *, gfp_t); + struct nfs4_label *label = (c != NULL) ? c->label : NULL; struct nfs4_opendata *p;
p = kzalloc(sizeof(*p), gfp_mask); @@ -1131,15 +1137,11 @@ static struct nfs4_opendata *nfs4_opendata_alloc(struct dentry *dentry, case NFS4_OPEN_CLAIM_DELEG_PREV_FH: p->o_arg.fh = NFS_FH(d_inode(dentry)); } - if (attrs != NULL && attrs->ia_valid != 0) { - __u32 verf[2]; - + if (c != NULL && c->sattr != NULL && c->sattr->ia_valid != 0) { p->o_arg.u.attrs = &p->attrs; - memcpy(&p->attrs, attrs, sizeof(p->attrs)); + memcpy(&p->attrs, c->sattr, sizeof(p->attrs));
- verf[0] = jiffies; - verf[1] = current->pid; - memcpy(p->o_arg.u.verifier.data, verf, + memcpy(p->o_arg.u.verifier.data, c->verf, sizeof(p->o_arg.u.verifier.data)); } p->c_arg.fh = &p->o_res.fh; @@ -1653,7 +1655,7 @@ static struct nfs4_opendata *nfs4_open_recoverdata_alloc(struct nfs_open_context struct nfs4_opendata *opendata;
opendata = nfs4_opendata_alloc(ctx->dentry, state->owner, 0, 0, - NULL, NULL, claim, GFP_NOFS); + NULL, claim, GFP_NOFS); if (opendata == NULL) return ERR_PTR(-ENOMEM); opendata->state = state; @@ -2488,8 +2490,7 @@ static int _nfs4_open_and_get_state(struct nfs4_opendata *opendata, static int _nfs4_do_open(struct inode *dir, struct nfs_open_context *ctx, int flags, - struct iattr *sattr, - struct nfs4_label *label, + const struct nfs4_open_createattrs *c, int *opened) { struct nfs4_state_owner *sp; @@ -2501,6 +2502,8 @@ static int _nfs4_do_open(struct inode *dir, struct nfs4_threshold **ctx_th = &ctx->mdsthreshold; fmode_t fmode = ctx->mode & (FMODE_READ|FMODE_WRITE|FMODE_EXEC); enum open_claim_type4 claim = NFS4_OPEN_CLAIM_NULL; + struct iattr *sattr = c->sattr; + struct nfs4_label *label = c->label; struct nfs4_label *olabel = NULL; int status;
@@ -2519,8 +2522,8 @@ static int _nfs4_do_open(struct inode *dir, status = -ENOMEM; if (d_really_is_positive(dentry)) claim = NFS4_OPEN_CLAIM_FH; - opendata = nfs4_opendata_alloc(dentry, sp, fmode, flags, sattr, - label, claim, GFP_KERNEL); + opendata = nfs4_opendata_alloc(dentry, sp, fmode, flags, + c, claim, GFP_KERNEL); if (opendata == NULL) goto err_put_state_owner;
@@ -2596,10 +2599,18 @@ static struct nfs4_state *nfs4_do_open(struct inode *dir, struct nfs_server *server = NFS_SERVER(dir); struct nfs4_exception exception = { }; struct nfs4_state *res; + struct nfs4_open_createattrs c = { + .label = label, + .sattr = sattr, + .verf = { + [0] = (__u32)jiffies, + [1] = (__u32)current->pid, + }, + }; int status;
do { - status = _nfs4_do_open(dir, ctx, flags, sattr, label, opened); + status = _nfs4_do_open(dir, ctx, flags, &c, opened); res = ctx->state; trace_nfs4_open_file(ctx, flags, status); if (status == 0)
[ Upstream commit 44d8660d3bb0a1c8363ebcb906af2343ea8e15f6 ]
An NFSv4.1+ client negotiates the size of its duplicate reply cache size in the initial CREATE_SESSION request. The server preallocates the memory for the duplicate reply cache to ensure that we'll never fail to record the response to a nonidempotent operation.
To prevent a few CREATE_SESSIONs from consuming all of memory we set an upper limit based on nr_free_buffer_pages(). 1/2^10 has been too limiting in practice; 1/2^7 is still less than one percent.
Signed-off-by: J. Bruce Fields bfields@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/nfsd/nfssvc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/fs/nfsd/nfssvc.c b/fs/nfsd/nfssvc.c index b6eb56d18568..0fa990f08daf 100644 --- a/fs/nfsd/nfssvc.c +++ b/fs/nfsd/nfssvc.c @@ -360,7 +360,7 @@ void nfsd_reset_versions(void) */ static void set_max_drc(void) { - #define NFSD_DRC_SIZE_SHIFT 10 + #define NFSD_DRC_SIZE_SHIFT 7 nfsd_drc_max_mem = (nr_free_buffer_pages() >> NFSD_DRC_SIZE_SHIFT) * PAGE_SIZE; nfsd_drc_mem_used = 0;
[ Upstream commit de766e570413bd0484af0b580299b495ada625c3 ]
Instead of granting client's full requests until we hit our DRC size limit and then failing CREATE_SESSIONs (and hence mounts) completely, start granting clients smaller slot tables as we approach the limit.
The factor chosen here is pretty much arbitrary.
Signed-off-by: J. Bruce Fields bfields@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/nfsd/nfs4state.c | 5 +++++ 1 file changed, 5 insertions(+)
diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c index ba27a5ff8677..eb0f8af5203a 100644 --- a/fs/nfsd/nfs4state.c +++ b/fs/nfsd/nfs4state.c @@ -1396,6 +1396,11 @@ static u32 nfsd4_get_drc_mem(struct nfsd4_channel_attrs *ca) spin_lock(&nfsd_drc_lock); avail = min((unsigned long)NFSD_MAX_MEM_PER_SESSION, nfsd_drc_max_mem - nfsd_drc_mem_used); + /* + * Never use more than a third of the remaining memory, + * unless it's the only way to give this client a slot: + */ + avail = clamp_t(int, avail, slotsize, avail/3); num = min_t(int, num, avail / slotsize); nfsd_drc_mem_used += num * slotsize; spin_unlock(&nfsd_drc_lock);
[ Upstream commit c54f24e338ed2a35218f117a4a1afb5f9e2b4e64 ]
We're unintentionally limiting the number of slots per nfsv4.1 session to 10. Often more than 10 simultaneous RPCs are needed for the best performance.
This calculation was meant to prevent any one client from using up more than a third of the limit we set for total memory use across all clients and sessions. Instead, it's limiting the client to a third of the maximum for a single session.
Fix this.
Reported-by: Chris Tracy ctracy@engr.scu.edu Cc: stable@vger.kernel.org Fixes: de766e570413 "nfsd: give out fewer session slots as limit approaches" Signed-off-by: J. Bruce Fields bfields@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/nfsd/nfs4state.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c index eb0f8af5203a..1e1abf1d5769 100644 --- a/fs/nfsd/nfs4state.c +++ b/fs/nfsd/nfs4state.c @@ -1391,16 +1391,16 @@ static u32 nfsd4_get_drc_mem(struct nfsd4_channel_attrs *ca) { u32 slotsize = slot_bytes(ca); u32 num = ca->maxreqs; - int avail; + unsigned long avail, total_avail;
spin_lock(&nfsd_drc_lock); - avail = min((unsigned long)NFSD_MAX_MEM_PER_SESSION, - nfsd_drc_max_mem - nfsd_drc_mem_used); + total_avail = nfsd_drc_max_mem - nfsd_drc_mem_used; + avail = min((unsigned long)NFSD_MAX_MEM_PER_SESSION, total_avail); /* * Never use more than a third of the remaining memory, * unless it's the only way to give this client a slot: */ - avail = clamp_t(int, avail, slotsize, avail/3); + avail = clamp_t(int, avail, slotsize, total_avail/3); num = min_t(int, num, avail / slotsize); nfsd_drc_mem_used += num * slotsize; spin_unlock(&nfsd_drc_lock);
[ Upstream commit 3b2d4dcf71c4a91b420f835e52ddea8192300a3b ]
Since commit 10a68cdf10 (nfsd: fix performance-limiting session calculation) (Linux 5.1-rc1 and 4.19.31), shares from NFS servers with 1 TB of memory cannot be mounted anymore. The mount just hangs on the client.
The gist of commit 10a68cdf10 is the change below.
-avail = clamp_t(int, avail, slotsize, avail/3); +avail = clamp_t(int, avail, slotsize, total_avail/3);
Here are the macros.
#define min_t(type, x, y) __careful_cmp((type)(x), (type)(y), <) #define clamp_t(type, val, lo, hi) min_t(type, max_t(type, val, lo), hi)
`total_avail` is 8,434,659,328 on the 1 TB machine. `clamp_t()` casts the values to `int`, which for 32-bit integers can only hold values −2,147,483,648 (−2^31) through 2,147,483,647 (2^31 − 1).
`avail` (in the function signature) is just 65536, so that no overflow was happening. Before the commit the assignment would result in 21845, and `num = 4`.
When using `total_avail`, it is causing the assignment to be 18446744072226137429 (printed as %lu), and `num` is then 4164608182.
My next guess is, that `nfsd_drc_mem_used` is then exceeded, and the server thinks there is no memory available any more for this client.
Updating the arguments of `clamp_t()` and `min_t()` to `unsigned long` fixes the issue.
Now, `avail = 65536` (before commit 10a68cdf10 `avail = 21845`), but `num = 4` remains the same.
Fixes: c54f24e338ed (nfsd: fix performance-limiting session calculation) Cc: stable@vger.kernel.org Signed-off-by: Paul Menzel pmenzel@molgen.mpg.de Signed-off-by: J. Bruce Fields bfields@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/nfsd/nfs4state.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c index 1e1abf1d5769..ea5cb1ba282f 100644 --- a/fs/nfsd/nfs4state.c +++ b/fs/nfsd/nfs4state.c @@ -1400,7 +1400,7 @@ static u32 nfsd4_get_drc_mem(struct nfsd4_channel_attrs *ca) * Never use more than a third of the remaining memory, * unless it's the only way to give this client a slot: */ - avail = clamp_t(int, avail, slotsize, total_avail/3); + avail = clamp_t(unsigned long, avail, slotsize, total_avail/3); num = min_t(int, num, avail / slotsize); nfsd_drc_mem_used += num * slotsize; spin_unlock(&nfsd_drc_lock);
[ Upstream commit 7ad9db66fafb0f0ad53fd2a66217105da5ddeffe ]
In case mipi_dsi_attach() fails remove the registered panel to avoid added panel without corresponding device.
Signed-off-by: Peter Ujfalusi peter.ujfalusi@ti.com Signed-off-by: Thierry Reding treding@nvidia.com Link: https://patchwork.freedesktop.org/patch/msgid/20190226081153.31334-1-peter.u... Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/gpu/drm/panel/panel-simple.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-)
diff --git a/drivers/gpu/drm/panel/panel-simple.c b/drivers/gpu/drm/panel/panel-simple.c index f418c002d323..ecad4d7c6cd1 100644 --- a/drivers/gpu/drm/panel/panel-simple.c +++ b/drivers/gpu/drm/panel/panel-simple.c @@ -1389,7 +1389,14 @@ static int panel_simple_dsi_probe(struct mipi_dsi_device *dsi) dsi->format = desc->format; dsi->lanes = desc->lanes;
- return mipi_dsi_attach(dsi); + err = mipi_dsi_attach(dsi); + if (err) { + struct panel_simple *panel = dev_get_drvdata(&dsi->dev); + + drm_panel_remove(&panel->base); + } + + return err; }
static int panel_simple_dsi_remove(struct mipi_dsi_device *dsi)
[ Upstream commit 561759292774707b71ee61aecc07724905bb7ef1 ]
If the device rejects the control transfer to enable device-initiated U1/U2 entry, then the device will not initiate U1/U2 transition. To improve the performance, the downstream port should not initate transition to U1/U2 to avoid the delay from the device link command response (no packet can be transmitted while waiting for a response from the device). If the device has some quirks and does not implement U1/U2, it may reject all the link state change requests, and the downstream port may resend and flood the bus with more requests. This will affect the device performance even further. This patch disables the hub-initated U1/U2 if the device-initiated U1/U2 entry fails.
Reference: USB 3.2 spec 7.2.4.2.3
Signed-off-by: Thinh Nguyen thinhn@synopsys.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/usb/core/hub.c | 28 ++++++++++++++++------------ 1 file changed, 16 insertions(+), 12 deletions(-)
diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index 3d714da96ce1..5c274c5440da 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c @@ -3823,6 +3823,9 @@ static int usb_set_lpm_timeout(struct usb_device *udev, * control transfers to set the hub timeout or enable device-initiated U1/U2 * will be successful. * + * If the control transfer to enable device-initiated U1/U2 entry fails, then + * hub-initiated U1/U2 will be disabled. + * * If we cannot set the parent hub U1/U2 timeout, we attempt to let the xHCI * driver know about it. If that call fails, it should be harmless, and just * take up more slightly more bus bandwidth for unnecessary U1/U2 exit latency. @@ -3877,23 +3880,24 @@ static void usb_enable_link_state(struct usb_hcd *hcd, struct usb_device *udev, * host know that this link state won't be enabled. */ hcd->driver->disable_usb3_lpm_timeout(hcd, udev, state); - } else { - /* Only a configured device will accept the Set Feature - * U1/U2_ENABLE - */ - if (udev->actconfig) - usb_set_device_initiated_lpm(udev, state, true); + return; + }
- /* As soon as usb_set_lpm_timeout(timeout) returns 0, the - * hub-initiated LPM is enabled. Thus, LPM is enabled no - * matter the result of usb_set_device_initiated_lpm(). - * The only difference is whether device is able to initiate - * LPM. - */ + /* Only a configured device will accept the Set Feature + * U1/U2_ENABLE + */ + if (udev->actconfig && + usb_set_device_initiated_lpm(udev, state, true) == 0) { if (state == USB3_LPM_U1) udev->usb3_lpm_u1_enabled = 1; else if (state == USB3_LPM_U2) udev->usb3_lpm_u2_enabled = 1; + } else { + /* Don't request U1/U2 entry if the device + * cannot transition to U1/U2. + */ + usb_set_lpm_timeout(udev, state, 0); + hcd->driver->disable_usb3_lpm_timeout(hcd, udev, state); } }
[ Upstream commit 35240ba26a932b279a513f66fa4cabfd7af55221 ]
Current calculator doesn't do it' job quite correct. First of all the max310x baud-rates generator supports the divisor being less than 16. In this case the x2/x4 modes can be used to double or quadruple the reference frequency. But the current baud-rate setter function just filters all these modes out by the first condition and setups these modes only if there is a clocks-baud division remainder. The former doesn't seem right at all, since enabling the x2/x4 modes causes the line noise tolerance reduction and should be only used as a last resort to enable a requested too high baud-rate.
Finally the fraction is supposed to be calculated from D = Fref/(c*baud) formulae, but not from D % 16, which causes the precision loss. So to speak the current baud-rate calculator code works well only if the baud perfectly fits to the uart reference input frequency.
Lets fix the calculator by implementing the algo fully compliant with the fractional baud-rate generator described in the datasheet: D = Fref / (c*baud), where c={16,8,4} is the x1/x2/x4 rate mode respectively, Fref - reference input frequency. The divisor fraction is calculated from the same formulae, but making sure it is found with a resolution of 0.0625 (four bits).
Signed-off-by: Serge Semin fancer.lancer@gmail.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/tty/serial/max310x.c | 51 ++++++++++++++++++++++-------------- 1 file changed, 31 insertions(+), 20 deletions(-)
diff --git a/drivers/tty/serial/max310x.c b/drivers/tty/serial/max310x.c index 0ac0c618954e..a66fb7afecc7 100644 --- a/drivers/tty/serial/max310x.c +++ b/drivers/tty/serial/max310x.c @@ -486,37 +486,48 @@ static bool max310x_reg_precious(struct device *dev, unsigned int reg)
static int max310x_set_baud(struct uart_port *port, int baud) { - unsigned int mode = 0, clk = port->uartclk, div = clk / baud; + unsigned int mode = 0, div = 0, frac = 0, c = 0, F = 0;
- /* Check for minimal value for divider */ - if (div < 16) - div = 16; - - if (clk % baud && (div / 16) < 0x8000) { + /* + * Calculate the integer divisor first. Select a proper mode + * in case if the requested baud is too high for the pre-defined + * clocks frequency. + */ + div = port->uartclk / baud; + if (div < 8) { + /* Mode x4 */ + c = 4; + mode = MAX310X_BRGCFG_4XMODE_BIT; + } else if (div < 16) { /* Mode x2 */ + c = 8; mode = MAX310X_BRGCFG_2XMODE_BIT; - clk = port->uartclk * 2; - div = clk / baud; - - if (clk % baud && (div / 16) < 0x8000) { - /* Mode x4 */ - mode = MAX310X_BRGCFG_4XMODE_BIT; - clk = port->uartclk * 4; - div = clk / baud; - } + } else { + c = 16; }
- max310x_port_write(port, MAX310X_BRGDIVMSB_REG, (div / 16) >> 8); - max310x_port_write(port, MAX310X_BRGDIVLSB_REG, div / 16); - max310x_port_write(port, MAX310X_BRGCFG_REG, (div % 16) | mode); + /* Calculate the divisor in accordance with the fraction coefficient */ + div /= c; + F = c*baud; + + /* Calculate the baud rate fraction */ + if (div > 0) + frac = (16*(port->uartclk % F)) / F; + else + div = 1; + + max310x_port_write(port, MAX310X_BRGDIVMSB_REG, div >> 8); + max310x_port_write(port, MAX310X_BRGDIVLSB_REG, div); + max310x_port_write(port, MAX310X_BRGCFG_REG, frac | mode);
- return DIV_ROUND_CLOSEST(clk, div); + /* Return the actual baud rate we just programmed */ + return (16*port->uartclk) / (c*(16*div + frac)); }
static int max310x_update_best_err(unsigned long f, long *besterr) { /* Use baudrate 115200 for calculate error */ - long err = f % (115200 * 16); + long err = f % (460800 * 16);
if ((*besterr < 0) || (*besterr > err)) { *besterr = err;
[ Upstream commit 3c89c70634bb0b6f48512de873e7a45c7e1fbaa5 ]
The call to of_parse_phandle returns a node pointer with refcount incremented thus it must be explicitly decremented after the last usage.
Detected by coccinelle with the following warnings: ./drivers/pinctrl/pinctrl-rockchip.c:3221:2-8: ERROR: missing of_node_put; acquired a node pointer with refcount incremented on line 3196, but without a corresponding object release within this function. ./drivers/pinctrl/pinctrl-rockchip.c:3223:1-7: ERROR: missing of_node_put; acquired a node pointer with refcount incremented on line 3196, but without a corresponding object release within this function.
Signed-off-by: Wen Yang wen.yang99@zte.com.cn Cc: Linus Walleij linus.walleij@linaro.org Cc: Heiko Stuebner heiko@sntech.de Cc: linux-gpio@vger.kernel.org Cc: linux-rockchip@lists.infradead.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Linus Walleij linus.walleij@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/pinctrl/pinctrl-rockchip.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/pinctrl/pinctrl-rockchip.c b/drivers/pinctrl/pinctrl-rockchip.c index a0651128e23a..616055b5e996 100644 --- a/drivers/pinctrl/pinctrl-rockchip.c +++ b/drivers/pinctrl/pinctrl-rockchip.c @@ -1837,6 +1837,7 @@ static int rockchip_get_bank_data(struct rockchip_pin_bank *bank, base, &rockchip_regmap_config); } + of_node_put(node); }
bank->irq = irq_of_parse_and_map(bank->of_node, 0);
[ Upstream commit 06aaa3d066db87e8478522d910285141d44b1e58 ]
SMC relocation can also be activated earlier by the bootloader, so the driver's behaviour cannot rely on selected kernel config.
When the SMC is relocated, CPM_CR_INIT_TRX cannot be used.
But the only thing CPM_CR_INIT_TRX does is to clear the rstate and tstate registers, so this can be done manually, even when SMC is not relocated.
Signed-off-by: Christophe Leroy christophe.leroy@c-s.fr Fixes: 9ab921201444 ("cpm_uart: fix non-console port startup bug") Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/tty/serial/cpm_uart/cpm_uart_core.c | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-)
diff --git a/drivers/tty/serial/cpm_uart/cpm_uart_core.c b/drivers/tty/serial/cpm_uart/cpm_uart_core.c index 0040c29f651a..b9e137c03fe3 100644 --- a/drivers/tty/serial/cpm_uart/cpm_uart_core.c +++ b/drivers/tty/serial/cpm_uart/cpm_uart_core.c @@ -421,7 +421,16 @@ static int cpm_uart_startup(struct uart_port *port) clrbits16(&pinfo->sccp->scc_sccm, UART_SCCM_RX); } cpm_uart_initbd(pinfo); - cpm_line_cr_cmd(pinfo, CPM_CR_INIT_TRX); + if (IS_SMC(pinfo)) { + out_be32(&pinfo->smcup->smc_rstate, 0); + out_be32(&pinfo->smcup->smc_tstate, 0); + out_be16(&pinfo->smcup->smc_rbptr, + in_be16(&pinfo->smcup->smc_rbase)); + out_be16(&pinfo->smcup->smc_tbptr, + in_be16(&pinfo->smcup->smc_tbase)); + } else { + cpm_line_cr_cmd(pinfo, CPM_CR_INIT_TRX); + } } /* Install interrupt handler. */ retval = request_irq(port->irq, cpm_uart_int, 0, "cpm_uart", port); @@ -875,16 +884,14 @@ static void cpm_uart_init_smc(struct uart_cpm_port *pinfo) (u8 __iomem *)pinfo->tx_bd_base - DPRAM_BASE);
/* - * In case SMC1 is being relocated... + * In case SMC is being relocated... */ -#if defined (CONFIG_I2C_SPI_SMC1_UCODE_PATCH) out_be16(&up->smc_rbptr, in_be16(&pinfo->smcup->smc_rbase)); out_be16(&up->smc_tbptr, in_be16(&pinfo->smcup->smc_tbase)); out_be32(&up->smc_rstate, 0); out_be32(&up->smc_tstate, 0); out_be16(&up->smc_brkcr, 1); /* number of break chars */ out_be16(&up->smc_brkec, 0); -#endif
/* Set up the uart parameters in the * parameter ram. @@ -898,8 +905,6 @@ static void cpm_uart_init_smc(struct uart_cpm_port *pinfo) out_be16(&up->smc_brkec, 0); out_be16(&up->smc_brkcr, 1);
- cpm_line_cr_cmd(pinfo, CPM_CR_INIT_TRX); - /* Set UART mode, 8 bit, no parity, one stop. * Enable receive and transmit. */
[ Upstream commit 65f1a0d39c289bb6fc85635528cd36c4b07f560e ]
If bus_register fails. On its error handling path, it has cleaned up what it has done. There is no need to call bus_unregister again. Otherwise, if bus_unregister is called, issues such as null-ptr-deref will arise.
Syzkaller report this:
kobject_add_internal failed for memstick (error: -12 parent: bus) BUG: KASAN: null-ptr-deref in sysfs_remove_file_ns+0x1b/0x40 fs/sysfs/file.c:467 Read of size 8 at addr 0000000000000078 by task syz-executor.0/4460
Call Trace: __dump_stack lib/dump_stack.c:77 [inline] dump_stack+0xa9/0x10e lib/dump_stack.c:113 __kasan_report+0x171/0x18d mm/kasan/report.c:321 kasan_report+0xe/0x20 mm/kasan/common.c:614 sysfs_remove_file_ns+0x1b/0x40 fs/sysfs/file.c:467 sysfs_remove_file include/linux/sysfs.h:519 [inline] bus_remove_file+0x6c/0x90 drivers/base/bus.c:145 remove_probe_files drivers/base/bus.c:599 [inline] bus_unregister+0x6e/0x100 drivers/base/bus.c:916 ? 0xffffffffc1590000 memstick_init+0x7a/0x1000 [memstick] do_one_initcall+0xb9/0x3b5 init/main.c:914 do_init_module+0xe0/0x330 kernel/module.c:3468 load_module+0x38eb/0x4270 kernel/module.c:3819 __do_sys_finit_module+0x162/0x190 kernel/module.c:3909 do_syscall_64+0x72/0x2a0 arch/x86/entry/common.c:298 entry_SYSCALL_64_after_hwframe+0x49/0xbe
Fixes: baf8532a147d ("memstick: initial commit for Sony MemoryStick support") Reported-by: Hulk Robot hulkci@huawei.com Signed-off-by: Wang Hai wanghai26@huawei.com Signed-off-by: Ulf Hansson ulf.hansson@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/memstick/core/memstick.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-)
diff --git a/drivers/memstick/core/memstick.c b/drivers/memstick/core/memstick.c index 4d673a626db4..1041eb7a6167 100644 --- a/drivers/memstick/core/memstick.c +++ b/drivers/memstick/core/memstick.c @@ -629,13 +629,18 @@ static int __init memstick_init(void) return -ENOMEM;
rc = bus_register(&memstick_bus_type); - if (!rc) - rc = class_register(&memstick_host_class); + if (rc) + goto error_destroy_workqueue;
- if (!rc) - return 0; + rc = class_register(&memstick_host_class); + if (rc) + goto error_bus_unregister; + + return 0;
+error_bus_unregister: bus_unregister(&memstick_bus_type); +error_destroy_workqueue: destroy_workqueue(workqueue);
return rc;
[ Upstream commit c7ad9ba0611c53cfe194223db02e3bca015f0674 ]
When modprobe/rmmod/modprobe module, if platform_driver_register() fails, the kernel complained,
proc_dir_entry 'driver/digicolor-usart' already registered WARNING: CPU: 1 PID: 5636 at fs/proc/generic.c:360 proc_register+0x19d/0x270
Fix this by adding uart_unregister_driver() when platform_driver_register() fails.
Reported-by: Hulk Robot hulkci@huawei.com Signed-off-by: Kefeng Wang wangkefeng.wang@huawei.com Acked-by: Baruch Siach baruch@tkos.co.il Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/tty/serial/digicolor-usart.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/drivers/tty/serial/digicolor-usart.c b/drivers/tty/serial/digicolor-usart.c index a80cdad114f3..d8cb94997487 100644 --- a/drivers/tty/serial/digicolor-usart.c +++ b/drivers/tty/serial/digicolor-usart.c @@ -544,7 +544,11 @@ static int __init digicolor_uart_init(void) if (ret) return ret;
- return platform_driver_register(&digicolor_uart_platform); + ret = platform_driver_register(&digicolor_uart_platform); + if (ret) + uart_unregister_driver(&digicolor_uart); + + return ret; } module_init(digicolor_uart_init);
[ Upstream commit ba3684f99f1b25d2a30b6956d02d339d7acb9799 ]
The function msm_wait_for_xmitr can be taken with interrupts disabled. In order to avoid a potential system lockup - demonstrated under stress testing conditions on SoC QCS404/5 - make sure we wait for a bounded amount of time.
Tested on SoC QCS404.
Signed-off-by: Jorge Ramirez-Ortiz jorge.ramirez-ortiz@linaro.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/tty/serial/msm_serial.c | 4 ++++ 1 file changed, 4 insertions(+)
diff --git a/drivers/tty/serial/msm_serial.c b/drivers/tty/serial/msm_serial.c index 5f0ded6fc4e9..eaeb098b5d6a 100644 --- a/drivers/tty/serial/msm_serial.c +++ b/drivers/tty/serial/msm_serial.c @@ -222,10 +222,14 @@ static void msm_request_rx_dma(struct msm_port *msm_port, resource_size_t base)
static inline void msm_wait_for_xmitr(struct uart_port *port) { + unsigned int timeout = 500000; + while (!(msm_read(port, UART_SR) & UART_SR_TX_EMPTY)) { if (msm_read(port, UART_ISR) & UART_ISR_TX_READY) break; udelay(1); + if (!timeout--) + break; } msm_write(port, UART_CR_CMD_RESET_TX_READY, UART_CR); }
[ Upstream commit 9ff3a5c88e1f1ab17a31402b96d45abe14aab9d7 ]
After data is copied to the cache entry, atomic_set is used indicate that the data is the entry is valid without appropriate memory barriers. Similarly the read side was missing the corresponding memory barriers.
Signed-off-by: David Riley davidriley@chromium.org Link: http://patchwork.freedesktop.org/patch/msgid/20190610211810.253227-5-davidri... Signed-off-by: Gerd Hoffmann kraxel@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/gpu/drm/virtio/virtgpu_ioctl.c | 3 +++ drivers/gpu/drm/virtio/virtgpu_vq.c | 2 ++ 2 files changed, 5 insertions(+)
diff --git a/drivers/gpu/drm/virtio/virtgpu_ioctl.c b/drivers/gpu/drm/virtio/virtgpu_ioctl.c index 6296e9f270ca..0b8f8c10f2ed 100644 --- a/drivers/gpu/drm/virtio/virtgpu_ioctl.c +++ b/drivers/gpu/drm/virtio/virtgpu_ioctl.c @@ -535,6 +535,9 @@ static int virtio_gpu_get_caps_ioctl(struct drm_device *dev, ret = wait_event_timeout(vgdev->resp_wq, atomic_read(&cache_ent->is_valid), 5 * HZ);
+ /* is_valid check must proceed before copy of the cache entry. */ + smp_rmb(); + ptr = cache_ent->caps_cache;
copy_exit: diff --git a/drivers/gpu/drm/virtio/virtgpu_vq.c b/drivers/gpu/drm/virtio/virtgpu_vq.c index 52436b3c01bb..a1b3ea1ccb65 100644 --- a/drivers/gpu/drm/virtio/virtgpu_vq.c +++ b/drivers/gpu/drm/virtio/virtgpu_vq.c @@ -618,6 +618,8 @@ static void virtio_gpu_cmd_capset_cb(struct virtio_gpu_device *vgdev, cache_ent->id == le32_to_cpu(cmd->capset_id)) { memcpy(cache_ent->caps_cache, resp->capset_data, cache_ent->size); + /* Copy must occur before is_valid is signalled. */ + smp_wmb(); atomic_set(&cache_ent->is_valid, 1); break; }
[ Upstream commit d4a36e82924d3305a17ac987a510f3902df5a4b2 ]
This patch fixes memory leak at error paths of the probe function. In for_each_child_of_node, if the loop returns, the driver should call of_put_node() before returns.
Reported-by: Julia Lawall julia.lawall@lip6.fr Fixes: 1233f59f745b237 ("phy: Renesas R-Car Gen2 PHY driver") Signed-off-by: Yoshihiro Shimoda yoshihiro.shimoda.uh@renesas.com Reviewed-by: Geert Uytterhoeven geert+renesas@glider.be Signed-off-by: Kishon Vijay Abraham I kishon@ti.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/phy/phy-rcar-gen2.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/drivers/phy/phy-rcar-gen2.c b/drivers/phy/phy-rcar-gen2.c index c7a05996d5c1..99d2b73654f4 100644 --- a/drivers/phy/phy-rcar-gen2.c +++ b/drivers/phy/phy-rcar-gen2.c @@ -287,6 +287,7 @@ static int rcar_gen2_phy_probe(struct platform_device *pdev) error = of_property_read_u32(np, "reg", &channel_num); if (error || channel_num > 2) { dev_err(dev, "Invalid "reg" property\n"); + of_node_put(np); return error; } channel->select_mask = select_mask[channel_num]; @@ -302,6 +303,7 @@ static int rcar_gen2_phy_probe(struct platform_device *pdev) &rcar_gen2_phy_ops); if (IS_ERR(phy->phy)) { dev_err(dev, "Failed to create PHY\n"); + of_node_put(np); return PTR_ERR(phy->phy); } phy_set_drvdata(phy->phy, phy);
[ Upstream commit e59a175faa8df9d674247946f2a5a9c29c835725 ]
CPU online/offline code paths are sensitive to parts of the device tree (various cpu node properties, cache nodes) that can be changed as a result of a migration.
Prevent CPU hotplug while the device tree potentially is inconsistent.
Fixes: 410bccf97881 ("powerpc/pseries: Partition migration in the kernel") Signed-off-by: Nathan Lynch nathanl@linux.ibm.com Reviewed-by: Gautham R. Shenoy ego@linux.vnet.ibm.com Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Sasha Levin sashal@kernel.org --- arch/powerpc/platforms/pseries/mobility.c | 9 +++++++++ 1 file changed, 9 insertions(+)
diff --git a/arch/powerpc/platforms/pseries/mobility.c b/arch/powerpc/platforms/pseries/mobility.c index c773396d0969..fcd1a32267c4 100644 --- a/arch/powerpc/platforms/pseries/mobility.c +++ b/arch/powerpc/platforms/pseries/mobility.c @@ -9,6 +9,7 @@ * 2 as published by the Free Software Foundation. */
+#include <linux/cpu.h> #include <linux/kernel.h> #include <linux/kobject.h> #include <linux/smp.h> @@ -309,11 +310,19 @@ void post_mobility_fixup(void) if (rc) printk(KERN_ERR "Post-mobility activate-fw failed: %d\n", rc);
+ /* + * We don't want CPUs to go online/offline while the device + * tree is being updated. + */ + cpus_read_lock(); + rc = pseries_devicetree_update(MIGRATION_SCOPE); if (rc) printk(KERN_ERR "Post-mobility device tree update " "failed: %d\n", rc);
+ cpus_read_unlock(); + /* Possibly switch to a new RFI flush type */ pseries_setup_rfi_flush();
[ Upstream commit e610a466d16a086e321f0bd421e2fc75cff28605 ]
It's common for the platform to replace the cache device nodes after a migration. Since the cacheinfo code is never informed about this, it never drops its references to the source system's cache nodes, causing it to wind up in an inconsistent state resulting in warnings and oopses as soon as CPU online/offline occurs after the migration, e.g.
cache for /cpus/l3-cache@3113(Unified) refers to cache for /cpus/l2-cache@200d(Unified) WARNING: CPU: 15 PID: 86 at arch/powerpc/kernel/cacheinfo.c:176 release_cache+0x1bc/0x1d0 [...] NIP release_cache+0x1bc/0x1d0 LR release_cache+0x1b8/0x1d0 Call Trace: release_cache+0x1b8/0x1d0 (unreliable) cacheinfo_cpu_offline+0x1c4/0x2c0 unregister_cpu_online+0x1b8/0x260 cpuhp_invoke_callback+0x114/0xf40 cpuhp_thread_fun+0x270/0x310 smpboot_thread_fn+0x2c8/0x390 kthread+0x1b8/0x1c0 ret_from_kernel_thread+0x5c/0x68
Using device tree notifiers won't work since we want to rebuild the hierarchy only after all the removals and additions have occurred and the device tree is in a consistent state. Call cacheinfo_teardown() before processing device tree updates, and rebuild the hierarchy afterward.
Fixes: 410bccf97881 ("powerpc/pseries: Partition migration in the kernel") Signed-off-by: Nathan Lynch nathanl@linux.ibm.com Reviewed-by: Gautham R. Shenoy ego@linux.vnet.ibm.com Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Sasha Levin sashal@kernel.org --- arch/powerpc/platforms/pseries/mobility.c | 10 ++++++++++ 1 file changed, 10 insertions(+)
diff --git a/arch/powerpc/platforms/pseries/mobility.c b/arch/powerpc/platforms/pseries/mobility.c index fcd1a32267c4..e85767c74e81 100644 --- a/arch/powerpc/platforms/pseries/mobility.c +++ b/arch/powerpc/platforms/pseries/mobility.c @@ -22,6 +22,7 @@ #include <asm/machdep.h> #include <asm/rtas.h> #include "pseries.h" +#include "../../kernel/cacheinfo.h"
static struct kobject *mobility_kobj;
@@ -316,11 +317,20 @@ void post_mobility_fixup(void) */ cpus_read_lock();
+ /* + * It's common for the destination firmware to replace cache + * nodes. Release all of the cacheinfo hierarchy's references + * before updating the device tree. + */ + cacheinfo_teardown(); + rc = pseries_devicetree_update(MIGRATION_SCOPE); if (rc) printk(KERN_ERR "Post-mobility device tree update " "failed: %d\n", rc);
+ cacheinfo_rebuild(); + cpus_read_unlock();
/* Possibly switch to a new RFI flush type */
[ Upstream commit 508595515f4bcfe36246e4a565cf280937aeaade ]
In some cases the "Allocate & copy" block in ffs_epfile_io() is not executed. Consequently, in such a case ffs_alloc_buffer() is never called and struct ffs_io_data is not initialized properly. This in turn leads to problems when ffs_free_buffer() is called at the end of ffs_epfile_io().
This patch uses kzalloc() instead of kmalloc() in the aio case and memset() in non-aio case to properly initialize struct ffs_io_data.
Signed-off-by: Andrzej Pietrasiewicz andrzej.p@collabora.com Signed-off-by: Felipe Balbi felipe.balbi@linux.intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/usb/gadget/function/f_fs.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c index 4800bb22cdd6..4cb1355271ec 100644 --- a/drivers/usb/gadget/function/f_fs.c +++ b/drivers/usb/gadget/function/f_fs.c @@ -912,11 +912,12 @@ static ssize_t ffs_epfile_write_iter(struct kiocb *kiocb, struct iov_iter *from) ENTER();
if (!is_sync_kiocb(kiocb)) { - p = kmalloc(sizeof(io_data), GFP_KERNEL); + p = kzalloc(sizeof(io_data), GFP_KERNEL); if (unlikely(!p)) return -ENOMEM; p->aio = true; } else { + memset(p, 0, sizeof(*p)); p->aio = false; }
@@ -948,11 +949,12 @@ static ssize_t ffs_epfile_read_iter(struct kiocb *kiocb, struct iov_iter *to) ENTER();
if (!is_sync_kiocb(kiocb)) { - p = kmalloc(sizeof(io_data), GFP_KERNEL); + p = kzalloc(sizeof(io_data), GFP_KERNEL); if (unlikely(!p)) return -ENOMEM; p->aio = true; } else { + memset(p, 0, sizeof(*p)); p->aio = false; }
[ Upstream commit df5be5be8735ef2ae80d5ae1f2453cd81a035c4b ]
When the firmware does PCI BAR resource allocation, it passes the assigned addresses and flags (prefetch/64bit/...) via the "reg" property of a PCI device device tree node so the kernel does not need to do resource allocation.
The flags are stored in resource::flags - the lower byte stores PCI_BASE_ADDRESS_SPACE/etc bits and the other bytes are IORESOURCE_IO/etc. Some flags from PCI_BASE_ADDRESS_xxx and IORESOURCE_xxx are duplicated, such as PCI_BASE_ADDRESS_MEM_PREFETCH/PCI_BASE_ADDRESS_MEM_TYPE_64/etc. When parsing the "reg" property, we copy the prefetch flag but we skip on PCI_BASE_ADDRESS_MEM_TYPE_64 which leaves the flags out of sync.
The missing IORESOURCE_MEM_64 flag comes into play under 2 conditions: 1. we remove PCI_PROBE_ONLY for pseries (by hacking pSeries_setup_arch() or by passing "/chosen/linux,pci-probe-only"); 2. we request resource alignment (by passing pci=resource_alignment= via the kernel cmd line to request PAGE_SIZE alignment or defining ppc_md.pcibios_default_alignment which returns anything but 0). Note that the alignment requests are ignored if PCI_PROBE_ONLY is enabled.
With 1) and 2), the generic PCI code in the kernel unconditionally decides to: - reassign the BARs in pci_specified_resource_alignment() (works fine) - write new BARs to the device - this fails for 64bit BARs as the generic code looks at IORESOURCE_MEM_64 (not set) and writes only lower 32bits of the BAR and leaves the upper 32bit unmodified which breaks BAR mapping in the hypervisor.
This fixes the issue by copying the flag. This is useful if we want to enforce certain BAR alignment per platform as handling subpage sized BARs is proven to cause problems with hotplug (SLOF already aligns BARs to 64k).
Signed-off-by: Alexey Kardashevskiy aik@ozlabs.ru Reviewed-by: Sam Bobroff sbobroff@linux.ibm.com Reviewed-by: Oliver O'Halloran oohall@gmail.com Reviewed-by: Shawn Anastasio shawn@anastas.io Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Sasha Levin sashal@kernel.org --- arch/powerpc/kernel/pci_of_scan.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/arch/powerpc/kernel/pci_of_scan.c b/arch/powerpc/kernel/pci_of_scan.c index 2e710c15893f..a38d7293460d 100644 --- a/arch/powerpc/kernel/pci_of_scan.c +++ b/arch/powerpc/kernel/pci_of_scan.c @@ -45,6 +45,8 @@ static unsigned int pci_parse_of_flags(u32 addr0, int bridge) if (addr0 & 0x02000000) { flags = IORESOURCE_MEM | PCI_BASE_ADDRESS_SPACE_MEMORY; flags |= (addr0 >> 22) & PCI_BASE_ADDRESS_MEM_TYPE_64; + if (flags & PCI_BASE_ADDRESS_MEM_TYPE_64) + flags |= IORESOURCE_MEM_64; flags |= (addr0 >> 28) & PCI_BASE_ADDRESS_MEM_TYPE_1M; if (addr0 & 0x40000000) flags |= IORESOURCE_PREFETCH
[ Upstream commit dc6b698a86fe40a50525433eb8e92a267847f6f9 ]
With CONFIG_PROVE_LOCKING=y, using sysfs to remove a bridge with a device below it causes a lockdep warning, e.g.,
# echo 1 > /sys/class/pci_bus/0000:00/device/0000:00:00.0/remove ============================================ WARNING: possible recursive locking detected ... pci_bus 0000:01: busn_res: [bus 01] is released
The remove recursively removes the subtree below the bridge. Each call uses a different lock so there's no deadlock, but the locks were all created with the same lockdep key so the lockdep checker can't tell them apart.
Mark the "remove" sysfs attribute with __ATTR_IGNORE_LOCKDEP() as it is safe to ignore the lockdep check between different "remove" kernfs instances.
There's discussion about a similar issue in USB at [1], which resulted in 356c05d58af0 ("sysfs: get rid of some lockdep false positives") and e9b526fe7048 ("i2c: suppress lockdep warning on delete_device"), which do basically the same thing for USB "remove" and i2c "delete_device" files.
[1] https://lore.kernel.org/r/Pine.LNX.4.44L0.1204251436140.1206-100000@iolanthe... Link: https://lore.kernel.org/r/20190526225151.3865-1-marek.vasut@gmail.com Signed-off-by: Marek Vasut marek.vasut+renesas@gmail.com [bhelgaas: trim commit log, details at above links] Signed-off-by: Bjorn Helgaas bhelgaas@google.com Cc: Geert Uytterhoeven geert+renesas@glider.be Cc: Phil Edworthy phil.edworthy@renesas.com Cc: Simon Horman horms+renesas@verge.net.au Cc: Tejun Heo tj@kernel.org Cc: Wolfram Sang wsa@the-dreams.de Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/pci/pci-sysfs.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c index 5fb4ed6ea322..6ac6618c1c10 100644 --- a/drivers/pci/pci-sysfs.c +++ b/drivers/pci/pci-sysfs.c @@ -371,7 +371,7 @@ static ssize_t remove_store(struct device *dev, struct device_attribute *attr, pci_stop_and_remove_bus_device_locked(to_pci_dev(dev)); return count; } -static struct device_attribute dev_remove_attr = __ATTR(remove, +static struct device_attribute dev_remove_attr = __ATTR_IGNORE_LOCKDEP(remove, (S_IWUSR|S_IWGRP), NULL, remove_store);
[ Upstream commit 208a68c8393d6041a90862992222f3d7943d44d6 ]
On some machines, iio-sensor-proxy was returning all 0's for IIO sensor values. It turns out that the bits_used for this sensor is 32, which makes the mask calculation:
*mask = (1 << 32) - 1;
If the compiler interprets the 1 literals as 32-bit ints, it generates undefined behavior depending on compiler version and optimization level. On my system, it optimizes out the shift, so the mask value becomes
*mask = (1) - 1;
With a mask value of 0, iio-sensor-proxy will always return 0 for every axis.
Avoid incorrect 0 values caused by compiler optimization.
See original fix by Brett Dutro brett.dutro@gmail.com in iio-sensor-proxy: https://github.com/hadess/iio-sensor-proxy/commit/9615ceac7c134d838660e20972...
Signed-off-by: Bastien Nocera hadess@hadess.net Signed-off-by: Jonathan Cameron Jonathan.Cameron@huawei.com Signed-off-by: Sasha Levin sashal@kernel.org --- tools/iio/iio_utils.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/tools/iio/iio_utils.c b/tools/iio/iio_utils.c index 5eb6793f3972..2d0dcd6fc64c 100644 --- a/tools/iio/iio_utils.c +++ b/tools/iio/iio_utils.c @@ -163,9 +163,9 @@ int iioutils_get_type(unsigned *is_signed, unsigned *bytes, unsigned *bits_used, *be = (endianchar == 'b'); *bytes = padint / 8; if (*bits_used == 64) - *mask = ~0; + *mask = ~(0ULL); else - *mask = (1ULL << *bits_used) - 1; + *mask = (1ULL << *bits_used) - 1ULL;
*is_signed = (signchar == 's'); if (fclose(sysfsfp)) {
[ Upstream commit 80e5302e4bc85a6b685b7668c36c6487b5f90e9a ]
An impending change to enable HAVE_C_RECORDMCOUNT on powerpc leads to warnings such as the following:
# modprobe kprobe_example ftrace-powerpc: Not expected bl: opcode is 3c4c0001 WARNING: CPU: 0 PID: 227 at kernel/trace/ftrace.c:2001 ftrace_bug+0x90/0x318 Modules linked in: CPU: 0 PID: 227 Comm: modprobe Not tainted 5.2.0-rc6-00678-g1c329100b942 #2 NIP: c000000000264318 LR: c00000000025d694 CTR: c000000000f5cd30 REGS: c000000001f2b7b0 TRAP: 0700 Not tainted (5.2.0-rc6-00678-g1c329100b942) MSR: 900000010282b033 <SF,HV,VEC,VSX,EE,FP,ME,IR,DR,RI,LE,TM[E]> CR: 28228222 XER: 00000000 CFAR: c0000000002642fc IRQMASK: 0 <snip> NIP [c000000000264318] ftrace_bug+0x90/0x318 LR [c00000000025d694] ftrace_process_locs+0x4f4/0x5e0 Call Trace: [c000000001f2ba40] [0000000000000004] 0x4 (unreliable) [c000000001f2bad0] [c00000000025d694] ftrace_process_locs+0x4f4/0x5e0 [c000000001f2bb90] [c00000000020ff10] load_module+0x25b0/0x30c0 [c000000001f2bd00] [c000000000210cb0] sys_finit_module+0xc0/0x130 [c000000001f2be20] [c00000000000bda4] system_call+0x5c/0x70 Instruction dump: 419e0018 2f83ffff 419e00bc 2f83ffea 409e00cc 4800001c 0fe00000 3c62ff96 39000001 39400000 386386d0 480000c4 <0fe00000> 3ce20003 39000001 3c62ff96 ---[ end trace 4c438d5cebf78381 ]--- ftrace failed to modify [<c0080000012a0008>] 0xc0080000012a0008 actual: 01:00:4c:3c Initializing ftrace call sites ftrace record flags: 2000000 (0) expected tramp: c00000000006af4c
Looking at the relocation records in __mcount_loc shows a few spurious entries:
RELOCATION RECORDS FOR [__mcount_loc]: OFFSET TYPE VALUE 0000000000000000 R_PPC64_ADDR64 .text.unlikely+0x0000000000000008 0000000000000008 R_PPC64_ADDR64 .text.unlikely+0x0000000000000014 0000000000000010 R_PPC64_ADDR64 .text.unlikely+0x0000000000000060 0000000000000018 R_PPC64_ADDR64 .text.unlikely+0x00000000000000b4 0000000000000020 R_PPC64_ADDR64 .init.text+0x0000000000000008 0000000000000028 R_PPC64_ADDR64 .init.text+0x0000000000000014
The first entry in each section is incorrect. Looking at the relocation records, the spurious entries correspond to the R_PPC64_ENTRY records:
RELOCATION RECORDS FOR [.text.unlikely]: OFFSET TYPE VALUE 0000000000000000 R_PPC64_REL64 .TOC.-0x0000000000000008 0000000000000008 R_PPC64_ENTRY *ABS* 0000000000000014 R_PPC64_REL24 _mcount <snip>
The problem is that we are not validating the return value from get_mcountsym() in sift_rel_mcount(). With this entry, mcountsym is 0, but Elf_r_sym(relp) also ends up being 0. Fix this by ensuring mcountsym is valid before processing the entry.
Signed-off-by: Naveen N. Rao naveen.n.rao@linux.vnet.ibm.com Acked-by: Steven Rostedt (VMware) rostedt@goodmis.org Tested-by: Satheesh Rajendran sathnaga@linux.vnet.ibm.com Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Sasha Levin sashal@kernel.org --- scripts/recordmcount.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/scripts/recordmcount.h b/scripts/recordmcount.h index b9897e2be404..04151ede8043 100644 --- a/scripts/recordmcount.h +++ b/scripts/recordmcount.h @@ -326,7 +326,8 @@ static uint_t *sift_rel_mcount(uint_t *mlocp, if (!mcountsym) mcountsym = get_mcountsym(sym0, relp, str0);
- if (mcountsym == Elf_r_sym(relp) && !is_fake_mcount(relp)) { + if (mcountsym && mcountsym == Elf_r_sym(relp) && + !is_fake_mcount(relp)) { uint_t const addend = _w(_w(relp->r_offset) - recval + mcount_adjust); mrelp->r_offset = _w(offbase
[ Upstream commit c176c6d7e932662668bcaec2d763657096589d85 ]
The logic for setting the of_node on devices created by mfd did not set the fwnode pointer to match, which caused fwnode-based APIs to malfunction on these devices since the fwnode pointer was null. Fix this.
Signed-off-by: Robert Hancock hancock@sedsystems.ca Signed-off-by: Lee Jones lee.jones@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/mfd/mfd-core.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/mfd/mfd-core.c b/drivers/mfd/mfd-core.c index 022c9374ce8b..215bb5eeb5ac 100644 --- a/drivers/mfd/mfd-core.c +++ b/drivers/mfd/mfd-core.c @@ -178,6 +178,7 @@ static int mfd_add_device(struct device *parent, int id, for_each_child_of_node(parent->of_node, np) { if (of_device_is_compatible(np, cell->of_compatible)) { pdev->dev.of_node = np; + pdev->dev.fwnode = &np->fwnode; break; } }
[ Upstream commit 5da6cbcd2f395981aa9bfc571ace99f1c786c985 ]
When the driver is used with a subdevice that is disabled in the kernel configuration, clang gets a little confused about the control flow and fails to notice that n_subdevs is only uninitialized when subdevs is NULL, and we check for that, leading to a false-positive warning:
drivers/mfd/arizona-core.c:1423:19: error: variable 'n_subdevs' is uninitialized when used here [-Werror,-Wuninitialized] subdevs, n_subdevs, NULL, 0, NULL); ^~~~~~~~~ drivers/mfd/arizona-core.c:999:15: note: initialize the variable 'n_subdevs' to silence this warning int n_subdevs, ret, i; ^ = 0
Ideally, we would rearrange the code to avoid all those early initializations and have an explicit exit in each disabled case, but it's much easier to chicken out and add one more initialization here to shut up the warning.
Signed-off-by: Arnd Bergmann arnd@arndb.de Reviewed-by: Nathan Chancellor natechancellor@gmail.com Signed-off-by: Charles Keepax ckeepax@opensource.cirrus.com Signed-off-by: Lee Jones lee.jones@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/mfd/arizona-core.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/mfd/arizona-core.c b/drivers/mfd/arizona-core.c index d474732cc65c..fb54de5c1aba 100644 --- a/drivers/mfd/arizona-core.c +++ b/drivers/mfd/arizona-core.c @@ -967,7 +967,7 @@ int arizona_dev_init(struct arizona *arizona) unsigned int reg, val, mask; int (*apply_patch)(struct arizona *) = NULL; const struct mfd_cell *subdevs = NULL; - int n_subdevs, ret, i; + int n_subdevs = 0, ret, i;
dev_set_drvdata(arizona->dev, arizona); mutex_init(&arizona->clk_lock);
[ Upstream commit 80bf6ceaf9310b3f61934c69b382d4912deee049 ]
When we get into activate_mm(), lockdep complains that we're doing something strange:
WARNING: possible circular locking dependency detected 5.1.0-10252-gb00152307319-dirty #121 Not tainted ------------------------------------------------------ inside.sh/366 is trying to acquire lock: (____ptrval____) (&(&p->alloc_lock)->rlock){+.+.}, at: flush_old_exec+0x703/0x8d7
but task is already holding lock: (____ptrval____) (&mm->mmap_sem){++++}, at: flush_old_exec+0x6c5/0x8d7
which lock already depends on the new lock.
the existing dependency chain (in reverse order) is:
-> #1 (&mm->mmap_sem){++++}: [...] __lock_acquire+0x12ab/0x139f lock_acquire+0x155/0x18e down_write+0x3f/0x98 flush_old_exec+0x748/0x8d7 load_elf_binary+0x2ca/0xddb [...]
-> #0 (&(&p->alloc_lock)->rlock){+.+.}: [...] __lock_acquire+0x12ab/0x139f lock_acquire+0x155/0x18e _raw_spin_lock+0x30/0x83 flush_old_exec+0x703/0x8d7 load_elf_binary+0x2ca/0xddb [...]
other info that might help us debug this:
Possible unsafe locking scenario:
CPU0 CPU1 ---- ---- lock(&mm->mmap_sem); lock(&(&p->alloc_lock)->rlock); lock(&mm->mmap_sem); lock(&(&p->alloc_lock)->rlock);
*** DEADLOCK ***
2 locks held by inside.sh/366: #0: (____ptrval____) (&sig->cred_guard_mutex){+.+.}, at: __do_execve_file+0x12d/0x869 #1: (____ptrval____) (&mm->mmap_sem){++++}, at: flush_old_exec+0x6c5/0x8d7
stack backtrace: CPU: 0 PID: 366 Comm: inside.sh Not tainted 5.1.0-10252-gb00152307319-dirty #121 Stack: [...] Call Trace: [<600420de>] show_stack+0x13b/0x155 [<6048906b>] dump_stack+0x2a/0x2c [<6009ae64>] print_circular_bug+0x332/0x343 [<6009c5c6>] check_prev_add+0x669/0xdad [<600a06b4>] __lock_acquire+0x12ab/0x139f [<6009f3d0>] lock_acquire+0x155/0x18e [<604a07e0>] _raw_spin_lock+0x30/0x83 [<60151e6a>] flush_old_exec+0x703/0x8d7 [<601a8eb8>] load_elf_binary+0x2ca/0xddb [...]
I think it's because in exec_mmap() we have
down_read(&old_mm->mmap_sem); ... task_lock(tsk); ... activate_mm(active_mm, mm); (which does down_write(&mm->mmap_sem))
I'm not really sure why lockdep throws in the whole knowledge about the task lock, but it seems that old_mm and mm shouldn't ever be the same (and it doesn't deadlock) so tell lockdep that they're different.
Signed-off-by: Johannes Berg johannes.berg@intel.com Signed-off-by: Richard Weinberger richard@nod.at Signed-off-by: Sasha Levin sashal@kernel.org --- arch/um/include/asm/mmu_context.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/arch/um/include/asm/mmu_context.h b/arch/um/include/asm/mmu_context.h index 941527e507f7..f618f45fc8e9 100644 --- a/arch/um/include/asm/mmu_context.h +++ b/arch/um/include/asm/mmu_context.h @@ -42,7 +42,7 @@ static inline void activate_mm(struct mm_struct *old, struct mm_struct *new) * when the new ->mm is used for the first time. */ __switch_mm(&new->context.id); - down_write(&new->mmap_sem); + down_write_nested(&new->mmap_sem, 1); uml_setup_stubs(new); up_write(&new->mmap_sem); }
[ Upstream commit 3ab3a0689e74e6aa5b41360bc18861040ddef5b1 ]
When testing out gpio-keys with a button, a spurious interrupt (and therefore a key press or release event) gets triggered as soon as the driver enables the irq line for the first time.
This patch clears any potential bogus generated interrupt that was caused by the switching of the associated irq's type and polarity.
Signed-off-by: Christian Lamparter chunkeey@gmail.com Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Sasha Levin sashal@kernel.org --- arch/powerpc/sysdev/uic.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/arch/powerpc/sysdev/uic.c b/arch/powerpc/sysdev/uic.c index 6893d8f236df..225346dda151 100644 --- a/arch/powerpc/sysdev/uic.c +++ b/arch/powerpc/sysdev/uic.c @@ -158,6 +158,7 @@ static int uic_set_irq_type(struct irq_data *d, unsigned int flow_type)
mtdcr(uic->dcrbase + UIC_PR, pr); mtdcr(uic->dcrbase + UIC_TR, tr); + mtdcr(uic->dcrbase + UIC_SR, ~mask);
raw_spin_unlock_irqrestore(&uic->lock, flags);
[ Upstream commit 8493eab02608b0e82f67b892aa72882e510c31d0 ]
When uart_flush_buffer() is called, the .flush_buffer() callback zeroes the tx_dma_len field. This may race with the work queue function handling transmit DMA requests:
1. If the buffer is flushed before the first DMA API call, dmaengine_prep_slave_single() may be called with a zero length, causing the DMA request to never complete, leading to messages like:
rcar-dmac e7300000.dma-controller: Channel Address Error happen
and, with debug enabled:
sh-sci e6e88000.serial: sci_dma_tx_work_fn: ffff800639b55000: 0...0, cookie 126
and DMA timeouts.
2. If the buffer is flushed after the first DMA API call, but before the second, dma_sync_single_for_device() may be called with a zero length, causing the transmit data not to be flushed to RAM, and leading to stale data being output.
Fix this by: 1. Letting sci_dma_tx_work_fn() return immediately if the transmit buffer is empty, 2. Extending the critical section to cover all DMA preparational work, so tx_dma_len stays consistent for all of it, 3. Using local copies of circ_buf.head and circ_buf.tail, to make sure they match the actual operation above.
Reported-by: Eugeniu Rosca erosca@de.adit-jv.com Suggested-by: Yoshihiro Shimoda yoshihiro.shimoda.uh@renesas.com Signed-off-by: Geert Uytterhoeven geert+renesas@glider.be Reviewed-by: Eugeniu Rosca erosca@de.adit-jv.com Tested-by: Eugeniu Rosca erosca@de.adit-jv.com Link: https://lore.kernel.org/r/20190624123540.20629-2-geert+renesas@glider.be Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/tty/serial/sh-sci.c | 22 +++++++++++++++------- 1 file changed, 15 insertions(+), 7 deletions(-)
diff --git a/drivers/tty/serial/sh-sci.c b/drivers/tty/serial/sh-sci.c index 669134e27ed9..c450e32c153d 100644 --- a/drivers/tty/serial/sh-sci.c +++ b/drivers/tty/serial/sh-sci.c @@ -1203,6 +1203,7 @@ static void work_fn_tx(struct work_struct *work) struct uart_port *port = &s->port; struct circ_buf *xmit = &port->state->xmit; dma_addr_t buf; + int head, tail;
/* * DMA is idle now. @@ -1212,16 +1213,23 @@ static void work_fn_tx(struct work_struct *work) * consistent xmit buffer state. */ spin_lock_irq(&port->lock); - buf = s->tx_dma_addr + (xmit->tail & (UART_XMIT_SIZE - 1)); + head = xmit->head; + tail = xmit->tail; + buf = s->tx_dma_addr + (tail & (UART_XMIT_SIZE - 1)); s->tx_dma_len = min_t(unsigned int, - CIRC_CNT(xmit->head, xmit->tail, UART_XMIT_SIZE), - CIRC_CNT_TO_END(xmit->head, xmit->tail, UART_XMIT_SIZE)); - spin_unlock_irq(&port->lock); + CIRC_CNT(head, tail, UART_XMIT_SIZE), + CIRC_CNT_TO_END(head, tail, UART_XMIT_SIZE)); + if (!s->tx_dma_len) { + /* Transmit buffer has been flushed */ + spin_unlock_irq(&port->lock); + return; + }
desc = dmaengine_prep_slave_single(chan, buf, s->tx_dma_len, DMA_MEM_TO_DEV, DMA_PREP_INTERRUPT | DMA_CTRL_ACK); if (!desc) { + spin_unlock_irq(&port->lock); dev_warn(port->dev, "Failed preparing Tx DMA descriptor\n"); /* switch to PIO */ sci_tx_dma_release(s, true); @@ -1231,20 +1239,20 @@ static void work_fn_tx(struct work_struct *work) dma_sync_single_for_device(chan->device->dev, buf, s->tx_dma_len, DMA_TO_DEVICE);
- spin_lock_irq(&port->lock); desc->callback = sci_dma_tx_complete; desc->callback_param = s; - spin_unlock_irq(&port->lock); s->cookie_tx = dmaengine_submit(desc); if (dma_submit_error(s->cookie_tx)) { + spin_unlock_irq(&port->lock); dev_warn(port->dev, "Failed submitting Tx DMA descriptor\n"); /* switch to PIO */ sci_tx_dma_release(s, true); return; }
+ spin_unlock_irq(&port->lock); dev_dbg(port->dev, "%s: %p: %d...%d, cookie %d\n", - __func__, xmit->buf, xmit->tail, xmit->head, s->cookie_tx); + __func__, xmit->buf, tail, head, s->cookie_tx);
dma_async_issue_pending(chan); }
[ Upstream commit 33177f01ca3fe550146bb9001bec2fd806b2f40c ]
gcc asan instrumentation emits the following sequence to store frame pc when the kernel is built with CONFIG_RELOCATABLE: debug/vsprintf.s: .section .data.rel.ro.local,"aw" .align 8 .LC3: .quad .LASANPC4826@GOTOFF .text .align 8 .type number, @function number: .LASANPC4826:
and in case reloc is issued for LASANPC label it also gets into .symtab with the same address as actual function symbol: $ nm -n vmlinux | grep 0000000001397150 0000000001397150 t .LASANPC4826 0000000001397150 t number
In the end kernel backtraces are almost unreadable: [ 143.748476] Call Trace: [ 143.748484] ([<000000002da3e62c>] .LASANPC2671+0x114/0x190) [ 143.748492] [<000000002eca1a58>] .LASANPC2612+0x110/0x160 [ 143.748502] [<000000002de9d830>] print_address_description+0x80/0x3b0 [ 143.748511] [<000000002de9dd64>] __kasan_report+0x15c/0x1c8 [ 143.748521] [<000000002ecb56d4>] strrchr+0x34/0x60 [ 143.748534] [<000003ff800a9a40>] kasan_strings+0xb0/0x148 [test_kasan] [ 143.748547] [<000003ff800a9bba>] kmalloc_tests_init+0xe2/0x528 [test_kasan] [ 143.748555] [<000000002da2117c>] .LASANPC4069+0x354/0x748 [ 143.748563] [<000000002dbfbb16>] do_init_module+0x136/0x3b0 [ 143.748571] [<000000002dbff3f4>] .LASANPC3191+0x2164/0x25d0 [ 143.748580] [<000000002dbffc4c>] .LASANPC3196+0x184/0x1b8 [ 143.748587] [<000000002ecdf2ec>] system_call+0xd8/0x2d8
Since LASANPC labels are not even unique and get into .symtab only due to relocs filter them out in kallsyms.
Signed-off-by: Vasily Gorbik gor@linux.ibm.com Signed-off-by: Masahiro Yamada yamada.masahiro@socionext.com Signed-off-by: Sasha Levin sashal@kernel.org --- scripts/kallsyms.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/scripts/kallsyms.c b/scripts/kallsyms.c index 8fa81e84e295..d117c68d1607 100644 --- a/scripts/kallsyms.c +++ b/scripts/kallsyms.c @@ -158,6 +158,9 @@ static int read_symbol(FILE *in, struct sym_entry *s) /* exclude debugging symbols */ else if (stype == 'N') return -1; + /* exclude s390 kasan local symbols */ + else if (!strncmp(sym, ".LASANPC", 8)) + return -1;
/* include the type field in the symbol name, so that it gets * compressed together */
[ Upstream commit 4e4cf62b37da5ff45c904a3acf242ab29ed5881d ]
Running the 'perf test' command after building perf with a memory sanitizer causes a warning that says:
WARNING: MemorySanitizer: use-of-uninitialized-value... in mmap-thread-lookup.c
Initializing the go variable to 0 silences this harmless warning.
Committer warning:
This was harmless, just a simple test writing whatever was at that sizeof(int) memory area just to signal another thread blocked reading that file created with pipe(). Initialize it tho so that we don't get this warning.
Signed-off-by: Numfor Mbiziwo-Tiapo nums@google.com Cc: Alexander Shishkin alexander.shishkin@linux.intel.com Cc: Ian Rogers irogers@google.com Cc: Jiri Olsa jolsa@redhat.com Cc: Mark Drayton mbd@fb.com Cc: Namhyung Kim namhyung@kernel.org Cc: Peter Zijlstra peterz@infradead.org Cc: Song Liu songliubraving@fb.com Cc: Stephane Eranian eranian@google.com Link: http://lkml.kernel.org/r/20190702173716.181223-1-nums@google.com Signed-off-by: Arnaldo Carvalho de Melo acme@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- tools/perf/tests/mmap-thread-lookup.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tools/perf/tests/mmap-thread-lookup.c b/tools/perf/tests/mmap-thread-lookup.c index 145050e2e544..195ba31e2f35 100644 --- a/tools/perf/tests/mmap-thread-lookup.c +++ b/tools/perf/tests/mmap-thread-lookup.c @@ -49,7 +49,7 @@ static void *thread_fn(void *arg) { struct thread_data *td = arg; ssize_t ret; - int go; + int go = 0;
if (thread_init(td)) return NULL;
[ Upstream commit 56f3ce675103e3fb9e631cfb4131fc768bc23e9a ]
blkoff_off might over 512 due to fs corrupt or security vulnerability. That should be checked before being using.
Use ENTRIES_IN_SUM to protect invalid value in cur_data_blkoff.
Signed-off-by: Ocean Chen oceanchen@google.com Reviewed-by: Chao Yu yuchao0@huawei.com Signed-off-by: Jaegeuk Kim jaegeuk@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- fs/f2fs/segment.c | 5 +++++ 1 file changed, 5 insertions(+)
diff --git a/fs/f2fs/segment.c b/fs/f2fs/segment.c index 6802cd754eda..014bee5c0e75 100644 --- a/fs/f2fs/segment.c +++ b/fs/f2fs/segment.c @@ -1510,6 +1510,11 @@ static int read_compacted_summaries(struct f2fs_sb_info *sbi) seg_i = CURSEG_I(sbi, i); segno = le32_to_cpu(ckpt->cur_data_segno[i]); blk_off = le16_to_cpu(ckpt->cur_data_blkoff[i]); + if (blk_off > ENTRIES_IN_SUM) { + f2fs_bug_on(sbi, 1); + f2fs_put_page(page, 1); + return -EFAULT; + } seg_i->next_segno = segno; reset_curseg(sbi, i, 0); seg_i->alloc_type = ckpt->alloc_type[i];
[ Upstream commit 25777e5784a7b417967460d4fcf9660d05a0c320 ]
Previously, if mbox_request_channel_byname was used with a name which did not exist in the "mbox-names" property of a mailbox client, the mailbox corresponding to the last entry in the "mbox-names" list would be incorrectly selected. With this patch, -EINVAL is returned if the named mailbox is not found.
Signed-off-by: Morten Borup Petersen morten_bp@live.dk Signed-off-by: Jassi Brar jaswinder.singh@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/mailbox/mailbox.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/drivers/mailbox/mailbox.c b/drivers/mailbox/mailbox.c index 9cf826df89b1..b4ad85251cf7 100644 --- a/drivers/mailbox/mailbox.c +++ b/drivers/mailbox/mailbox.c @@ -389,11 +389,13 @@ struct mbox_chan *mbox_request_channel_byname(struct mbox_client *cl,
of_property_for_each_string(np, "mbox-names", prop, mbox_name) { if (!strncmp(name, mbox_name, strlen(name))) - break; + return mbox_request_channel(cl, index); index++; }
- return mbox_request_channel(cl, index); + dev_err(cl->dev, "%s() could not locate channel named "%s"\n", + __func__, name); + return ERR_PTR(-EINVAL); } EXPORT_SYMBOL_GPL(mbox_request_channel_byname);
[ Upstream commit 33439620680be5225c1b8806579a291e0d761ca0 ]
In commit 4a7b06c157a2 ("powerpc/eeh: Handle hugepages in ioremap space") support for using hugepages in the vmalloc and ioremap areas was enabled for radix. Unfortunately this broke EEH MMIO error checking.
Detection works by inserting a hook which checks the results of the ioreadXX() set of functions. When a read returns a 0xFFs response we need to check for an error which we do by mapping the (virtual) MMIO address back to a physical address, then mapping physical address to a PCI device via an interval tree.
When translating virt -> phys we currently assume the ioremap space is only populated by PAGE_SIZE mappings. If a hugepage mapping is found we emit a WARN_ON(), but otherwise handles the check as though a normal page was found. In pathalogical cases such as copying a buffer containing a lot of 0xFFs from BAR memory this can result in the system not booting because it's too busy printing WARN_ON()s.
There's no real reason to assume huge pages can't be present and we're prefectly capable of handling them, so do that.
Fixes: 4a7b06c157a2 ("powerpc/eeh: Handle hugepages in ioremap space") Reported-by: Sachin Sant sachinp@linux.vnet.ibm.com Signed-off-by: Oliver O'Halloran oohall@gmail.com Tested-by: Sachin Sant sachinp@linux.vnet.ibm.com Signed-off-by: Michael Ellerman mpe@ellerman.id.au Link: https://lore.kernel.org/r/20190710150517.27114-1-oohall@gmail.com Signed-off-by: Sasha Levin sashal@kernel.org --- arch/powerpc/kernel/eeh.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-)
diff --git a/arch/powerpc/kernel/eeh.c b/arch/powerpc/kernel/eeh.c index 6696c1986844..16193d7b0635 100644 --- a/arch/powerpc/kernel/eeh.c +++ b/arch/powerpc/kernel/eeh.c @@ -363,10 +363,19 @@ static inline unsigned long eeh_token_to_phys(unsigned long token) NULL, &hugepage_shift); if (!ptep) return token; - WARN_ON(hugepage_shift); - pa = pte_pfn(*ptep) << PAGE_SHIFT;
- return pa | (token & (PAGE_SIZE-1)); + pa = pte_pfn(*ptep); + + /* On radix we can do hugepage mappings for io, so handle that */ + if (hugepage_shift) { + pa <<= hugepage_shift; + pa |= token & ((1ul << hugepage_shift) - 1); + } else { + pa <<= PAGE_SHIFT; + pa |= token & (PAGE_SIZE - 1); + } + + return pa; }
/*
[ Upstream commit 733f0025f0fb43e382b84db0930ae502099b7e62 ]
When building drm/exynos for sh, as part of an allmodconfig build, the following warning triggered:
exynos7_drm_decon.c: In function `decon_remove': exynos7_drm_decon.c:769:24: warning: unused variable `ctx' struct decon_context *ctx = dev_get_drvdata(&pdev->dev);
The ctx variable is only used as argument to iounmap().
In sh - allmodconfig CONFIG_MMU is not defined so it ended up in:
#define __iounmap(addr) do { } while (0) #define iounmap __iounmap
Fix the warning by introducing a static inline function for iounmap.
This is similar to several other architectures.
Link: http://lkml.kernel.org/r/20190622114208.24427-1-sam@ravnborg.org Signed-off-by: Sam Ravnborg sam@ravnborg.org Reviewed-by: Geert Uytterhoeven geert+renesas@glider.be Cc: Yoshinori Sato ysato@users.sourceforge.jp Cc: Rich Felker dalias@libc.org Cc: Will Deacon will.deacon@arm.com Cc: Mark Brown broonie@kernel.org Cc: Inki Dae inki.dae@samsung.com Cc: Krzysztof Kozlowski krzk@kernel.org Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- arch/sh/include/asm/io.h | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/arch/sh/include/asm/io.h b/arch/sh/include/asm/io.h index 3280a6bfa503..b2592c3864ad 100644 --- a/arch/sh/include/asm/io.h +++ b/arch/sh/include/asm/io.h @@ -370,7 +370,11 @@ static inline int iounmap_fixed(void __iomem *addr) { return -EINVAL; }
#define ioremap_nocache ioremap #define ioremap_uc ioremap -#define iounmap __iounmap + +static inline void iounmap(void __iomem *addr) +{ + __iounmap(addr); +}
/* * Convert a physical pointer to a virtual kernel pointer for /dev/mem
[ Upstream commit 6ef9056952532c3b746de46aa10d45b4d7797bd8 ]
in_softirq() is a wrong predicate to check if we are in a softirq context. It also returns true if we have BH disabled, so objects are falsely stamped with "softirq" comm. The correct predicate is in_serving_softirq().
If user does cat from /sys/kernel/debug/kmemleak previously they would see this, which is clearly wrong, this is system call context (see the comm):
unreferenced object 0xffff88805bd661c0 (size 64): comm "softirq", pid 0, jiffies 4294942959 (age 12.400s) hex dump (first 32 bytes): 00 00 00 00 00 00 00 00 ff ff ff ff 00 00 00 00 ................ 00 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 ................ backtrace: [<0000000007dcb30c>] kmemleak_alloc_recursive include/linux/kmemleak.h:55 [inline] [<0000000007dcb30c>] slab_post_alloc_hook mm/slab.h:439 [inline] [<0000000007dcb30c>] slab_alloc mm/slab.c:3326 [inline] [<0000000007dcb30c>] kmem_cache_alloc_trace+0x13d/0x280 mm/slab.c:3553 [<00000000969722b7>] kmalloc include/linux/slab.h:547 [inline] [<00000000969722b7>] kzalloc include/linux/slab.h:742 [inline] [<00000000969722b7>] ip_mc_add1_src net/ipv4/igmp.c:1961 [inline] [<00000000969722b7>] ip_mc_add_src+0x36b/0x400 net/ipv4/igmp.c:2085 [<00000000a4134b5f>] ip_mc_msfilter+0x22d/0x310 net/ipv4/igmp.c:2475 [<00000000d20248ad>] do_ip_setsockopt.isra.0+0x19fe/0x1c00 net/ipv4/ip_sockglue.c:957 [<000000003d367be7>] ip_setsockopt+0x3b/0xb0 net/ipv4/ip_sockglue.c:1246 [<000000003c7c76af>] udp_setsockopt+0x4e/0x90 net/ipv4/udp.c:2616 [<000000000c1aeb23>] sock_common_setsockopt+0x3e/0x50 net/core/sock.c:3130 [<000000000157b92b>] __sys_setsockopt+0x9e/0x120 net/socket.c:2078 [<00000000a9f3d058>] __do_sys_setsockopt net/socket.c:2089 [inline] [<00000000a9f3d058>] __se_sys_setsockopt net/socket.c:2086 [inline] [<00000000a9f3d058>] __x64_sys_setsockopt+0x26/0x30 net/socket.c:2086 [<000000001b8da885>] do_syscall_64+0x7c/0x1a0 arch/x86/entry/common.c:301 [<00000000ba770c62>] entry_SYSCALL_64_after_hwframe+0x44/0xa9
now they will see this:
unreferenced object 0xffff88805413c800 (size 64): comm "syz-executor.4", pid 8960, jiffies 4294994003 (age 14.350s) hex dump (first 32 bytes): 00 7a 8a 57 80 88 ff ff e0 00 00 01 00 00 00 00 .z.W............ 00 00 00 00 00 00 00 00 01 00 00 00 00 00 00 00 ................ backtrace: [<00000000c5d3be64>] kmemleak_alloc_recursive include/linux/kmemleak.h:55 [inline] [<00000000c5d3be64>] slab_post_alloc_hook mm/slab.h:439 [inline] [<00000000c5d3be64>] slab_alloc mm/slab.c:3326 [inline] [<00000000c5d3be64>] kmem_cache_alloc_trace+0x13d/0x280 mm/slab.c:3553 [<0000000023865be2>] kmalloc include/linux/slab.h:547 [inline] [<0000000023865be2>] kzalloc include/linux/slab.h:742 [inline] [<0000000023865be2>] ip_mc_add1_src net/ipv4/igmp.c:1961 [inline] [<0000000023865be2>] ip_mc_add_src+0x36b/0x400 net/ipv4/igmp.c:2085 [<000000003029a9d4>] ip_mc_msfilter+0x22d/0x310 net/ipv4/igmp.c:2475 [<00000000ccd0a87c>] do_ip_setsockopt.isra.0+0x19fe/0x1c00 net/ipv4/ip_sockglue.c:957 [<00000000a85a3785>] ip_setsockopt+0x3b/0xb0 net/ipv4/ip_sockglue.c:1246 [<00000000ec13c18d>] udp_setsockopt+0x4e/0x90 net/ipv4/udp.c:2616 [<0000000052d748e3>] sock_common_setsockopt+0x3e/0x50 net/core/sock.c:3130 [<00000000512f1014>] __sys_setsockopt+0x9e/0x120 net/socket.c:2078 [<00000000181758bc>] __do_sys_setsockopt net/socket.c:2089 [inline] [<00000000181758bc>] __se_sys_setsockopt net/socket.c:2086 [inline] [<00000000181758bc>] __x64_sys_setsockopt+0x26/0x30 net/socket.c:2086 [<00000000d4b73623>] do_syscall_64+0x7c/0x1a0 arch/x86/entry/common.c:301 [<00000000c1098bec>] entry_SYSCALL_64_after_hwframe+0x44/0xa9
Link: http://lkml.kernel.org/r/20190517171507.96046-1-dvyukov@gmail.com Signed-off-by: Dmitry Vyukov dvyukov@google.com Acked-by: Catalin Marinas catalin.marinas@arm.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- mm/kmemleak.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/mm/kmemleak.c b/mm/kmemleak.c index 84c93879aa5d..4d675318754e 100644 --- a/mm/kmemleak.c +++ b/mm/kmemleak.c @@ -566,7 +566,7 @@ static struct kmemleak_object *create_object(unsigned long ptr, size_t size, if (in_irq()) { object->pid = 0; strncpy(object->comm, "hardirq", sizeof(object->comm)); - } else if (in_softirq()) { + } else if (in_serving_softirq()) { object->pid = 0; strncpy(object->comm, "softirq", sizeof(object->comm)); } else {
[ Upstream commit f053cbd4366051d7eb6ba1b8d529d20f719c2963 ]
Fix the callback 9p passes to read_cache_page to actually have the proper type expected. Casting around function pointers can easily hide typing bugs, and defeats control flow protection.
Link: http://lkml.kernel.org/r/20190520055731.24538-5-hch@lst.de Signed-off-by: Christoph Hellwig hch@lst.de Reviewed-by: Kees Cook keescook@chromium.org Cc: Sami Tolvanen samitolvanen@google.com Cc: Nick Desaulniers ndesaulniers@google.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- fs/9p/vfs_addr.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/fs/9p/vfs_addr.c b/fs/9p/vfs_addr.c index e9e04376c52c..e80ad0c7c2a9 100644 --- a/fs/9p/vfs_addr.c +++ b/fs/9p/vfs_addr.c @@ -49,8 +49,9 @@ * @page: structure to page * */ -static int v9fs_fid_readpage(struct p9_fid *fid, struct page *page) +static int v9fs_fid_readpage(void *data, struct page *page) { + struct p9_fid *fid = data; struct inode *inode = page->mapping->host; struct bio_vec bvec = {.bv_page = page, .bv_len = PAGE_SIZE}; struct iov_iter to; @@ -121,7 +122,8 @@ static int v9fs_vfs_readpages(struct file *filp, struct address_space *mapping, if (ret == 0) return ret;
- ret = read_cache_pages(mapping, pages, (void *)v9fs_vfs_readpage, filp); + ret = read_cache_pages(mapping, pages, v9fs_fid_readpage, + filp->private_data); p9_debug(P9_DEBUG_VFS, " = %d\n", ret); return ret; }
[ Upstream commit 543bdb2d825fe2400d6e951f1786d92139a16931 ]
Make mmu_notifier_register() safer by issuing a memory barrier before registering a new notifier. This fixes a theoretical bug on weakly ordered CPUs. For example, take this simplified use of notifiers by a driver:
my_struct->mn.ops = &my_ops; /* (1) */ mmu_notifier_register(&my_struct->mn, mm) ... hlist_add_head(&mn->hlist, &mm->mmu_notifiers); /* (2) */ ...
Once mmu_notifier_register() releases the mm locks, another thread can invalidate a range:
mmu_notifier_invalidate_range() ... hlist_for_each_entry_rcu(mn, &mm->mmu_notifiers, hlist) { if (mn->ops->invalidate_range)
The read side relies on the data dependency between mn and ops to ensure that the pointer is properly initialized. But the write side doesn't have any dependency between (1) and (2), so they could be reordered and the readers could dereference an invalid mn->ops. mmu_notifier_register() does take all the mm locks before adding to the hlist, but those have acquire semantics which isn't sufficient.
By calling hlist_add_head_rcu() instead of hlist_add_head() we update the hlist using a store-release, ensuring that readers see prior initialization of my_struct. This situation is better illustated by litmus test MP+onceassign+derefonce.
Link: http://lkml.kernel.org/r/20190502133532.24981-1-jean-philippe.brucker@arm.co... Fixes: cddb8a5c14aa ("mmu-notifiers: core") Signed-off-by: Jean-Philippe Brucker jean-philippe.brucker@arm.com Cc: Jérôme Glisse jglisse@redhat.com Cc: Michal Hocko mhocko@suse.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- mm/mmu_notifier.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/mm/mmu_notifier.c b/mm/mmu_notifier.c index 5fbdd367bbed..ad90b8f85223 100644 --- a/mm/mmu_notifier.c +++ b/mm/mmu_notifier.c @@ -286,7 +286,7 @@ static int do_mmu_notifier_register(struct mmu_notifier *mn, * thanks to mm_take_all_locks(). */ spin_lock(&mm->mmu_notifier_mm->lock); - hlist_add_head(&mn->hlist, &mm->mmu_notifier_mm->list); + hlist_add_head_rcu(&mn->hlist, &mm->mmu_notifier_mm->list); spin_unlock(&mm->mmu_notifier_mm->lock);
mm_drop_all_locks(mm);
[ Upstream commit 68d41d8c94a31dfb8233ab90b9baf41a2ed2da68 ]
The stats variable nr_unused_locks is incremented every time a new lock class is register and decremented when the lock is first used in __lock_acquire(). And after all, it is shown and checked in lockdep_stats.
However, under configurations that either CONFIG_TRACE_IRQFLAGS or CONFIG_PROVE_LOCKING is not defined:
The commit:
091806515124b20 ("locking/lockdep: Consolidate lock usage bit initialization")
missed marking the LOCK_USED flag at IRQ usage initialization because as mark_usage() is not called. And the commit:
886532aee3cd42d ("locking/lockdep: Move mark_lock() inside CONFIG_TRACE_IRQFLAGS && CONFIG_PROVE_LOCKING")
further made mark_lock() not defined such that the LOCK_USED cannot be marked at all when the lock is first acquired.
As a result, we fix this by not showing and checking the stats under such configurations for lockdep_stats.
Reported-by: Qian Cai cai@lca.pw Signed-off-by: Yuyang Du duyuyang@gmail.com Signed-off-by: Peter Zijlstra (Intel) peterz@infradead.org Cc: Andrew Morton akpm@linux-foundation.org Cc: Linus Torvalds torvalds@linux-foundation.org Cc: Paul E. McKenney paulmck@linux.vnet.ibm.com Cc: Peter Zijlstra peterz@infradead.org Cc: Thomas Gleixner tglx@linutronix.de Cc: Will Deacon will.deacon@arm.com Cc: arnd@arndb.de Cc: frederic@kernel.org Link: https://lkml.kernel.org/r/20190709101522.9117-1-duyuyang@gmail.com Signed-off-by: Ingo Molnar mingo@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/locking/lockdep_proc.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/kernel/locking/lockdep_proc.c b/kernel/locking/lockdep_proc.c index dbb61a302548..9778b6701019 100644 --- a/kernel/locking/lockdep_proc.c +++ b/kernel/locking/lockdep_proc.c @@ -227,6 +227,7 @@ static int lockdep_stats_show(struct seq_file *m, void *v) nr_hardirq_read_safe = 0, nr_hardirq_read_unsafe = 0, sum_forward_deps = 0;
+#ifdef CONFIG_PROVE_LOCKING list_for_each_entry(class, &all_lock_classes, lock_entry) {
if (class->usage_mask == 0) @@ -258,12 +259,12 @@ static int lockdep_stats_show(struct seq_file *m, void *v) if (class->usage_mask & LOCKF_ENABLED_HARDIRQ_READ) nr_hardirq_read_unsafe++;
-#ifdef CONFIG_PROVE_LOCKING sum_forward_deps += lockdep_count_forward_deps(class); -#endif } #ifdef CONFIG_DEBUG_LOCKDEP DEBUG_LOCKS_WARN_ON(debug_atomic_read(nr_unused_locks) != nr_unused); +#endif + #endif seq_printf(m, " lock-classes: %11lu [max: %lu]\n", nr_lock_classes, MAX_LOCKDEP_KEYS);
[ Upstream commit 68037aa78208f34bda4e5cd76c357f718b838cbb ]
The usage is now hidden in an #ifdef, so we need to move the variable itself in there as well to avoid this warning:
kernel/locking/lockdep_proc.c:203:21: error: unused variable 'class' [-Werror,-Wunused-variable]
Signed-off-by: Arnd Bergmann arnd@arndb.de Signed-off-by: Peter Zijlstra (Intel) peterz@infradead.org Cc: Andrew Morton akpm@linux-foundation.org Cc: Bart Van Assche bvanassche@acm.org Cc: Linus Torvalds torvalds@linux-foundation.org Cc: Paul E. McKenney paulmck@linux.vnet.ibm.com Cc: Peter Zijlstra peterz@infradead.org Cc: Qian Cai cai@lca.pw Cc: Thomas Gleixner tglx@linutronix.de Cc: Waiman Long longman@redhat.com Cc: Will Deacon will.deacon@arm.com Cc: Will Deacon will@kernel.org Cc: Yuyang Du duyuyang@gmail.com Cc: frederic@kernel.org Fixes: 68d41d8c94a3 ("locking/lockdep: Fix lock used or unused stats error") Link: https://lkml.kernel.org/r/20190715092809.736834-1-arnd@arndb.de Signed-off-by: Ingo Molnar mingo@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/locking/lockdep_proc.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/kernel/locking/lockdep_proc.c b/kernel/locking/lockdep_proc.c index 9778b6701019..35b34eccdd10 100644 --- a/kernel/locking/lockdep_proc.c +++ b/kernel/locking/lockdep_proc.c @@ -217,7 +217,6 @@ static void lockdep_stats_debug_show(struct seq_file *m)
static int lockdep_stats_show(struct seq_file *m, void *v) { - struct lock_class *class; unsigned long nr_unused = 0, nr_uncategorized = 0, nr_irq_safe = 0, nr_irq_unsafe = 0, nr_softirq_safe = 0, nr_softirq_unsafe = 0, @@ -228,6 +227,8 @@ static int lockdep_stats_show(struct seq_file *m, void *v) sum_forward_deps = 0;
#ifdef CONFIG_PROVE_LOCKING + struct lock_class *class; + list_for_each_entry(class, &all_lock_classes, lock_entry) {
if (class->usage_mask == 0)
From: Phong Tran tranmanphong@gmail.com
commit f90bf1ece48a736097ea224430578fe586a9544c upstream.
syzboot reported that https://syzkaller.appspot.com/bug?extid=fd2bd7df88c606eea4ef
There is not consitency parameter in cluste_id_get/put calling. In case of getting the id with result is failure, the wusbhc->cluster_id will not be updated and this can not be used for wusb_cluster_id_put().
Tested report https://groups.google.com/d/msg/syzkaller-bugs/0znZopp3-9k/oxOrhLkLEgAJ
Reproduce and gdb got the details:
139 addr = wusb_cluster_id_get(); (gdb) n 140 if (addr == 0) (gdb) print addr $1 = 254 '\376' (gdb) n 142 result = __hwahc_set_cluster_id(hwahc, addr); (gdb) print result $2 = -71 (gdb) break wusb_cluster_id_put Breakpoint 3 at 0xffffffff836e3f20: file drivers/usb/wusbcore/wusbhc.c, line 384. (gdb) s Thread 2 hit Breakpoint 3, wusb_cluster_id_put (id=0 '\000') at drivers/usb/wusbcore/wusbhc.c:384 384 id = 0xff - id; (gdb) n 385 BUG_ON(id >= CLUSTER_IDS); (gdb) print id $3 = 255 '\377'
Reported-by: syzbot+fd2bd7df88c606eea4ef@syzkaller.appspotmail.com Signed-off-by: Phong Tran tranmanphong@gmail.com Cc: stable stable@vger.kernel.org Link: https://lore.kernel.org/r/20190724020601.15257-1-tranmanphong@gmail.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/usb/host/hwa-hc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/drivers/usb/host/hwa-hc.c +++ b/drivers/usb/host/hwa-hc.c @@ -173,7 +173,7 @@ out: return result;
error_set_cluster_id: - wusb_cluster_id_put(wusbhc->cluster_id); + wusb_cluster_id_put(addr); error_cluster_id_get: goto out;
From: Ryan Kennedy ryan5544@gmail.com
commit f3dccdaade4118070a3a47bef6b18321431f9ac6 upstream.
The AMD PLL USB quirk is incorrectly enabled on newer Ryzen chipsets. The logic in usb_amd_find_chipset_info currently checks for unaffected chipsets rather than affected ones. This broke once a new chipset was added in e788787ef. It makes more sense to reverse the logic so it won't need to be updated as new chipsets are added. Note that the core of the workaround in usb_amd_quirk_pll does correctly check the chipset.
Signed-off-by: Ryan Kennedy ryan5544@gmail.com Fixes: e788787ef4f9 ("usb:xhci:Add quirk for Certain failing HP keyboard on reset after resume") Cc: stable stable@vger.kernel.org Acked-by: Alan Stern stern@rowland.harvard.edu Link: https://lore.kernel.org/r/20190704153529.9429-2-ryan5544@gmail.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/usb/host/pci-quirks.c | 31 +++++++++++++++++++------------ 1 file changed, 19 insertions(+), 12 deletions(-)
--- a/drivers/usb/host/pci-quirks.c +++ b/drivers/usb/host/pci-quirks.c @@ -178,7 +178,7 @@ int usb_amd_find_chipset_info(void) { unsigned long flags; struct amd_chipset_info info; - int ret; + int need_pll_quirk = 0;
spin_lock_irqsave(&amd_lock, flags);
@@ -192,21 +192,28 @@ int usb_amd_find_chipset_info(void) spin_unlock_irqrestore(&amd_lock, flags);
if (!amd_chipset_sb_type_init(&info)) { - ret = 0; goto commit; }
- /* Below chipset generations needn't enable AMD PLL quirk */ - if (info.sb_type.gen == AMD_CHIPSET_UNKNOWN || - info.sb_type.gen == AMD_CHIPSET_SB600 || - info.sb_type.gen == AMD_CHIPSET_YANGTZE || - (info.sb_type.gen == AMD_CHIPSET_SB700 && - info.sb_type.rev > 0x3b)) { + switch (info.sb_type.gen) { + case AMD_CHIPSET_SB700: + need_pll_quirk = info.sb_type.rev <= 0x3B; + break; + case AMD_CHIPSET_SB800: + case AMD_CHIPSET_HUDSON2: + case AMD_CHIPSET_BOLTON: + need_pll_quirk = 1; + break; + default: + need_pll_quirk = 0; + break; + } + + if (!need_pll_quirk) { if (info.smbus_dev) { pci_dev_put(info.smbus_dev); info.smbus_dev = NULL; } - ret = 0; goto commit; }
@@ -225,7 +232,7 @@ int usb_amd_find_chipset_info(void) } }
- ret = info.probe_result = 1; + need_pll_quirk = info.probe_result = 1; printk(KERN_DEBUG "QUIRK: Enable AMD PLL fix\n");
commit: @@ -236,7 +243,7 @@ commit:
/* Mark that we where here */ amd_chipset.probe_count++; - ret = amd_chipset.probe_result; + need_pll_quirk = amd_chipset.probe_result;
spin_unlock_irqrestore(&amd_lock, flags);
@@ -250,7 +257,7 @@ commit: spin_unlock_irqrestore(&amd_lock, flags); }
- return ret; + return need_pll_quirk; } EXPORT_SYMBOL_GPL(usb_amd_find_chipset_info);
From: Hans de Goede hdegoede@redhat.com
commit d02f1aa39189e0619c3525d5cd03254e61bf606a upstream.
Some Lenovo 2-in-1s with a detachable keyboard have a portrait screen but advertise a landscape resolution and pitch, resulting in a messed up display if the kernel tries to show anything on the efifb (because of the wrong pitch).
Fix this by adding a new DMI match table for devices which need to have their width and height swapped.
At first it was tried to use the existing table for overriding some of the efifb parameters, but some of the affected devices have variants with different LCD resolutions which will not work with hardcoded override values.
Reference: https://bugzilla.redhat.com/show_bug.cgi?id=1730783 Signed-off-by: Hans de Goede hdegoede@redhat.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Cc: stable@vger.kernel.org Link: https://lkml.kernel.org/r/20190721152418.11644-1-hdegoede@redhat.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/x86/kernel/sysfb_efi.c | 46 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 46 insertions(+)
--- a/arch/x86/kernel/sysfb_efi.c +++ b/arch/x86/kernel/sysfb_efi.c @@ -216,9 +216,55 @@ static const struct dmi_system_id efifb_ {}, };
+/* + * Some devices have a portrait LCD but advertise a landscape resolution (and + * pitch). We simply swap width and height for these devices so that we can + * correctly deal with some of them coming with multiple resolutions. + */ +static const struct dmi_system_id efifb_dmi_swap_width_height[] __initconst = { + { + /* + * Lenovo MIIX310-10ICR, only some batches have the troublesome + * 800x1280 portrait screen. Luckily the portrait version has + * its own BIOS version, so we match on that. + */ + .matches = { + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "LENOVO"), + DMI_EXACT_MATCH(DMI_PRODUCT_VERSION, "MIIX 310-10ICR"), + DMI_EXACT_MATCH(DMI_BIOS_VERSION, "1HCN44WW"), + }, + }, + { + /* Lenovo MIIX 320-10ICR with 800x1280 portrait screen */ + .matches = { + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "LENOVO"), + DMI_EXACT_MATCH(DMI_PRODUCT_VERSION, + "Lenovo MIIX 320-10ICR"), + }, + }, + { + /* Lenovo D330 with 800x1280 or 1200x1920 portrait screen */ + .matches = { + DMI_EXACT_MATCH(DMI_SYS_VENDOR, "LENOVO"), + DMI_EXACT_MATCH(DMI_PRODUCT_VERSION, + "Lenovo ideapad D330-10IGM"), + }, + }, + {}, +}; + __init void sysfb_apply_efi_quirks(void) { if (screen_info.orig_video_isVGA != VIDEO_TYPE_EFI || !(screen_info.capabilities & VIDEO_CAPABILITY_SKIP_QUIRKS)) dmi_check_system(efifb_dmi_system_table); + + if (screen_info.orig_video_isVGA == VIDEO_TYPE_EFI && + dmi_check_system(efifb_dmi_swap_width_height)) { + u16 temp = screen_info.lfb_width; + + screen_info.lfb_width = screen_info.lfb_height; + screen_info.lfb_height = temp; + screen_info.lfb_linelength = 4 * screen_info.lfb_width; + } }
From: Zhenzhong Duan zhenzhong.duan@oracle.com
commit 517c3ba00916383af6411aec99442c307c23f684 upstream.
X86_HYPER_NATIVE isn't accurate for checking if running on native platform, e.g. CONFIG_HYPERVISOR_GUEST isn't set or "nopv" is enabled.
Checking the CPU feature bit X86_FEATURE_HYPERVISOR to determine if it's running on native platform is more accurate.
This still doesn't cover the platforms on which X86_FEATURE_HYPERVISOR is unsupported, e.g. VMware, but there is nothing which can be done about this scenario.
Fixes: 8a4b06d391b0 ("x86/speculation/mds: Add sysfs reporting for MDS") Signed-off-by: Zhenzhong Duan zhenzhong.duan@oracle.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Cc: stable@vger.kernel.org Link: https://lkml.kernel.org/r/1564022349-17338-1-git-send-email-zhenzhong.duan@o... Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/x86/kernel/cpu/bugs.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -1094,7 +1094,7 @@ static void __init l1tf_select_mitigatio static ssize_t mds_show_state(char *buf) { #ifdef CONFIG_HYPERVISOR_GUEST - if (x86_hyper) { + if (boot_cpu_has(X86_FEATURE_HYPERVISOR)) { return sprintf(buf, "%s; SMT Host state unknown\n", mds_strings[mds_mitigation]); }
From: Kefeng Wang wangkefeng.wang@huawei.com
commit 0c7d37f4d9b8446956e97b7c5e61173cdb7c8522 upstream.
The base value in do_div() called by hpet_time_div() is truncated from unsigned long to uint32_t, resulting in a divide-by-zero exception.
UBSAN: Undefined behaviour in ../drivers/char/hpet.c:572:2 division by zero CPU: 1 PID: 23682 Comm: syz-executor.3 Not tainted 4.4.184.x86_64+ #4 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS Ubuntu-1.8.2-1ubuntu1 04/01/2014 0000000000000000 b573382df1853d00 ffff8800a3287b98 ffffffff81ad7561 ffff8800a3287c00 ffffffff838b35b0 ffffffff838b3860 ffff8800a3287c20 0000000000000000 ffff8800a3287bb0 ffffffff81b8f25e ffffffff838b35a0 Call Trace: [<ffffffff81ad7561>] __dump_stack lib/dump_stack.c:15 [inline] [<ffffffff81ad7561>] dump_stack+0xc1/0x120 lib/dump_stack.c:51 [<ffffffff81b8f25e>] ubsan_epilogue+0x12/0x8d lib/ubsan.c:166 [<ffffffff81b900cb>] __ubsan_handle_divrem_overflow+0x282/0x2c8 lib/ubsan.c:262 [<ffffffff823560dd>] hpet_time_div drivers/char/hpet.c:572 [inline] [<ffffffff823560dd>] hpet_ioctl_common drivers/char/hpet.c:663 [inline] [<ffffffff823560dd>] hpet_ioctl_common.cold+0xa8/0xad drivers/char/hpet.c:577 [<ffffffff81e63d56>] hpet_ioctl+0xc6/0x180 drivers/char/hpet.c:676 [<ffffffff81711590>] vfs_ioctl fs/ioctl.c:43 [inline] [<ffffffff81711590>] file_ioctl fs/ioctl.c:470 [inline] [<ffffffff81711590>] do_vfs_ioctl+0x6e0/0xf70 fs/ioctl.c:605 [<ffffffff81711eb4>] SYSC_ioctl fs/ioctl.c:622 [inline] [<ffffffff81711eb4>] SyS_ioctl+0x94/0xc0 fs/ioctl.c:613 [<ffffffff82846003>] tracesys_phase2+0x90/0x95
The main C reproducer autogenerated by syzkaller,
syscall(__NR_mmap, 0x20000000, 0x1000000, 3, 0x32, -1, 0); memcpy((void*)0x20000100, "/dev/hpet\000", 10); syscall(__NR_openat, 0xffffffffffffff9c, 0x20000100, 0, 0); syscall(__NR_ioctl, r[0], 0x40086806, 0x40000000000000);
Fix it by using div64_ul().
Signed-off-by: Kefeng Wang wangkefeng.wang@huawei.com Signed-off-by: Zhang HongJun zhanghongjun2@huawei.com Cc: stable stable@vger.kernel.org Reviewed-by: Arnd Bergmann arnd@arndb.de Link: https://lore.kernel.org/r/20190711132757.130092-1-wangkefeng.wang@huawei.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/char/hpet.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
--- a/drivers/char/hpet.c +++ b/drivers/char/hpet.c @@ -569,8 +569,7 @@ static inline unsigned long hpet_time_di unsigned long long m;
m = hpets->hp_tick_freq + (dis >> 1); - do_div(m, dis); - return (unsigned long)m; + return div64_ul(m, dis); }
static int
From: Kai-Heng Feng kai.heng.feng@canonical.com
commit 70256b42caaf3e13c2932c2be7903a73fbe8bb8b upstream.
Commit 7b9584fa1c0b ("staging: line6: Move altsetting to properties") set a wrong altsetting for LINE6_PODHD500_1 during refactoring.
Set the correct altsetting number to fix the issue.
BugLink: https://bugs.launchpad.net/bugs/1790595 Fixes: 7b9584fa1c0b ("staging: line6: Move altsetting to properties") Signed-off-by: Kai-Heng Feng kai.heng.feng@canonical.com Cc: stable@vger.kernel.org Signed-off-by: Takashi Iwai tiwai@suse.de Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- sound/usb/line6/podhd.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/sound/usb/line6/podhd.c +++ b/sound/usb/line6/podhd.c @@ -155,7 +155,7 @@ static const struct line6_properties pod .capabilities = LINE6_CAP_CONTROL | LINE6_CAP_PCM | LINE6_CAP_HWMON, - .altsetting = 1, + .altsetting = 0, .ep_ctrl_r = 0x81, .ep_ctrl_w = 0x01, .ep_audio_r = 0x86,
From: Hui Wang hui.wang@canonical.com
commit 3f8809499bf02ef7874254c5e23fc764a47a21a0 upstream.
This conexant codec isn't in the supported codec list yet, the hda generic driver can drive this codec well, but on a Lenovo machine with mute/mic-mute leds, we need to apply CXT_FIXUP_THINKPAD_ACPI to make the leds work. After adding this codec to the list, the driver patch_conexant.c will apply THINKPAD_ACPI to this machine.
Cc: stable@vger.kernel.org Signed-off-by: Hui Wang hui.wang@canonical.com Signed-off-by: Takashi Iwai tiwai@suse.de Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- sound/pci/hda/patch_conexant.c | 1 + 1 file changed, 1 insertion(+)
--- a/sound/pci/hda/patch_conexant.c +++ b/sound/pci/hda/patch_conexant.c @@ -1008,6 +1008,7 @@ static int patch_conexant_auto(struct hd */
static const struct hda_device_id snd_hda_id_conexant[] = { + HDA_CODEC_ENTRY(0x14f11f86, "CX8070", patch_conexant_auto), HDA_CODEC_ENTRY(0x14f12008, "CX8200", patch_conexant_auto), HDA_CODEC_ENTRY(0x14f15045, "CX20549 (Venice)", patch_conexant_auto), HDA_CODEC_ENTRY(0x14f15047, "CX20551 (Waikiki)", patch_conexant_auto),
From: Michael Neuling mikey@neuling.org
commit f16d80b75a096c52354c6e0a574993f3b0dfbdfe upstream.
On systems like P9 powernv where we have no TM (or P8 booted with ppc_tm=off), userspace can construct a signal context which still has the MSR TS bits set. The kernel tries to restore this context which results in the following crash:
Unexpected TM Bad Thing exception at c0000000000022fc (msr 0x8000000102a03031) tm_scratch=800000020280f033 Oops: Unrecoverable exception, sig: 6 [#1] LE PAGE_SIZE=64K MMU=Hash SMP NR_CPUS=2048 NUMA pSeries Modules linked in: CPU: 0 PID: 1636 Comm: sigfuz Not tainted 5.2.0-11043-g0a8ad0ffa4 #69 NIP: c0000000000022fc LR: 00007fffb2d67e48 CTR: 0000000000000000 REGS: c00000003fffbd70 TRAP: 0700 Not tainted (5.2.0-11045-g7142b497d8) MSR: 8000000102a03031 <SF,VEC,VSX,FP,ME,IR,DR,LE,TM[E]> CR: 42004242 XER: 00000000 CFAR: c0000000000022e0 IRQMASK: 0 GPR00: 0000000000000072 00007fffb2b6e560 00007fffb2d87f00 0000000000000669 GPR04: 00007fffb2b6e728 0000000000000000 0000000000000000 00007fffb2b6f2a8 GPR08: 0000000000000000 0000000000000000 0000000000000000 0000000000000000 GPR12: 0000000000000000 00007fffb2b76900 0000000000000000 0000000000000000 GPR16: 00007fffb2370000 00007fffb2d84390 00007fffea3a15ac 000001000a250420 GPR20: 00007fffb2b6f260 0000000010001770 0000000000000000 0000000000000000 GPR24: 00007fffb2d843a0 00007fffea3a14a0 0000000000010000 0000000000800000 GPR28: 00007fffea3a14d8 00000000003d0f00 0000000000000000 00007fffb2b6e728 NIP [c0000000000022fc] rfi_flush_fallback+0x7c/0x80 LR [00007fffb2d67e48] 0x7fffb2d67e48 Call Trace: Instruction dump: e96a0220 e96a02a8 e96a0330 e96a03b8 394a0400 4200ffdc 7d2903a6 e92d0c00 e94d0c08 e96d0c10 e82d0c18 7db242a6 <4c000024> 7db243a6 7db142a6 f82d0c18
The problem is the signal code assumes TM is enabled when CONFIG_PPC_TRANSACTIONAL_MEM is enabled. This may not be the case as with P9 powernv or if `ppc_tm=off` is used on P8.
This means any local user can crash the system.
Fix the problem by returning a bad stack frame to the user if they try to set the MSR TS bits with sigreturn() on systems where TM is not supported.
Found with sigfuz kernel selftest on P9.
This fixes CVE-2019-13648.
Fixes: 2b0a576d15e0 ("powerpc: Add new transactional memory state to the signal context") Cc: stable@vger.kernel.org # v3.9 Reported-by: Praveen Pandey Praveen.Pandey@in.ibm.com Signed-off-by: Michael Neuling mikey@neuling.org Signed-off-by: Michael Ellerman mpe@ellerman.id.au Link: https://lore.kernel.org/r/20190719050502.405-1-mikey@neuling.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- arch/powerpc/kernel/signal_32.c | 3 +++ arch/powerpc/kernel/signal_64.c | 5 +++++ 2 files changed, 8 insertions(+)
--- a/arch/powerpc/kernel/signal_32.c +++ b/arch/powerpc/kernel/signal_32.c @@ -1261,6 +1261,9 @@ long sys_rt_sigreturn(int r3, int r4, in goto bad;
if (MSR_TM_ACTIVE(msr_hi<<32)) { + /* Trying to start TM on non TM system */ + if (!cpu_has_feature(CPU_FTR_TM)) + goto bad; /* We only recheckpoint on return if we're * transaction. */ --- a/arch/powerpc/kernel/signal_64.c +++ b/arch/powerpc/kernel/signal_64.c @@ -695,6 +695,11 @@ int sys_rt_sigreturn(unsigned long r3, u if (MSR_TM_ACTIVE(msr)) { /* We recheckpoint on return. */ struct ucontext __user *uc_transact; + + /* Trying to start TM on non TM system */ + if (!cpu_has_feature(CPU_FTR_TM)) + goto badframe; + if (__get_user(uc_transact, &uc->uc_link)) goto badframe; if (restore_tm_sigcontexts(regs, &uc->uc_mcontext,
From: Linus Torvalds torvalds@linux-foundation.org
commit d7852fbd0f0423937fa287a598bfde188bb68c22 upstream.
It turns out that 'access()' (and 'faccessat()') can cause a lot of RCU work because it installs a temporary credential that gets allocated and freed for each system call.
The allocation and freeing overhead is mostly benign, but because credentials can be accessed under the RCU read lock, the freeing involves a RCU grace period.
Which is not a huge deal normally, but if you have a lot of access() calls, this causes a fair amount of seconday damage: instead of having a nice alloc/free patterns that hits in hot per-CPU slab caches, you have all those delayed free's, and on big machines with hundreds of cores, the RCU overhead can end up being enormous.
But it turns out that all of this is entirely unnecessary. Exactly because access() only installs the credential as the thread-local subjective credential, the temporary cred pointer doesn't actually need to be RCU free'd at all. Once we're done using it, we can just free it synchronously and avoid all the RCU overhead.
So add a 'non_rcu' flag to 'struct cred', which can be set by users that know they only use it in non-RCU context (there are other potential users for this). We can make it a union with the rcu freeing list head that we need for the RCU case, so this doesn't need any extra storage.
Note that this also makes 'get_current_cred()' clear the new non_rcu flag, in case we have filesystems that take a long-term reference to the cred and then expect the RCU delayed freeing afterwards. It's not entirely clear that this is required, but it makes for clear semantics: the subjective cred remains non-RCU as long as you only access it synchronously using the thread-local accessors, but you _can_ use it as a generic cred if you want to.
It is possible that we should just remove the whole RCU markings for ->cred entirely. Only ->real_cred is really supposed to be accessed through RCU, and the long-term cred copies that nfs uses might want to explicitly re-enable RCU freeing if required, rather than have get_current_cred() do it implicitly.
But this is a "minimal semantic changes" change for the immediate problem.
Acked-by: Peter Zijlstra (Intel) peterz@infradead.org Acked-by: Eric Dumazet edumazet@google.com Acked-by: Paul E. McKenney paulmck@linux.ibm.com Cc: Oleg Nesterov oleg@redhat.com Cc: Jan Glauber jglauber@marvell.com Cc: Jiri Kosina jikos@kernel.org Cc: Jayachandran Chandrasekharan Nair jnair@marvell.com Cc: Greg KH greg@kroah.com Cc: Kees Cook keescook@chromium.org Cc: David Howells dhowells@redhat.com Cc: Miklos Szeredi miklos@szeredi.hu Cc: Al Viro viro@zeniv.linux.org.uk Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- fs/open.c | 19 +++++++++++++++++++ include/linux/cred.h | 7 ++++++- kernel/cred.c | 21 +++++++++++++++++++-- 3 files changed, 44 insertions(+), 3 deletions(-)
--- a/fs/open.c +++ b/fs/open.c @@ -363,6 +363,25 @@ SYSCALL_DEFINE3(faccessat, int, dfd, con override_cred->cap_permitted; }
+ /* + * The new set of credentials can *only* be used in + * task-synchronous circumstances, and does not need + * RCU freeing, unless somebody then takes a separate + * reference to it. + * + * NOTE! This is _only_ true because this credential + * is used purely for override_creds() that installs + * it as the subjective cred. Other threads will be + * accessing ->real_cred, not the subjective cred. + * + * If somebody _does_ make a copy of this (using the + * 'get_current_cred()' function), that will clear the + * non_rcu field, because now that other user may be + * expecting RCU freeing. But normal thread-synchronous + * cred accesses will keep things non-RCY. + */ + override_cred->non_rcu = 1; + old_cred = override_creds(override_cred); retry: res = user_path_at(dfd, filename, lookup_flags, &path); --- a/include/linux/cred.h +++ b/include/linux/cred.h @@ -153,7 +153,11 @@ struct cred { struct user_struct *user; /* real user ID subscription */ struct user_namespace *user_ns; /* user_ns the caps and keyrings are relative to. */ struct group_info *group_info; /* supplementary groups for euid/fsgid */ - struct rcu_head rcu; /* RCU deletion hook */ + /* RCU deletion */ + union { + int non_rcu; /* Can we skip RCU deletion? */ + struct rcu_head rcu; /* RCU deletion hook */ + }; };
extern void __put_cred(struct cred *); @@ -251,6 +255,7 @@ static inline const struct cred *get_cre { struct cred *nonconst_cred = (struct cred *) cred; validate_creds(cred); + nonconst_cred->non_rcu = 0; return get_new_cred(nonconst_cred); }
--- a/kernel/cred.c +++ b/kernel/cred.c @@ -146,7 +146,10 @@ void __put_cred(struct cred *cred) BUG_ON(cred == current->cred); BUG_ON(cred == current->real_cred);
- call_rcu(&cred->rcu, put_cred_rcu); + if (cred->non_rcu) + put_cred_rcu(&cred->rcu); + else + call_rcu(&cred->rcu, put_cred_rcu); } EXPORT_SYMBOL(__put_cred);
@@ -257,6 +260,7 @@ struct cred *prepare_creds(void) old = task->cred; memcpy(new, old, sizeof(struct cred));
+ new->non_rcu = 0; atomic_set(&new->usage, 1); set_cred_subscribers(new, 0); get_group_info(new->group_info); @@ -536,7 +540,19 @@ const struct cred *override_creds(const
validate_creds(old); validate_creds(new); - get_cred(new); + + /* + * NOTE! This uses 'get_new_cred()' rather than 'get_cred()'. + * + * That means that we do not clear the 'non_rcu' flag, since + * we are only installing the cred into the thread-synchronous + * '->cred' pointer, not the '->real_cred' pointer that is + * visible to other threads under RCU. + * + * Also note that we did validate_creds() manually, not depending + * on the validation in 'get_cred()'. + */ + get_new_cred((struct cred *)new); alter_cred_subscribers(new, 1); rcu_assign_pointer(current->cred, new); alter_cred_subscribers(old, -1); @@ -619,6 +635,7 @@ struct cred *prepare_kernel_cred(struct validate_creds(old);
*new = *old; + new->non_rcu = 0; atomic_set(&new->usage, 1); set_cred_subscribers(new, 0); get_uid(new->user);
From: Christoph Lameter cl@linux.com
commit 587198ba5206cdf0d30855f7361af950a4172cd6 upstream.
If we detect that there is nothing to do just set the flag and do not check if it was already set before. Races really do not matter. If the flag is set by any code then the shepherd will start dealing with the situation and reenable the vmstat workers when necessary again.
Since commit 0eb77e988032 ("vmstat: make vmstat_updater deferrable again and shut down on idle") quiet_vmstat might update cpu_stat_off and mark a particular cpu to be handled by vmstat_shepherd. This might trigger a VM_BUG_ON in vmstat_update because the work item might have been sleeping during the idle period and see the cpu_stat_off updated after the wake up. The VM_BUG_ON is therefore misleading and no more appropriate. Moreover it doesn't really suite any protection from real bugs because vmstat_shepherd will simply reschedule the vmstat_work anytime it sees a particular cpu set or vmstat_update would do the same from the worker context directly. Even when the two would race the result wouldn't be incorrect as the counters update is fully idempotent.
Reported-by: Sasha Levin sasha.levin@oracle.com Signed-off-by: Christoph Lameter cl@linux.com Acked-by: Michal Hocko mhocko@suse.com Cc: Johannes Weiner hannes@cmpxchg.org Cc: Tetsuo Handa penguin-kernel@i-love.sakura.ne.jp Cc: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Daniel Wagner wagi@monom.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- mm/vmstat.c | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-)
--- a/mm/vmstat.c +++ b/mm/vmstat.c @@ -1407,17 +1407,7 @@ static void vmstat_update(struct work_st * Defer the checking for differentials to the * shepherd thread on a different processor. */ - int r; - /* - * Shepherd work thread does not race since it never - * changes the bit if its zero but the cpu - * online / off line code may race if - * worker threads are still allowed during - * shutdown / startup. - */ - r = cpumask_test_and_set_cpu(smp_processor_id(), - cpu_stat_off); - VM_BUG_ON(r); + cpumask_set_cpu(smp_processor_id(), cpu_stat_off); } }
From: Michal Hocko mhocko@suse.com
commit f01f17d3705bb6081c9e5728078f64067982be36 upstream.
Mike has reported a considerable overhead of refresh_cpu_vm_stats from the idle entry during pipe test:
12.89% [kernel] [k] refresh_cpu_vm_stats.isra.12 4.75% [kernel] [k] __schedule 4.70% [kernel] [k] mutex_unlock 3.14% [kernel] [k] __switch_to
This is caused by commit 0eb77e988032 ("vmstat: make vmstat_updater deferrable again and shut down on idle") which has placed quiet_vmstat into cpu_idle_loop. The main reason here seems to be that the idle entry has to get over all zones and perform atomic operations for each vmstat entry even though there might be no per cpu diffs. This is a pointless overhead for _each_ idle entry.
Make sure that quiet_vmstat is as light as possible.
First of all it doesn't make any sense to do any local sync if the current cpu is already set in oncpu_stat_off because vmstat_update puts itself there only if there is nothing to do.
Then we can check need_update which should be a cheap way to check for potential per-cpu diffs and only then do refresh_cpu_vm_stats.
The original patch also did cancel_delayed_work which we are not doing here. There are two reasons for that. Firstly cancel_delayed_work from idle context will blow up on RT kernels (reported by Mike):
CPU: 1 PID: 0 Comm: swapper/1 Not tainted 4.5.0-rt3 #7 Hardware name: MEDION MS-7848/MS-7848, BIOS M7848W08.20C 09/23/2013 Call Trace: dump_stack+0x49/0x67 ___might_sleep+0xf5/0x180 rt_spin_lock+0x20/0x50 try_to_grab_pending+0x69/0x240 cancel_delayed_work+0x26/0xe0 quiet_vmstat+0x75/0xa0 cpu_idle_loop+0x38/0x3e0 cpu_startup_entry+0x13/0x20 start_secondary+0x114/0x140
And secondly, even on !RT kernels it might add some non trivial overhead which is not necessary. Even if the vmstat worker wakes up and preempts idle then it will be most likely a single shot noop because the stats were already synced and so it would end up on the oncpu_stat_off anyway. We just need to teach both vmstat_shepherd and vmstat_update to stop scheduling the worker if there is nothing to do.
[mgalbraith@suse.de: cancel pending work of the cpu_stat_off CPU] Signed-off-by: Michal Hocko mhocko@suse.com Reported-by: Mike Galbraith umgwanakikbuti@gmail.com Acked-by: Christoph Lameter cl@linux.com Signed-off-by: Mike Galbraith mgalbraith@suse.de Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Daniel Wagner wagi@monom.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- mm/vmstat.c | 68 ++++++++++++++++++++++++++++++++++++++++-------------------- 1 file changed, 46 insertions(+), 22 deletions(-)
--- a/mm/vmstat.c +++ b/mm/vmstat.c @@ -1395,10 +1395,15 @@ static void vmstat_update(struct work_st * Counters were updated so we expect more updates * to occur in the future. Keep on running the * update worker thread. + * If we were marked on cpu_stat_off clear the flag + * so that vmstat_shepherd doesn't schedule us again. */ - queue_delayed_work_on(smp_processor_id(), vmstat_wq, - this_cpu_ptr(&vmstat_work), - round_jiffies_relative(sysctl_stat_interval)); + if (!cpumask_test_and_clear_cpu(smp_processor_id(), + cpu_stat_off)) { + queue_delayed_work_on(smp_processor_id(), vmstat_wq, + this_cpu_ptr(&vmstat_work), + round_jiffies_relative(sysctl_stat_interval)); + } } else { /* * We did not update any counters so the app may be in @@ -1416,18 +1421,6 @@ static void vmstat_update(struct work_st * until the diffs stay at zero. The function is used by NOHZ and can only be * invoked when tick processing is not active. */ -void quiet_vmstat(void) -{ - if (system_state != SYSTEM_RUNNING) - return; - - do { - if (!cpumask_test_and_set_cpu(smp_processor_id(), cpu_stat_off)) - cancel_delayed_work(this_cpu_ptr(&vmstat_work)); - - } while (refresh_cpu_vm_stats(false)); -} - /* * Check if the diffs for a certain cpu indicate that * an update is needed. @@ -1451,6 +1444,30 @@ static bool need_update(int cpu) return false; }
+void quiet_vmstat(void) +{ + if (system_state != SYSTEM_RUNNING) + return; + + /* + * If we are already in hands of the shepherd then there + * is nothing for us to do here. + */ + if (cpumask_test_and_set_cpu(smp_processor_id(), cpu_stat_off)) + return; + + if (!need_update(smp_processor_id())) + return; + + /* + * Just refresh counters and do not care about the pending delayed + * vmstat_update. It doesn't fire that often to matter and canceling + * it would be too expensive from this path. + * vmstat_shepherd will take care about that for us. + */ + refresh_cpu_vm_stats(false); +} +
/* * Shepherd worker thread that checks the @@ -1468,18 +1485,25 @@ static void vmstat_shepherd(struct work_
get_online_cpus(); /* Check processors whose vmstat worker threads have been disabled */ - for_each_cpu(cpu, cpu_stat_off) - if (need_update(cpu) && - cpumask_test_and_clear_cpu(cpu, cpu_stat_off)) - - queue_delayed_work_on(cpu, vmstat_wq, - &per_cpu(vmstat_work, cpu), 0); + for_each_cpu(cpu, cpu_stat_off) { + struct delayed_work *dw = &per_cpu(vmstat_work, cpu);
+ if (need_update(cpu)) { + if (cpumask_test_and_clear_cpu(cpu, cpu_stat_off)) + queue_delayed_work_on(cpu, vmstat_wq, dw, 0); + } else { + /* + * Cancel the work if quiet_vmstat has put this + * cpu on cpu_stat_off because the work item might + * be still scheduled + */ + cancel_delayed_work(dw); + } + } put_online_cpus();
schedule_delayed_work(&shepherd, round_jiffies_relative(sysctl_stat_interval)); - }
static void __init start_shepherd_timer(void)
[ Upstream commit 99253eb750fda6a644d5188fb26c43bad8d5a745 ]
Commit 5e1859fbcc3c ("ipv4: ipmr: various fixes and cleanups") fixed the issue for ipv4 ipmr:
ip_mroute_setsockopt() & ip_mroute_getsockopt() should not access/set raw_sk(sk)->ipmr_table before making sure the socket is a raw socket, and protocol is IGMP
The same fix should be done for ipv6 ipmr as well.
This patch can fix the panic caused by overwriting the same offset as ipmr_table as in raw_sk(sk) when accessing other type's socket by ip_mroute_setsockopt().
Signed-off-by: Xin Long lucien.xin@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- net/ipv6/ip6mr.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-)
--- a/net/ipv6/ip6mr.c +++ b/net/ipv6/ip6mr.c @@ -1666,6 +1666,10 @@ int ip6_mroute_setsockopt(struct sock *s struct net *net = sock_net(sk); struct mr6_table *mrt;
+ if (sk->sk_type != SOCK_RAW || + inet_sk(sk)->inet_num != IPPROTO_ICMPV6) + return -EOPNOTSUPP; + mrt = ip6mr_get_table(net, raw6_sk(sk)->ip6mr_table ? : RT6_TABLE_DFLT); if (!mrt) return -ENOENT; @@ -1677,9 +1681,6 @@ int ip6_mroute_setsockopt(struct sock *s
switch (optname) { case MRT6_INIT: - if (sk->sk_type != SOCK_RAW || - inet_sk(sk)->inet_num != IPPROTO_ICMPV6) - return -EOPNOTSUPP; if (optlen < sizeof(int)) return -EINVAL;
@@ -1816,6 +1817,10 @@ int ip6_mroute_getsockopt(struct sock *s struct net *net = sock_net(sk); struct mr6_table *mrt;
+ if (sk->sk_type != SOCK_RAW || + inet_sk(sk)->inet_num != IPPROTO_ICMPV6) + return -EOPNOTSUPP; + mrt = ip6mr_get_table(net, raw6_sk(sk)->ip6mr_table ? : RT6_TABLE_DFLT); if (!mrt) return -ENOENT;
[ Upstream commit dbbf2d1e4077bab0c65ece2765d3fc69cf7d610f ]
tcp_write_queue_purge clears all the SKBs in the write queue but does not reset the sk_send_head. As a result, we can have a NULL pointer dereference anywhere that we use tcp_send_head instead of the tcp_write_queue_tail.
For example, after a27fd7a8ed38 (tcp: purge write queue upon RST), we can purge the write queue on RST. Prior to 75c119afe14f (tcp: implement rb-tree based retransmit queue), tcp_push will only check tcp_send_head and then accesses tcp_write_queue_tail to send the actual SKB. As a result, it will dereference a NULL pointer.
This has been reported twice for 4.14 where we don't have 75c119afe14f:
By Timofey Titovets:
[ 422.081094] BUG: unable to handle kernel NULL pointer dereference at 0000000000000038 [ 422.081254] IP: tcp_push+0x42/0x110 [ 422.081314] PGD 0 P4D 0 [ 422.081364] Oops: 0002 [#1] SMP PTI
By Yongjian Xu:
BUG: unable to handle kernel NULL pointer dereference at 0000000000000038 IP: tcp_push+0x48/0x120 PGD 80000007ff77b067 P4D 80000007ff77b067 PUD 7fd989067 PMD 0 Oops: 0002 [#18] SMP PTI Modules linked in: tcp_diag inet_diag tcp_bbr sch_fq iTCO_wdt iTCO_vendor_support pcspkr ixgbe mdio i2c_i801 lpc_ich joydev input_leds shpchp e1000e igb dca ptp pps_core hwmon mei_me mei ipmi_si ipmi_msghandler sg ses scsi_transport_sas enclosure ext4 jbd2 mbcache sd_mod ahci libahci megaraid_sas wmi ast ttm dm_mirror dm_region_hash dm_log dm_mod dax CPU: 6 PID: 14156 Comm: [ET_NET 6] Tainted: G D 4.14.26-1.el6.x86_64 #1 Hardware name: LENOVO ThinkServer RD440 /ThinkServer RD440, BIOS A0TS80A 09/22/2014 task: ffff8807d78d8140 task.stack: ffffc9000e944000 RIP: 0010:tcp_push+0x48/0x120 RSP: 0018:ffffc9000e947a88 EFLAGS: 00010246 RAX: 00000000000005b4 RBX: ffff880f7cce9c00 RCX: 0000000000000000 RDX: 0000000000000000 RSI: 0000000000000040 RDI: ffff8807d00f5000 RBP: ffffc9000e947aa8 R08: 0000000000001c84 R09: 0000000000000000 R10: ffff8807d00f5158 R11: 0000000000000000 R12: ffff8807d00f5000 R13: 0000000000000020 R14: 00000000000256d4 R15: 0000000000000000 FS: 00007f5916de9700(0000) GS:ffff88107fd00000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 0000000000000038 CR3: 00000007f8226004 CR4: 00000000001606e0 Call Trace: tcp_sendmsg_locked+0x33d/0xe50 tcp_sendmsg+0x37/0x60 inet_sendmsg+0x39/0xc0 sock_sendmsg+0x49/0x60 sock_write_iter+0xb6/0x100 do_iter_readv_writev+0xec/0x130 ? rw_verify_area+0x49/0xb0 do_iter_write+0x97/0xd0 vfs_writev+0x7e/0xe0 ? __wake_up_common_lock+0x80/0xa0 ? __fget_light+0x2c/0x70 ? __do_page_fault+0x1e7/0x530 do_writev+0x60/0xf0 ? inet_shutdown+0xac/0x110 SyS_writev+0x10/0x20 do_syscall_64+0x6f/0x140 ? prepare_exit_to_usermode+0x8b/0xa0 entry_SYSCALL_64_after_hwframe+0x3d/0xa2 RIP: 0033:0x3135ce0c57 RSP: 002b:00007f5916de4b00 EFLAGS: 00000293 ORIG_RAX: 0000000000000014 RAX: ffffffffffffffda RBX: 0000000000000000 RCX: 0000003135ce0c57 RDX: 0000000000000002 RSI: 00007f5916de4b90 RDI: 000000000000606f RBP: 0000000000000000 R08: 0000000000000000 R09: 00007f5916de8c38 R10: 0000000000000000 R11: 0000000000000293 R12: 00000000000464cc R13: 00007f5916de8c30 R14: 00007f58d8bef080 R15: 0000000000000002 Code: 48 8b 97 60 01 00 00 4c 8d 97 58 01 00 00 41 b9 00 00 00 00 41 89 f3 4c 39 d2 49 0f 44 d1 41 81 e3 00 80 00 00 0f 85 b0 00 00 00 <80> 4a 38 08 44 8b 8f 74 06 00 00 44 89 8f 7c 06 00 00 83 e6 01 RIP: tcp_push+0x48/0x120 RSP: ffffc9000e947a88 CR2: 0000000000000038 ---[ end trace 8d545c2e93515549 ]---
There is other scenario which found in stable 4.4: Allocated: [<ffffffff82f380a6>] __alloc_skb+0xe6/0x600 net/core/skbuff.c:218 [<ffffffff832466c3>] alloc_skb_fclone include/linux/skbuff.h:856 [inline] [<ffffffff832466c3>] sk_stream_alloc_skb+0xa3/0x5d0 net/ipv4/tcp.c:833 [<ffffffff83249164>] tcp_sendmsg+0xd34/0x2b00 net/ipv4/tcp.c:1178 [<ffffffff83300ef3>] inet_sendmsg+0x203/0x4d0 net/ipv4/af_inet.c:755 Freed: [<ffffffff82f372fd>] __kfree_skb+0x1d/0x20 net/core/skbuff.c:676 [<ffffffff83288834>] sk_wmem_free_skb include/net/sock.h:1447 [inline] [<ffffffff83288834>] tcp_write_queue_purge include/net/tcp.h:1460 [inline] [<ffffffff83288834>] tcp_connect_init net/ipv4/tcp_output.c:3122 [inline] [<ffffffff83288834>] tcp_connect+0xb24/0x30c0 net/ipv4/tcp_output.c:3261 [<ffffffff8329b991>] tcp_v4_connect+0xf31/0x1890 net/ipv4/tcp_ipv4.c:246
BUG: KASAN: use-after-free in tcp_skb_pcount include/net/tcp.h:796 [inline] BUG: KASAN: use-after-free in tcp_init_tso_segs net/ipv4/tcp_output.c:1619 [inline] BUG: KASAN: use-after-free in tcp_write_xmit+0x3fc2/0x4cb0 net/ipv4/tcp_output.c:2056 [<ffffffff81515cd5>] kasan_report.cold.7+0x175/0x2f7 mm/kasan/report.c:408 [<ffffffff814f9784>] __asan_report_load2_noabort+0x14/0x20 mm/kasan/report.c:427 [<ffffffff83286582>] tcp_skb_pcount include/net/tcp.h:796 [inline] [<ffffffff83286582>] tcp_init_tso_segs net/ipv4/tcp_output.c:1619 [inline] [<ffffffff83286582>] tcp_write_xmit+0x3fc2/0x4cb0 net/ipv4/tcp_output.c:2056 [<ffffffff83287a40>] __tcp_push_pending_frames+0xa0/0x290 net/ipv4/tcp_output.c:2307
stable 4.4 and stable 4.9 don't have the commit abb4a8b870b5 ("tcp: purge write queue upon RST") which is referred in dbbf2d1e4077, in tcp_connect_init, it calls tcp_write_queue_purge, and does not reset sk_send_head, then UAF.
stable 4.14 have the commit abb4a8b870b5 ("tcp: purge write queue upon RST"), in tcp_reset, it calls tcp_write_queue_purge(sk), and does not reset sk_send_head, then UAF.
So this patch can be used to fix stable 4.4 and 4.9.
Fixes: a27fd7a8ed38 (tcp: purge write queue upon RST) Reported-by: Timofey Titovets nefelim4ag@gmail.com Reported-by: Yongjian Xu yongjianchn@gmail.com Signed-off-by: Eric Dumazet edumazet@google.com Signed-off-by: Soheil Hassas Yeganeh soheil@google.com Tested-by: Yongjian Xu yongjianchn@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Mao Wenan maowenan@huawei.com Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org --- include/net/tcp.h | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-)
--- a/include/net/tcp.h +++ b/include/net/tcp.h @@ -1443,6 +1443,11 @@ struct sock *tcp_try_fastopen(struct soc void tcp_fastopen_init_key_once(bool publish); #define TCP_FASTOPEN_KEY_LENGTH 16
+static inline void tcp_init_send_head(struct sock *sk) +{ + sk->sk_send_head = NULL; +} + /* Fastopen key context */ struct tcp_fastopen_context { struct crypto_cipher *tfm; @@ -1459,6 +1464,7 @@ static inline void tcp_write_queue_purge sk_wmem_free_skb(sk, skb); sk_mem_reclaim(sk); tcp_clear_all_retrans_hints(tcp_sk(sk)); + tcp_init_send_head(sk); inet_csk(sk)->icsk_backoff = 0; }
@@ -1520,11 +1526,6 @@ static inline void tcp_check_send_head(s tcp_sk(sk)->highest_sack = NULL; }
-static inline void tcp_init_send_head(struct sock *sk) -{ - sk->sk_send_head = NULL; -} - static inline void __tcp_add_write_queue_tail(struct sock *sk, struct sk_buff *skb) { __skb_queue_tail(&sk->sk_write_queue, skb);
From: Phong Tran tranmanphong@gmail.com
commit f384e62a82ba5d85408405fdd6aeff89354deaa9 upstream.
The syzbot test with random endpoint address which made the idx is overflow in the table of endpoint configuations.
this adds the checking for fixing the error report from syzbot
KASAN: stack-out-of-bounds Read in hfcsusb_probe [1] The patch tested by syzbot [2]
Reported-by: syzbot+8750abbc3a46ef47d509@syzkaller.appspotmail.com
[1]: https://syzkaller.appspot.com/bug?id=30a04378dac680c5d521304a00a86156bb91352... [2]: https://groups.google.com/d/msg/syzkaller-bugs/_6HBdge8F3E/OJn7wVNpBAAJ
Signed-off-by: Phong Tran tranmanphong@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/isdn/hardware/mISDN/hfcsusb.c | 3 +++ 1 file changed, 3 insertions(+)
--- a/drivers/isdn/hardware/mISDN/hfcsusb.c +++ b/drivers/isdn/hardware/mISDN/hfcsusb.c @@ -1963,6 +1963,9 @@ hfcsusb_probe(struct usb_interface *intf
/* get endpoint base */ idx = ((ep_addr & 0x7f) - 1) * 2; + if (idx > 15) + return -EIO; + if (ep_addr & 0x80) idx++; attr = ep->desc.bmAttributes;
From: Oliver Neukum oneukum@suse.com
commit eff73de2b1600ad8230692f00bc0ab49b166512a upstream.
Kasan reported a use after free in cpia2_usb_disconnect() It first freed everything and then woke up those waiting. The reverse order is correct.
Fixes: 6c493f8b28c67 ("[media] cpia2: major overhaul to get it in a working state again")
Signed-off-by: Oliver Neukum oneukum@suse.com Reported-by: syzbot+0c90fc937c84f97d0aa6@syzkaller.appspotmail.com Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/media/usb/cpia2/cpia2_usb.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
--- a/drivers/media/usb/cpia2/cpia2_usb.c +++ b/drivers/media/usb/cpia2/cpia2_usb.c @@ -884,7 +884,6 @@ static void cpia2_usb_disconnect(struct cpia2_unregister_camera(cam); v4l2_device_disconnect(&cam->v4l2_dev); mutex_unlock(&cam->v4l2_lock); - v4l2_device_put(&cam->v4l2_dev);
if(cam->buffers) { DBG("Wakeup waiting processes\n"); @@ -897,6 +896,8 @@ static void cpia2_usb_disconnect(struct DBG("Releasing interface\n"); usb_driver_release_interface(&cpia2_driver, intf);
+ v4l2_device_put(&cam->v4l2_dev); + LOG("CPiA2 camera disconnected.\n"); }
From: Luke Nowakowski-Krijger lnowakow@eng.ucsd.edu
commit c666355e60ddb4748ead3bdd983e3f7f2224aaf0 upstream.
Change devm_k*alloc to k*alloc to manually allocate memory
The manual allocation and freeing of memory is necessary because when the USB radio is disconnected, the memory associated with devm_k*alloc is freed. Meaning if we still have unresolved references to the radio device, then we get use-after-free errors.
This patch fixes this by manually allocating memory, and freeing it in the v4l2.release callback that gets called when the last radio device exits.
Reported-and-tested-by: syzbot+a4387f5b6b799f6becbf@syzkaller.appspotmail.com
Signed-off-by: Luke Nowakowski-Krijger lnowakow@eng.ucsd.edu Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl [hverkuil-cisco@xs4all.nl: cleaned up two small checkpatch.pl warnings] [hverkuil-cisco@xs4all.nl: prefix subject with driver name] Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/media/radio/radio-raremono.c | 30 +++++++++++++++++++++++------- 1 file changed, 23 insertions(+), 7 deletions(-)
--- a/drivers/media/radio/radio-raremono.c +++ b/drivers/media/radio/radio-raremono.c @@ -283,6 +283,14 @@ static int vidioc_g_frequency(struct fil return 0; }
+static void raremono_device_release(struct v4l2_device *v4l2_dev) +{ + struct raremono_device *radio = to_raremono_dev(v4l2_dev); + + kfree(radio->buffer); + kfree(radio); +} + /* File system interface */ static const struct v4l2_file_operations usb_raremono_fops = { .owner = THIS_MODULE, @@ -307,12 +315,14 @@ static int usb_raremono_probe(struct usb struct raremono_device *radio; int retval = 0;
- radio = devm_kzalloc(&intf->dev, sizeof(struct raremono_device), GFP_KERNEL); - if (radio) - radio->buffer = devm_kmalloc(&intf->dev, BUFFER_LENGTH, GFP_KERNEL); - - if (!radio || !radio->buffer) + radio = kzalloc(sizeof(*radio), GFP_KERNEL); + if (!radio) + return -ENOMEM; + radio->buffer = kmalloc(BUFFER_LENGTH, GFP_KERNEL); + if (!radio->buffer) { + kfree(radio); return -ENOMEM; + }
radio->usbdev = interface_to_usbdev(intf); radio->intf = intf; @@ -336,7 +346,8 @@ static int usb_raremono_probe(struct usb if (retval != 3 || (get_unaligned_be16(&radio->buffer[1]) & 0xfff) == 0x0242) { dev_info(&intf->dev, "this is not Thanko's Raremono.\n"); - return -ENODEV; + retval = -ENODEV; + goto free_mem; }
dev_info(&intf->dev, "Thanko's Raremono connected: (%04X:%04X)\n", @@ -345,7 +356,7 @@ static int usb_raremono_probe(struct usb retval = v4l2_device_register(&intf->dev, &radio->v4l2_dev); if (retval < 0) { dev_err(&intf->dev, "couldn't register v4l2_device\n"); - return retval; + goto free_mem; }
mutex_init(&radio->lock); @@ -357,6 +368,7 @@ static int usb_raremono_probe(struct usb radio->vdev.ioctl_ops = &usb_raremono_ioctl_ops; radio->vdev.lock = &radio->lock; radio->vdev.release = video_device_release_empty; + radio->v4l2_dev.release = raremono_device_release;
usb_set_intfdata(intf, &radio->v4l2_dev);
@@ -372,6 +384,10 @@ static int usb_raremono_probe(struct usb } dev_err(&intf->dev, "could not register video device\n"); v4l2_device_unregister(&radio->v4l2_dev); + +free_mem: + kfree(radio->buffer); + kfree(radio); return retval; }
From: Vladis Dronov vdronov@redhat.com
commit b36a1552d7319bbfd5cf7f08726c23c5c66d4f73 upstream.
Certain ttys operations (pty_unix98_ops) lack tiocmget() and tiocmset() functions which are called by the certain HCI UART protocols (hci_ath, hci_bcm, hci_intel, hci_mrvl, hci_qca) via hci_uart_set_flow_control() or directly. This leads to an execution at NULL and can be triggered by an unprivileged user. Fix this by adding a helper function and a check for the missing tty operations in the protocols code.
This fixes CVE-2019-10207. The Fixes: lines list commits where calls to tiocm[gs]et() or hci_uart_set_flow_control() were added to the HCI UART protocols.
Link: https://syzkaller.appspot.com/bug?id=1b42faa2848963564a5b1b7f8c837ea7b55ffa5... Reported-by: syzbot+79337b501d6aa974d0f6@syzkaller.appspotmail.com Cc: stable@vger.kernel.org # v2.6.36+ Fixes: b3190df62861 ("Bluetooth: Support for Atheros AR300x serial chip") Fixes: 118612fb9165 ("Bluetooth: hci_bcm: Add suspend/resume PM functions") Fixes: ff2895592f0f ("Bluetooth: hci_intel: Add Intel baudrate configuration support") Fixes: 162f812f23ba ("Bluetooth: hci_uart: Add Marvell support") Fixes: fa9ad876b8e0 ("Bluetooth: hci_qca: Add support for Qualcomm Bluetooth chip wcn3990") Signed-off-by: Vladis Dronov vdronov@redhat.com Signed-off-by: Marcel Holtmann marcel@holtmann.org Reviewed-by: Yu-Chen, Cho acho@suse.com Tested-by: Yu-Chen, Cho acho@suse.com Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/bluetooth/hci_ath.c | 3 +++ drivers/bluetooth/hci_bcm.c | 3 +++ drivers/bluetooth/hci_intel.c | 3 +++ drivers/bluetooth/hci_ldisc.c | 9 +++++++++ drivers/bluetooth/hci_uart.h | 1 + 5 files changed, 19 insertions(+)
--- a/drivers/bluetooth/hci_ath.c +++ b/drivers/bluetooth/hci_ath.c @@ -101,6 +101,9 @@ static int ath_open(struct hci_uart *hu)
BT_DBG("hu %p", hu);
+ if (!hci_uart_has_flow_control(hu)) + return -EOPNOTSUPP; + ath = kzalloc(sizeof(*ath), GFP_KERNEL); if (!ath) return -ENOMEM; --- a/drivers/bluetooth/hci_bcm.c +++ b/drivers/bluetooth/hci_bcm.c @@ -279,6 +279,9 @@ static int bcm_open(struct hci_uart *hu)
bt_dev_dbg(hu->hdev, "hu %p", hu);
+ if (!hci_uart_has_flow_control(hu)) + return -EOPNOTSUPP; + bcm = kzalloc(sizeof(*bcm), GFP_KERNEL); if (!bcm) return -ENOMEM; --- a/drivers/bluetooth/hci_intel.c +++ b/drivers/bluetooth/hci_intel.c @@ -407,6 +407,9 @@ static int intel_open(struct hci_uart *h
BT_DBG("hu %p", hu);
+ if (!hci_uart_has_flow_control(hu)) + return -EOPNOTSUPP; + intel = kzalloc(sizeof(*intel), GFP_KERNEL); if (!intel) return -ENOMEM; --- a/drivers/bluetooth/hci_ldisc.c +++ b/drivers/bluetooth/hci_ldisc.c @@ -257,6 +257,15 @@ static int hci_uart_send_frame(struct hc return 0; }
+/* Check the underlying device or tty has flow control support */ +bool hci_uart_has_flow_control(struct hci_uart *hu) +{ + if (hu->tty->driver->ops->tiocmget && hu->tty->driver->ops->tiocmset) + return true; + + return false; +} + /* Flow control or un-flow control the device */ void hci_uart_set_flow_control(struct hci_uart *hu, bool enable) { --- a/drivers/bluetooth/hci_uart.h +++ b/drivers/bluetooth/hci_uart.h @@ -105,6 +105,7 @@ int hci_uart_tx_wakeup(struct hci_uart * int hci_uart_init_ready(struct hci_uart *hu); void hci_uart_init_tty(struct hci_uart *hu); void hci_uart_set_baudrate(struct hci_uart *hu, unsigned int speed); +bool hci_uart_has_flow_control(struct hci_uart *hu); void hci_uart_set_flow_control(struct hci_uart *hu, bool enable); void hci_uart_set_speeds(struct hci_uart *hu, unsigned int init_speed, unsigned int oper_speed);
From: Jann Horn jannh@google.com
commit 16d51a590a8ce3befb1308e0e7ab77f3b661af33 upstream.
When going through execve(), zero out the NUMA fault statistics instead of freeing them.
During execve, the task is reachable through procfs and the scheduler. A concurrent /proc/*/sched reader can read data from a freed ->numa_faults allocation (confirmed by KASAN) and write it back to userspace. I believe that it would also be possible for a use-after-free read to occur through a race between a NUMA fault and execve(): task_numa_fault() can lead to task_numa_compare(), which invokes task_weight() on the currently running task of a different CPU.
Another way to fix this would be to make ->numa_faults RCU-managed or add extra locking, but it seems easier to wipe the NUMA fault statistics on execve.
Signed-off-by: Jann Horn jannh@google.com Signed-off-by: Peter Zijlstra (Intel) peterz@infradead.org Cc: Linus Torvalds torvalds@linux-foundation.org Cc: Peter Zijlstra peterz@infradead.org Cc: Petr Mladek pmladek@suse.com Cc: Sergey Senozhatsky sergey.senozhatsky@gmail.com Cc: Thomas Gleixner tglx@linutronix.de Cc: Will Deacon will@kernel.org Fixes: 82727018b0d3 ("sched/numa: Call task_numa_free() from do_execve()") Link: https://lkml.kernel.org/r/20190716152047.14424-1-jannh@google.com Signed-off-by: Ingo Molnar mingo@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- fs/exec.c | 2 +- include/linux/sched.h | 4 ++-- kernel/fork.c | 2 +- kernel/sched/fair.c | 24 ++++++++++++++++++++---- 4 files changed, 24 insertions(+), 8 deletions(-)
--- a/fs/exec.c +++ b/fs/exec.c @@ -1642,7 +1642,7 @@ static int do_execveat_common(int fd, st current->fs->in_exec = 0; current->in_execve = 0; acct_update_integrals(current); - task_numa_free(current); + task_numa_free(current, false); free_bprm(bprm); kfree(pathbuf); putname(filename); --- a/include/linux/sched.h +++ b/include/linux/sched.h @@ -1860,7 +1860,7 @@ extern int arch_task_struct_size __read_ extern void task_numa_fault(int last_node, int node, int pages, int flags); extern pid_t task_numa_group_id(struct task_struct *p); extern void set_numabalancing_state(bool enabled); -extern void task_numa_free(struct task_struct *p); +extern void task_numa_free(struct task_struct *p, bool final); extern bool should_numa_migrate_memory(struct task_struct *p, struct page *page, int src_nid, int dst_cpu); #else @@ -1875,7 +1875,7 @@ static inline pid_t task_numa_group_id(s static inline void set_numabalancing_state(bool enabled) { } -static inline void task_numa_free(struct task_struct *p) +static inline void task_numa_free(struct task_struct *p, bool final) { } static inline bool should_numa_migrate_memory(struct task_struct *p, --- a/kernel/fork.c +++ b/kernel/fork.c @@ -254,7 +254,7 @@ void __put_task_struct(struct task_struc WARN_ON(tsk == current);
cgroup_free(tsk); - task_numa_free(tsk); + task_numa_free(tsk, true); security_task_free(tsk); exit_creds(tsk); delayacct_tsk_free(tsk); --- a/kernel/sched/fair.c +++ b/kernel/sched/fair.c @@ -2054,13 +2054,23 @@ no_join: return; }
-void task_numa_free(struct task_struct *p) +/* + * Get rid of NUMA staticstics associated with a task (either current or dead). + * If @final is set, the task is dead and has reached refcount zero, so we can + * safely free all relevant data structures. Otherwise, there might be + * concurrent reads from places like load balancing and procfs, and we should + * reset the data back to default state without freeing ->numa_faults. + */ +void task_numa_free(struct task_struct *p, bool final) { struct numa_group *grp = p->numa_group; - void *numa_faults = p->numa_faults; + unsigned long *numa_faults = p->numa_faults; unsigned long flags; int i;
+ if (!numa_faults) + return; + if (grp) { spin_lock_irqsave(&grp->lock, flags); for (i = 0; i < NR_NUMA_HINT_FAULT_STATS * nr_node_ids; i++) @@ -2073,8 +2083,14 @@ void task_numa_free(struct task_struct * put_numa_group(grp); }
- p->numa_faults = NULL; - kfree(numa_faults); + if (final) { + p->numa_faults = NULL; + kfree(numa_faults); + } else { + p->total_numa_faults = 0; + for (i = 0; i < NR_NUMA_HINT_FAULT_STATS * nr_node_ids; i++) + numa_faults[i] = 0; + } }
/*
From: Miroslav Lichvar mlichvar@redhat.com
commit 5515e9a6273b8c02034466bcbd717ac9f53dab99 upstream.
The PPS assert/clear offset corrections are set by the PPS_SETPARAMS ioctl in the pps_ktime structs, which also contain flags. The flags are not initialized by applications (using the timepps.h header) and they are not used by the kernel for anything except returning them back in the PPS_GETPARAMS ioctl.
Set the flags to zero to make it clear they are unused and avoid leaking uninitialized data of the PPS_SETPARAMS caller to other applications that have a read access to the PPS device.
Link: http://lkml.kernel.org/r/20190702092251.24303-1-mlichvar@redhat.com Signed-off-by: Miroslav Lichvar mlichvar@redhat.com Reviewed-by: Thomas Gleixner tglx@linutronix.de Acked-by: Rodolfo Giometti giometti@enneenne.com Cc: Greg KH greg@kroah.com Cc: Dan Carpenter dan.carpenter@oracle.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/pps/pps.c | 8 ++++++++ 1 file changed, 8 insertions(+)
--- a/drivers/pps/pps.c +++ b/drivers/pps/pps.c @@ -129,6 +129,14 @@ static long pps_cdev_ioctl(struct file * pps->params.mode |= PPS_CANWAIT; pps->params.api_version = PPS_API_VERS;
+ /* + * Clear unused fields of pps_kparams to avoid leaking + * uninitialized data of the PPS_SETPARAMS caller via + * PPS_GETPARAMS + */ + pps->params.assert_off_tu.flags = 0; + pps->params.clear_off_tu.flags = 0; + spin_unlock_irq(&pps->lock);
break;
From: Yan, Zheng zyan@redhat.com
commit d6e47819721ae2d9d090058ad5570a66f3c42e39 upstream.
ceph_d_revalidate(, LOOKUP_RCU) may call __ceph_caps_issued_mask() on a freeing inode.
Signed-off-by: "Yan, Zheng" zyan@redhat.com Reviewed-by: Jeff Layton jlayton@redhat.com Signed-off-by: Ilya Dryomov idryomov@gmail.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- fs/ceph/caps.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
--- a/fs/ceph/caps.c +++ b/fs/ceph/caps.c @@ -1072,20 +1072,23 @@ static int send_cap_msg(struct ceph_mds_ }
/* - * Queue cap releases when an inode is dropped from our cache. Since - * inode is about to be destroyed, there is no need for i_ceph_lock. + * Queue cap releases when an inode is dropped from our cache. */ void ceph_queue_caps_release(struct inode *inode) { struct ceph_inode_info *ci = ceph_inode(inode); struct rb_node *p;
+ /* lock i_ceph_lock, because ceph_d_revalidate(..., LOOKUP_RCU) + * may call __ceph_caps_issued_mask() on a freeing inode. */ + spin_lock(&ci->i_ceph_lock); p = rb_first(&ci->i_caps); while (p) { struct ceph_cap *cap = rb_entry(p, struct ceph_cap, ci_node); p = rb_next(p); __ceph_remove_cap(cap, true); } + spin_unlock(&ci->i_ceph_lock); }
/*
On Fri, Aug 02, 2019 at 11:27:01AM +0200, Greg Kroah-Hartman wrote:
This is the start of the stable review cycle for the 4.4.187 release. There are 158 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Sun 04 Aug 2019 09:19:34 AM UTC. Anything received after that time might be too late.
The whole patch series can be found in one patch at: https://www.kernel.org/pub/linux/kernel/v4.x/stable-review/patch-4.4.187-rc1... or in the git tree and branch at: git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git linux-4.4.y and the diffstat can be found below.
thanks,
greg k-h
All tests passing for Tegra...
Test results for stable-v4.4: 6 builds: 6 pass, 0 fail 12 boots: 12 pass, 0 fail 19 tests: 19 pass, 0 fail
Linux version: 4.4.187-rc1-g26f755a0d3e0 Boards tested: tegra124-jetson-tk1, tegra20-ventana, tegra30-cardhu-a04
Thierry
On Fri, Aug 02, 2019 at 11:27:01AM +0200, Greg Kroah-Hartman wrote:
This is the start of the stable review cycle for the 4.4.187 release. There are 158 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Sun 04 Aug 2019 09:19:34 AM UTC. Anything received after that time might be too late.
Early feedback:
Build reference: v4.4.186-159-g26f755a0d3e0
Building powerpc:defconfig ... failed
arch/powerpc/platforms/pseries/mobility.c: In function ‘post_mobility_fixup’: arch/powerpc/platforms/pseries/mobility.c:318:2: error: implicit declaration of function ‘cpus_read_lock’ arch/powerpc/platforms/pseries/mobility.c:325:2: error: implicit declaration of function ‘cacheinfo_teardown’ arch/powerpc/platforms/pseries/mobility.c:332:2: error: implicit declaration of function ‘cacheinfo_rebuild’ arch/powerpc/platforms/pseries/mobility.c:334:2: error: implicit declaration of function ‘cpus_read_unlock’
Culprits:
9d263cc3b7c1 powerpc/pseries/mobility: rebuild cacheinfo hierarchy post-migration d4b0908c6289 powerpc/pseries/mobility: prevent cpu hotplug during DT update
Guenter
On Fri, Aug 02, 2019 at 08:52:11AM -0700, Guenter Roeck wrote:
On Fri, Aug 02, 2019 at 11:27:01AM +0200, Greg Kroah-Hartman wrote:
This is the start of the stable review cycle for the 4.4.187 release. There are 158 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Sun 04 Aug 2019 09:19:34 AM UTC. Anything received after that time might be too late.
Early feedback:
Build reference: v4.4.186-159-g26f755a0d3e0
Building powerpc:defconfig ... failed
arch/powerpc/platforms/pseries/mobility.c: In function ‘post_mobility_fixup’: arch/powerpc/platforms/pseries/mobility.c:318:2: error: implicit declaration of function ‘cpus_read_lock’ arch/powerpc/platforms/pseries/mobility.c:325:2: error: implicit declaration of function ‘cacheinfo_teardown’ arch/powerpc/platforms/pseries/mobility.c:332:2: error: implicit declaration of function ‘cacheinfo_rebuild’ arch/powerpc/platforms/pseries/mobility.c:334:2: error: implicit declaration of function ‘cpus_read_unlock’
Culprits:
9d263cc3b7c1 powerpc/pseries/mobility: rebuild cacheinfo hierarchy post-migration d4b0908c6289 powerpc/pseries/mobility: prevent cpu hotplug during DT update
Both patches now dropped, thanks for letting me know. I'll go push out a -rc2 with those removed.
greg k-h
stable-rc/linux-4.4.y boot: 92 boots: 1 failed, 59 passed with 32 offline (v4.4.186-159-gc4286991ea44)
Full Boot Summary: https://kernelci.org/boot/all/job/stable-rc/branch/linux-4.4.y/kernel/v4.4.1... Full Build Summary: https://kernelci.org/build/stable-rc/branch/linux-4.4.y/kernel/v4.4.186-159-...
Tree: stable-rc Branch: linux-4.4.y Git Describe: v4.4.186-159-gc4286991ea44 Git Commit: c4286991ea44309c9b2dcf717fd7d04270809eae Git URL: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git Tested: 44 unique boards, 20 SoC families, 14 builds out of 190
Boot Failure Detected:
arm64: defconfig: gcc-8: qcom-qdf2400: 1 failed lab
Offline Platforms:
arm:
tegra_defconfig: gcc-8 tegra20-iris-512: 1 offline lab
exynos_defconfig: gcc-8 exynos5250-arndale: 1 offline lab exynos5420-arndale-octa: 1 offline lab exynos5800-peach-pi: 1 offline lab
multi_v7_defconfig: gcc-8 bcm72521-bcm97252sffe: 1 offline lab bcm7445-bcm97445c: 1 offline lab exynos5250-arndale: 1 offline lab exynos5420-arndale-octa: 1 offline lab exynos5800-peach-pi: 1 offline lab imx6dl-wandboard_dual: 1 offline lab imx6dl-wandboard_solo: 1 offline lab imx6q-wandboard: 1 offline lab meson8b-odroidc1: 1 offline lab omap3-beagle: 1 offline lab omap4-panda: 1 offline lab qcom-apq8064-ifc6410: 1 offline lab stih410-b2120: 1 offline lab sun4i-a10-cubieboard: 1 offline lab sun7i-a20-bananapi: 1 offline lab tegra20-iris-512: 1 offline lab vf610-colibri-eval-v3: 1 offline lab
omap2plus_defconfig: gcc-8 omap3-beagle: 1 offline lab omap4-panda: 1 offline lab
qcom_defconfig: gcc-8 qcom-apq8064-ifc6410: 1 offline lab
davinci_all_defconfig: gcc-8 da850-evm: 1 offline lab dm365evm,legacy: 1 offline lab
imx_v6_v7_defconfig: gcc-8 imx6dl-wandboard_dual: 1 offline lab imx6dl-wandboard_solo: 1 offline lab imx6q-wandboard: 1 offline lab vf610-colibri-eval-v3: 1 offline lab
sunxi_defconfig: gcc-8 sun4i-a10-cubieboard: 1 offline lab sun7i-a20-bananapi: 1 offline lab
--- For more info write to info@kernelci.org
On 8/2/19 3:27 AM, Greg Kroah-Hartman wrote:
This is the start of the stable review cycle for the 4.4.187 release. There are 158 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Sun 04 Aug 2019 09:19:34 AM UTC. Anything received after that time might be too late.
The whole patch series can be found in one patch at: https://www.kernel.org/pub/linux/kernel/v4.x/stable-review/patch-4.4.187-rc1... or in the git tree and branch at: git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git linux-4.4.y and the diffstat can be found below.
thanks,
greg k-h
Compiled and booted on my test system. No dmesg regressions.
thanks, -- Shuah
On Fri, 2 Aug 2019 at 15:00, Greg Kroah-Hartman gregkh@linuxfoundation.org wrote:
This is the start of the stable review cycle for the 4.4.187 release. There are 158 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Sun 04 Aug 2019 09:19:34 AM UTC. Anything received after that time might be too late.
The whole patch series can be found in one patch at: https://www.kernel.org/pub/linux/kernel/v4.x/stable-review/patch-4.4.187-rc1... or in the git tree and branch at: git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git linux-4.4.y and the diffstat can be found below.
thanks,
greg k-h
Results from Linaro’s test farm. No regressions on arm64, arm, x86_64, and i386.
Summary ------------------------------------------------------------------------
kernel: 4.4.187-rc2 git repo: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git git branch: linux-4.4.y git commit: d9815060e3ec2433dfffc8a3dcaed9842b1798c7 git describe: v4.4.186-157-gd9815060e3ec Test details: https://qa-reports.linaro.org/lkft/linux-stable-rc-4.4-oe/build/v4.4.186-157...
No regressions (compared to build v4.4.186)
No fixes (compared to build v4.4.186)
Ran 13277 total tests in the following environments and test suites.
Environments -------------- - i386 - juno-r2 - arm64 - qemu_arm - qemu_arm64 - qemu_i386 - qemu_x86_64 - x15 - arm - x86_64
Test Suites ----------- * build * kselftest * kvm-unit-tests * libhugetlbfs * ltp-cap_bounds-tests * ltp-commands-tests * ltp-containers-tests * ltp-cpuhotplug-tests * ltp-cve-tests * ltp-dio-tests * ltp-fcntl-locktests-tests * ltp-filecaps-tests * ltp-fs-tests * ltp-fs_bind-tests * ltp-fs_perms_simple-tests * ltp-fsx-tests * ltp-hugetlb-tests * ltp-io-tests * ltp-ipc-tests * ltp-math-tests * ltp-mm-tests * ltp-nptl-tests * ltp-open-posix-tests * ltp-pty-tests * ltp-sched-tests * ltp-securebits-tests * ltp-syscalls-tests * ltp-timers-tests * network-basic-tests * perf * spectre-meltdown-checker-test * v4l2-compliance * install-android-platform-tools-r2600
Summary ------------------------------------------------------------------------
kernel: 4.4.187-rc2 git repo: https://git.linaro.org/lkft/arm64-stable-rc.git git branch: 4.4.187-rc2-hikey-20190802-517 git commit: 83e555c108c2c8fc5cc0af29c02f47cc2676fb88 git describe: 4.4.187-rc2-hikey-20190802-517 Test details: https://qa-reports.linaro.org/lkft/linaro-hikey-stable-rc-4.4-oe/build/4.4.1...
No regressions (compared to build 4.4.187-rc1-hikey-20190802-516)
No fixes (compared to build 4.4.187-rc1-hikey-20190802-516)
Ran 1549 total tests in the following environments and test suites.
Environments -------------- - hi6220-hikey - arm64
Test Suites ----------- * build * install-android-platform-tools-r2600 * kselftest * libhugetlbfs * ltp-cap_bounds-tests * ltp-commands-tests * ltp-containers-tests * ltp-cpuhotplug-tests * ltp-cve-tests * ltp-dio-tests * ltp-fcntl-locktests-tests * ltp-filecaps-tests * ltp-fs-tests * ltp-fs_bind-tests * ltp-fs_perms_simple-tests * ltp-fsx-tests * ltp-hugetlb-tests * ltp-io-tests * ltp-ipc-tests * ltp-math-tests * ltp-mm-tests * ltp-nptl-tests * ltp-pty-tests * ltp-sched-tests * ltp-securebits-tests * ltp-syscalls-tests * ltp-timers-tests * perf * spectre-meltdown-checker-test * v4l2-compliance
On 8/2/19 2:27 AM, Greg Kroah-Hartman wrote:
This is the start of the stable review cycle for the 4.4.187 release. There are 158 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Sun 04 Aug 2019 09:19:34 AM UTC. Anything received after that time might be too late.
Build results: total: 170 pass: 170 fail: 0 Qemu test results: total: 301 pass: 301 fail: 0
Guenter
linux-stable-mirror@lists.linaro.org