mirror of
https://github.com/rd-stuffs/msm-4.14.git
synced 2025-02-20 11:45:48 +08:00
* remotes/origin/tmp-cb1f148: Linux 4.14.47 Revert "vti4: Don't override MTU passed on link creation via IFLA_MTU" Revert "vti4: Don't override MTU passed on link creation via IFLA_MTU" Linux 4.14.46 Revert "perf record: Fix crash in pipe mode" tools: sync up .h files with the repective arch and uapi .h files perf tools: Add trace/beauty/generated/ into .gitignore Linux 4.14.45 drm/vmwgfx: Set dmabuf_size when vmw_dmabuf_init is successful kdb: make "mdr" command repeat pinctrl: mcp23s08: spi: Fix regmap debugfs entries pinctrl: msm: Use dynamic GPIO numbering regulator: of: Add a missing 'of_node_put()' in an error handling path of 'of_regulator_match()' ARM: dts: porter: Fix HDMI output routing ARM: dts: imx7d: cl-som-imx7: fix pinctrl_enet i40e: Add delay after EMP reset for firmware to recover regmap: Correct comparison in regmap_cached ARM: dts: at91: tse850: use the correct compatible for the eeprom drm: rcar-du: lvds: Fix LVDS startup on R-Car Gen2 drm: rcar-du: lvds: Fix LVDS startup on R-Car Gen3 netlabel: If PF_INET6, check sk_buff ip header version selftests/net: fixes psock_fanout eBPF test case perf tests: Fix dwarf unwind for stripped binaries perf report: Fix memory corruption in --branch-history mode --branch-history perf tests: Use arch__compare_symbol_names to compare symbols perf report: Fix wrong jump arrow perf test: Fix test case inet_pton to accept inlines. x86/apic: Set up through-local-APIC mode on the boot CPU if 'noapic' specified drm/rockchip: Respect page offset for PRIME mmap calls MIPS: Octeon: Fix logging messages with spurious periods after newlines dpaa_eth: fix pause capability advertisement logic pinctrl: sh-pfc: r8a7796: Fix MOD_SEL register pin assignment for SSI pins group rcu: Call touch_nmi_watchdog() while printing stall warnings net: stmmac: call correct function in stmmac_mac_config_rx_queues_routing() audit: return on memory error to avoid null pointer dereference PCMCIA / PM: Avoid noirq suspend aborts during suspend-to-idle ARM: dts: bcm283x: Fix pin function of JTAG pins ARM: dts: bcm283x: Fix probing of bcm2835-i2s power: supply: ltc2941-battery-gauge: Fix temperature units sh_eth: fix TSU init on SH7734/R8A7740 ixgbe: prevent ptp_rx_hang from running when in FILTER_ALL mode udf: Provide saner default for invalid uid / gid PCI: Add function 1 DMA alias quirk for Marvell 88SE9220 dpaa_eth: fix SG mapping cpufreq: Reorder cpufreq_online() error code path net: stmmac: ensure that the MSS desc is the last desc to set the own bit net: stmmac: ensure that the device has released ownership before reading data drm/amdgpu: adjust timeout for ib_ring_tests(v2) drm/amdgpu: disable GFX ring and disable PQ wptr in hw_fini ARM: dts: dra71-evm: Correct evm_sd regulator max voltage drm: omapdrm: dss: Move initialization code from component bind to probe dmaengine: qcom: bam_dma: get num-channels and num-ees from dt vfio-ccw: fence off transport mode pinctrl: artpec6: dt: add missing pin group uart5nocts pinctrl: devicetree: Fix dt_to_map_one_config handling of hogs hwrng: stm32 - add reset during probe watchdog: asm9260_wdt: fix error handling in asm9260_wdt_probe() enic: enable rq before updating rq descriptors dmaengine: rcar-dmac: Check the done lists in rcar_dmac_chan_get_residue() dmaengine: pl330: fix a race condition in case of threaded irqs block: null_blk: fix 'Invalid parameters' when loading module tools: hv: fix compiler warnings about major/target_fname drm/bridge: sii902x: Retry status read after DDI I2C phy: qcom-qmp: Fix phy pipe clock gating ALSA: vmaster: Propagate slave error phy: rockchip-emmc: retry calpad busy trimming x86/devicetree: Fix device IRQ settings in DT x86/devicetree: Initialize device tree before using it gfs2: Fix fallocate chunk size soc: qcom: wcnss_ctrl: Fix increment in NV upload arm64: dts: qcom: Fix SPI5 config on MSM8996 perf/x86/intel: Fix event update for auto-reload perf/x86/intel: Fix large period handling on Broadwell CPUs efi/arm*: Only register page tables when they exist cdrom: do not call check_disk_change() inside cdrom_open() perf/x86/intel: Properly save/restore the PMU state in the NMI handler hwmon: (pmbus/adm1275) Accept negative page register values hwmon: (pmbus/max8688) Accept negative page register values drm/panel: simple: Fix the bus format for the Ontat panel perf/core: Fix perf_output_read_group() max17042: propagate of_node to power supply device perf/core: Fix installing cgroup events on CPU f2fs: fix to check extent cache in f2fs_drop_extent_tree f2fs: fix to clear CP_TRIMMED_FLAG f2fs: fix to set KEEP_SIZE bit in f2fs_zero_range cxl: Check if PSL data-cache is available before issue flush request powerpc/powernv/npu: Fix deadlock in mmio_invalidate() powerpc: Add missing prototype for arch_irq_work_raise() drm/meson: Fix an un-handled error path in 'meson_drv_bind_master()' drm/meson: Fix some error handling paths in 'meson_drv_bind_master()' ipmi_ssif: Fix kernel panic at msg_done_handler watchdog: aspeed: Fix translation of reset mode to ctrl register watchdog: dw: RMW the control register PCI: Restore config space on runtime resume despite being unbound MIPS: ath79: Fix AR724X_PLL_REG_PCIE_CONFIG offset net/smc: pay attention to MAX_ORDER for CQ entries spi: bcm-qspi: fIX some error handling paths regulator: gpio: Fix some error handling paths in 'gpio_regulator_probe()' coresight: Use %px to print pcsr instead of %p drm/amdkfd: add missing include of mm.h IB/core: Honor port_num while resolving GID for IB link layer perf stat: Fix core dump when flag T is used perf top: Fix top.call-graph config option reading KVM: lapic: stop advertising DIRECTED_EOI when in-kernel IOAPIC is in use i2c: mv64xxx: Apply errata delay only in standard mode cxgb4: Fix queue free path of ULD drivers ACPICA: acpi: acpica: fix acpi operand cache leak in nseval.c ACPICA: Fix memory leak on unusual memory leak ACPICA: Events: add a return on failure from acpi_hw_register_read dt-bindings: add device tree binding for Allwinner H6 main CCU remoteproc: imx_rproc: Fix an error handling path in 'imx_rproc_probe()' bcache: quit dc->writeback_thread when BCACHE_DEV_DETACHING is set zorro: Set up z->dev.dma_mask for the DMA API IB/mlx5: Set the default active rate and width to QDR and 4X cpufreq: cppc_cpufreq: Fix cppc_cpufreq_init() failure path iommu/mediatek: Fix protect memory setting drm/vmwgfx: Unpin the screen object backup buffer when not used ext4: don't complain about incorrect features when probing arm: dts: socfpga: fix GIC PPI warning virtio-net: Fix operstate for virtio when no VIRTIO_NET_F_STATUS watchdog: aspeed: Allow configuring for alternate boot ima: Fallback to the builtin hash algorithm ima: Fix Kconfig to select TPM 2.0 CRB interface cxgb4: Setup FW queues before registering netdev ath9k: fix crash in spectral scan nvme-pci: disable APST for Samsung NVMe SSD 960 EVO + ASUS PRIME Z370-A ath10k: Fix kernel panic while using worker (ath10k_sta_rc_update_wk) watchdog: davinci_wdt: fix error handling in davinci_wdt_probe() net/mlx5: Protect from command bit overflow selftests: Print the test we're running to /dev/kmsg tools/thermal: tmon: fix for segfault rsi: fix kernel panic observed on 64bit machine powerpc/perf: Fix kernel address leak via sampling registers powerpc/perf: Prevent kernel address leak to userspace via BHRB buffer hwmon: (nct6775) Fix writing pwmX_mode parisc/pci: Switch LBA PCI bus from Hard Fail to Soft Fail mode iwlwifi: mvm: check if mac80211_queue is valid in iwl_mvm_disable_txq m68k: set dma and coherent masks for platform FEC ethernets intel_th: Use correct method of finding hub iommu/amd: Take into account that alloc_dev_data() may return NULL ath10k: advertize beacon_int_min_gcd ieee802154: ca8210: fix uninitialised data read powerpc/mpic: Check if cpu_possible() in mpic_physmask() ACPI: acpi_pad: Fix memory leak in power saving threads drivers: macintosh: rack-meter: really fix bogus memsets xen/acpi: off by one in read_acpi_id() rxrpc: Don't treat call aborts as conn aborts rxrpc: Fix Tx ring annotation after initial Tx failure btrfs: qgroup: Fix root item corruption when multiple same source snapshots are created with quota enabled btrfs: fix lockdep splat in btrfs_alloc_subvolume_writers Btrfs: fix copy_items() return value when logging an inode btrfs: tests/qgroup: Fix wrong tree backref level powerpc/64s: sreset panic if there is no debugger or crash dump handlers net: bgmac: Correctly annotate register space net: bgmac: Fix endian access in bgmac_dma_tx_ring_free() sparc64: Make atomic_xchg() an inline function rather than a macro. fscache: Fix hanging wait on page discarded by writeback lan78xx: Connect phy early KVM: VMX: raise internal error for exception during invalid protected mode state x86/mm: Fix bogus warning during EFI bootup, use boot_cpu_has() instead of this_cpu_has() in build_cr3_noflush() sched/rt: Fix rq->clock_update_flags < RQCF_ACT_SKIP warning powerpc/64s/idle: Fix restore of AMOR on POWER9 after deep sleep ocfs2/dlm: don't handle migrate lockres if already in shutdown IB/rxe: Fix for oops in rxe_register_device on ppc64le arch btrfs: Fix possible softlock on single core machines Btrfs: fix NULL pointer dereference in log_dir_items Btrfs: bail out on error during replay_dir_deletes mm: thp: fix potential clearing to referenced flag in page_idle_clear_pte_refs_one() mm: fix races between address_space dereference and free in page_evicatable mm/ksm: fix interaction with THP ibmvnic: Zero used TX descriptor counter on reset dp83640: Ensure against premature access to PHY registers after reset perf clang: Add support for recent clang versions perf tools: Fix perf builds with clang support powerpc/fscr: Enable interrupts earlier before calling get_user() cpufreq: CPPC: Initialize shared perf capabilities of CPUs Force log to disk before reading the AGF during a fstrim sr: get/drop reference to device in revalidate and check_events z3fold: fix memory leak swap: divide-by-zero when zero length swap file on ssd fs/proc/proc_sysctl.c: fix potential page fault while unregistering sysctl table x86/mm: Do not forbid _PAGE_RW before init for __ro_after_init x86/pgtable: Don't set huge PUD/PMD on non-leaf entries Btrfs: fix loss of prealloc extents past i_size after fsync log replay Btrfs: clean up resources during umount after trans is aborted nvme: don't send keep-alives to the discovery controller firmware: dmi_scan: Fix UUID length safety check sh: fix debug trap failure to process signals before return to user net: mvneta: fix enable of all initialized RXQs vlan: Fix vlan insertion for packets without ethernet header net: Fix untag for vlan packets without ethernet header qede: Do not drop rx-checksum invalidated packets. hv_netvsc: enable multicast if necessary mm/kmemleak.c: wait for scan completion before disabling free mm/vmstat.c: fix vmstat_update() preemption BUG mm/page_owner: fix recursion bug after changing skip entries mm, slab: memcg_link the SLAB's kmem_cache qede: Fix barrier usage after tx doorbell write. builddeb: Fix header package regarding dtc source links llc: properly handle dev_queue_xmit() return value x86/alternatives: Fixup alternative_call_2 perf/x86/intel: Fix linear IP of PEBS real_ip on Haswell and later CPUs net/mlx5: Make eswitch support to depend on switchdev net: dsa: mt7530: fix module autoloading for OF platform drivers bonding: fix the err path for dev hwaddr sync in bond_enslave net: qmi_wwan: add BroadMobi BM806U 2020:2033 lan78xx: Set ASD in MAC_CR when EEE is enabled. ARM: 8748/1: mm: Define vdso_start, vdso_end as array batman-adv: fix packet loss for broadcasted DHCP packets to a server batman-adv: fix multicast-via-unicast transmission with AP isolation drm/amdkfd: Fix scratch memory with HWS enabled selftests: ftrace: Add a testcase for probepoint selftests: ftrace: Add a testcase for string type with kprobe_event selftests: ftrace: Add probe event argument syntax testcase xfrm: Fix transport mode skb control buffer usage. mm, thp: do not cause memcg oom for thp mm/mempolicy.c: avoid use uninitialized preferred_node drm/ast: Fixed 1280x800 Display Issue net: dsa: Fix functional dsa-loop dependency on FIXED_PHY net/sched: fix idr leak in the error path of tcf_skbmod_init() net/sched: fix idr leak in the error path of __tcf_ipt_init() net/sched: fix idr leak in the error path of tcp_pedit_init() net/sched: fix idr leak in the error path of tcf_act_police_init() net/sched: fix idr leak in the error path of tcf_simp_init() net/sched: fix idr leak on the error path of tcf_bpf_init() RDMA/qedr: Fix QP state initialization race RDMA/qedr: Fix rc initialization on CNQ allocation failure RDMA/qedr: fix QP's ack timeout configuration RDMA/ucma: Correct option size check using optlen kbuild: make scripts/adjust_autoksyms.sh robust against timestamp races brcmfmac: Fix check for ISO3166 code perf/cgroup: Fix child event counting bug drm/tegra: Shutdown on driver unbind iwlwifi: mvm: fix array out of bounds reference iwlwifi: mvm: make sure internal station has a valid id iwlwifi: mvm: clear tx queue id when unreserving aggregation queue iwlwifi: mvm: Increase session protection time after CS vti6: Fix dev->max_mtu setting vti4: Don't override MTU passed on link creation via IFLA_MTU ip_tunnel: Clamp MTU to bounds on new link vti4: Don't count header length twice on tunnel setup batman-adv: Fix skbuff rcsum on packet reroute net/sched: fix NULL dereference in the error path of tcf_sample_init() batman-adv: fix header size check in batadv_dbg_arp() vlan: Fix out of order vlan headers with reorder header off net: Fix vlan untag for bridge and vlan_dev with reorder_hdr off iwlwifi: mvm: fix error checking for multi/broadcast sta iwlwifi: mvm: Correctly set IGTK for AP iwlwifi: mvm: set the correct tid when we flush the MCAST sta xfrm: fix rcu_read_unlock usage in xfrm_local_error drm/nouveau/bl: fix backlight regression drm/imx: move arming of the vblank event to atomic_flush gpu: ipu-v3: prg: avoid possible array underflow KVM: arm/arm64: vgic: Add missing irq_lock to vgic_mmio_read_pending sunvnet: does not support GSO for sctp ipv4: lock mtu in fnhe when received PMTU < net.ipv4.route.min_pmtu workqueue: use put_device() instead of kfree() bnxt_en: Check valid VNIC ID in bnxt_hwrm_vnic_set_tpa(). can: m_can: select pinctrl state in each suspend/resume function can: m_can: change comparison to bitshift when dealing with a mask netfilter: ebtables: fix erroneous reject of last rule dmaengine: mv_xor_v2: Fix clock resource by adding a register clock lib/test_kmod.c: fix limit check on number of test devices created selftests/vm/run_vmtests: adjust hugetlb size according to nr_cpus arm64: Relax ARM_SMCCC_ARCH_WORKAROUND_1 discovery ARM: davinci: fix the GPIO lookup for omapl138-hawk hv_netvsc: fix locking during VF setup hv_netvsc: fix locking for rx_mode hv_netvsc: fix filter flags xen: xenbus: use put_device() instead of kfree() xen-blkfront: move negotiate_mq to cover all cases of new VBDs cxgb4: do not set needs_free_netdev for mgmt dev's IB/core: Fix possible crash to access NULL netdev net: smsc911x: Fix unload crash when link is up net: qcom/emac: Use proper free methods during TX qed: Free RoCE ILT Memory on rmmod qedr fsl/fman: avoid sleeping in atomic context while adding an address fbdev: Fixing arbitrary kernel leak in case FBIOGETCMAP_SPARC in sbusfb_ioctl_helper(). IB/mlx5: Fix an error code in __mlx5_ib_modify_qp() IB/mlx4: Include GID type when deleting GIDs from HW table under RoCE IB/mlx4: Fix corruption of RoCEv2 IPv4 GIDs RDMA/qedr: Fix iWARP write and send with immediate RDMA/qedr: Fix kernel panic when running fio over NFSoRDMA ia64/err-inject: Use get_user_pages_fast() e1000e: allocate ring descriptors with dma_zalloc_coherent e1000e: Fix check_for_link return value with autoneg off perf record: Fix crash in pipe mode ARM: dts: rockchip: Add missing #sound-dai-cells on rk3288 hv_netvsc: propagate rx filters to VF hv_netvsc: filter multicast/broadcast hv_netvsc: use napi_schedule_irqoff batman-adv: Fix multicast packet loss with a single WANT_ALL_IPV4/6 flag watchdog: sbsa: use 32-bit read for WCV watchdog: f71808e_wdt: Fix magic close handling rds: Incorrect reference counting in TCP socket creation iwlwifi: mvm: Correctly set the tid for mcast queue iwlwifi: mvm: Direct multicast frames to the correct station iwlwifi: mvm: fix "failed to remove key" message iwlwifi: avoid collecting firmware dump if not loaded iwlwifi: mvm: fix assert 0x2B00 on older FWs iwlwifi: mvm: Fix channel switch for count 0 and 1 iwlwifi: mvm: fix TX of CCMP 256 net: ethtool: don't ignore return from driver get_fecparam method selftests/powerpc: Skip the subpage_prot tests if the syscall is unavailable nvme: pci: pass max vectors as num_possible_cpus() to pci_alloc_irq_vectors nvme-pci: Fix EEH failure on ppc block: display the correct diskname for bio ceph: fix potential memory leak in init_caches() Btrfs: fix log replay failure after linking special file and fsync Btrfs: send, fix issuing write op when processing hole in no data mode btrfs: use kvzalloc to allocate btrfs_fs_info drm/sun4i: Fix dclk_set_phase arm64: dts: rockchip: Fix rk3399-gru-* s2r (pinctrl hogs, wifi reset) xfrm: Fix ESN sequence number handling for IPsec GSO packets. drm/amd/amdgpu: Correct VRAM width for APUs with GMC9 xen/pirq: fix error path cleanup when binding MSIs RDMA/bnxt_re: Fix the ib_reg failure cleanup RDMA/bnxt_re: Fix incorrect DB offset calculation RDMA/bnxt_re: Unconditionly fence non wire memory operations IB/mlx: Set slid to zero in Ethernet completion struct ipvs: remove IPS_NAT_MASK check to fix passive FTP ARC: setup cpu possible mask according to possible-cpus dts property ARC: mcip: update MCIP debug mask when the new cpu came online ARC: mcip: halt GFRC counter when ARC cores halt spectrum: Reference count VLAN entries mlxsw: spectrum: Treat IPv6 unregistered multicast as broadcast mlxsw: core: Fix flex keys scratchpad offset conflict net/smc: use link_id of server in confirm link reply nvmet: fix PSDT field check in command format net/tcp/illinois: replace broken algorithm reference link gianfar: Fix Rx byte accounting for ndev stats clocksource/drivers/mips-gic-timer: Use correct shift count to extract data powerpc/boot: Fix random libfdt related build errors ARM: dts: bcm283x: Fix unit address of local_intc ARM: dts: NSP: Fix amount of RAM on BCM958625HR nbd: fix return value in error handling path sit: fix IFLA_MTU ignored on NEWLINK ip6_tunnel: fix IFLA_MTU ignored on NEWLINK ip_gre: fix IFLA_MTU ignored on NEWLINK bcache: fix kcrashes with fio in RAID5 backend dev dmaengine: rcar-dmac: fix max_chunk_size for R-Car Gen3 virtio-gpu: fix ioctl and expose the fixed status to userspace. r8152: fix tx packets accounting selftests/futex: Fix line continuation in Makefile qrtr: add MODULE_ALIAS macro to smd ARM: orion5x: Revert commit 4904dbda41c8. xen/pvcalls: fix null pointer dereference on map->sock ceph: fix dentry leak when failing to init debugfs libceph, ceph: avoid memory leak when specifying same option several times clocksource/drivers/fsl_ftm_timer: Fix error return checking nvme-pci: Fix nvme queue cleanup if IRQ setup fails batman-adv: Fix netlink dumping of BLA backbones batman-adv: Fix netlink dumping of BLA claims batman-adv: Ignore invalid batadv_v_gw during netlink send batman-adv: Ignore invalid batadv_iv_gw during netlink send netfilter: ebtables: convert BUG_ONs to WARN_ONs netfilter: ipt_CLUSTERIP: put config instead of freeing it netfilter: ipt_CLUSTERIP: put config struct if we can't increment ct refcount batman-adv: invalidate checksum on fragment reassembly batman-adv: fix packet checksum in receive path md/raid1: fix NULL pointer dereference md: fix a potential deadlock of raid5/raid10 reshape fs: dcache: Use READ_ONCE when accessing i_dir_seq fs: dcache: Avoid livelock between d_alloc_parallel and __d_add ARM: dts: imx6dl: Include correct dtsi file for Engicam i.CoreM6 DualLite/Solo RQS kvm: fix warning for CONFIG_HAVE_KVM_EVENTFD builds KVM: nVMX: Don't halt vcpu when L1 is injecting events to L2 macvlan: fix use-after-free in macvlan_common_newlink() arm64: fix unwind_frame() for filtered out fn for function graph tracing mac80211: drop frames with unexpected DS bits from fast-rx to slow path x86/topology: Update the 'cpu cores' field in /proc/cpuinfo correctly across CPU hotplug operations locking/xchg/alpha: Fix xchg() and cmpxchg() memory ordering bugs x86/intel_rdt: Fix incorrect returned value when creating rdgroup sub-directory in resctrl file system integrity/security: fix digsig.c build error with header file regulatory: add NUL to request alpha2 smsc75xx: fix smsc75xx_set_features() ARM: OMAP: Fix dmtimer init for omap1 nfs: system crashes after NFS4ERR_MOVED recovery arm64: dts: cavium: fix PCI bus dtc warnings PKCS#7: fix direct verification of SignerInfo signature selftests/bpf/test_maps: exit child process without error in ENOMEM case s390/cio: clear timer when terminating driver I/O s390/cio: fix return code after missing interrupt s390/cio: fix ccw_device_start_timeout API powerpc/bpf/jit: Fix 32-bit JIT for seccomp_data access soc: imx: gpc: de-register power domains only if initialized seccomp: add a selftest for get_metadata selftests/memfd: add run_fuse_test.sh to TEST_FILES bug.h: work around GCC PR82365 in BUG() kernel/relay.c: limit kmalloc size to KMALLOC_MAX_SIZE virtio_net: fix XDP code path in receive_small() md: raid5: avoid string overflow warning locking/xchg/alpha: Add unconditional memory barrier to cmpxchg() net/mlx5e: Return error if prio is specified when offloading eswitch vlan push ibmvnic: Check for NULL skb's in NAPI poll routine RDMA/bnxt_re: Fix system crash during load/unload RDMA/bnxt_re: Unpin SQ and RQ memory if QP create fails arm64: perf: correct PMUVer probing drm/meson: fix vsync buffer update drm/exynos: fix comparison to bitshift when dealing with a mask drm/exynos: g2d: use monotonic timestamps md raid10: fix NULL deference in handle_write_completed() gpu: ipu-v3: prg: fix device node leak in ipu_prg_lookup_by_phandle gpu: ipu-v3: pre: fix device node leak in ipu_pre_lookup_by_phandle mac80211: Fix sending ADDBA response for an ongoing session mac80211: Do not disconnect on invalid operating class cfg80211: clear wep keys after disconnection mac80211: fix calling sleeping function in atomic context mac80211: fix a possible leak of station stats mac80211: round IEEE80211_TX_STATUS_HEADROOM up to multiple of 4 xfrm: do not call rcu_read_unlock when afinfo is NULL in xfrm_get_tos s390/dasd: fix handling of internal requests md: fix md_write_start() deadlock w/o metadata devices MD: Free bioset when md_run fails rxrpc: Work around usercopy check NFC: llcp: Limit size of SDP URI iwlwifi: mvm: always init rs with 20mhz bandwidth rates iwlwifi: mvm: fix IBSS for devices that support station type API iwlwifi: mvm: fix security bug in PN checking ARM: dts: rockchip: Fix DWMMC clocks arm64: dts: rockchip: Fix DWMMC clocks IB/uverbs: Fix unbalanced unlock on error path for rdma_explicit_destroy IB/uverbs: Fix possible oops with duplicate ioctl attributes IB/uverbs: Fix method merging in uverbs_ioctl_merge xhci: workaround for AMD Promontory disabled ports wakeup tls: retrun the correct IV in getsockopt ibmvnic: Clean RX pool buffers during device close ibmvnic: Free RX socket buffer in case of adapter error ibmvnic: Wait until reset is complete to set carrier on ARM: OMAP1: clock: Fix debugfs_create_*() usage ARM: OMAP2+: Fix sar_base inititalization for HS omaps ARM: OMAP3: Fix prm wake interrupt for resume ARM: OMAP2+: timer: fix a kmemleak caused in omap_get_timer_dt selftests: memfd: add config fragment for fuse selftests: pstore: Adding config fragment CONFIG_PSTORE_RAM=m selftest/vDSO: fix O= selftests: sync: missing CFLAGS while compiling libata: Fix compile warning with ATA_DEBUG enabled arm64: dts: rockchip: correct ep-gpios for rk3399-sapphire arm64: dts: rockchip: fix rock64 gmac2io stability issues ptr_ring: prevent integer overflow when calculating size ARC: Fix malformed ARC_EMUL_UNALIGNED default mac80211: mesh: fix wrong mesh TTL offset calculation MIPS: generic: Fix machine compatible matching powerpc/64s: Add support for a store forwarding barrier at kernel entry/exit powerpc/64s: Fix section mismatch warnings from setup_rfi_flush() powerpc/pseries: Restore default security feature flags on setup powerpc: Move default security feature flags powerpc/pseries: Fix clearing of security feature flags powerpc/64s: Wire up cpu_show_spectre_v2() powerpc/64s: Wire up cpu_show_spectre_v1() powerpc/pseries: Use the security flags in pseries_setup_rfi_flush() powerpc/powernv: Use the security flags in pnv_setup_rfi_flush() powerpc/64s: Enhance the information in cpu_show_meltdown() powerpc/64s: Move cpu_show_meltdown() powerpc/powernv: Set or clear security feature flags powerpc/pseries: Set or clear security feature flags powerpc: Add security feature flags for Spectre/Meltdown powerpc/pseries: Add new H_GET_CPU_CHARACTERISTICS flags powerpc/rfi-flush: Call setup_rfi_flush() after LPM migration powerpc/rfi-flush: Differentiate enabled and patched flush types powerpc/rfi-flush: Always enable fallback flush on pseries powerpc/rfi-flush: Make it possible to call setup_rfi_flush() again powerpc/rfi-flush: Move the logic to avoid a redo into the debugfs code powerpc/powernv: Support firmware disable of RFI flush powerpc/pseries: Support firmware disable of RFI flush powerpc/64s: Improve RFI L1-D cache flush fallback x86/kvm: fix LAPIC timer drift when guest uses periodic mode kvm: x86: IA32_ARCH_CAPABILITIES is always supported KVM: x86: Update cpuid properly when CR4.OSXAVE or CR4.PKE is changed KVM: s390: vsie: fix < 8k check for the itdba KVM/VMX: Expose SSBD properly to guests kernel/sys.c: fix potential Spectre v1 issue kasan: fix memory hotplug during boot kasan: free allocated shadow memory on MEM_CANCEL_ONLINE mm/kasan: don't vfree() nonexistent vm_area ipc/shm: fix shmat() nil address after round-down when remapping Revert "ipc/shm: Fix shmat mmap nil-page protection" idr: fix invalid ptr dereference on item delete sr: pass down correctly sized SCSI sense buffer IB/umem: Use the correct mm during ib_umem_release IB/hfi1: Use after free race condition in send context error path powerpc/64s: Clear PCR on boot arm64: lse: Add early clobbers to some input/output asm operands drm/vmwgfx: Fix 32-bit VMW_PORT_HB_[IN|OUT] macros xen-swiotlb: fix the check condition for xen_swiotlb_free_coherent libata: blacklist Micron 500IT SSD with MU01 firmware libata: Blacklist some Sandisk SSDs for NCQ mmc: sdhci-iproc: add SDHCI_QUIRK2_HOST_OFF_CARD_ON for cygnus mmc: sdhci-iproc: fix 32bit writes for TRANSFER_MODE register mmc: sdhci-iproc: remove hard coded mmc cap 1.8v do d_instantiate/unlock_new_inode combinations safely ALSA: timer: Fix pause event notification aio: fix io_destroy(2) vs. lookup_ioctx() race fs: don't scan the inode cache before SB_BORN is set affs_lookup(): close a race with affs_remove_link() KVM: Fix spelling mistake: "cop_unsuable" -> "cop_unusable" MIPS: Fix ptrace(2) PTRACE_PEEKUSR and PTRACE_POKEUSR accesses to o32 FGRs MIPS: ptrace: Expose FIR register through FP regset MIPS: c-r4k: Fix data corruption related to cache coherence UPSTREAM: sched/fair: Consider RT/IRQ pressure in capacity_spare_wake BACKPORT, FROMLIST: fscrypt: add Speck128/256 support Change-Id: I64e5327b80b23c1ef79abed4b67bdb6a5684ec43 Signed-off-by: Isaac J. Manjarres <isaacm@codeaurora.org>
648 lines
15 KiB
C
648 lines
15 KiB
C
// SPDX-License-Identifier: GPL-2.0
|
|
#include <linux/debugfs.h>
|
|
#include <linux/mm.h>
|
|
#include <linux/slab.h>
|
|
#include <linux/uaccess.h>
|
|
#include <linux/bootmem.h>
|
|
#include <linux/stacktrace.h>
|
|
#include <linux/page_owner.h>
|
|
#include <linux/jump_label.h>
|
|
#include <linux/migrate.h>
|
|
#include <linux/stackdepot.h>
|
|
#include <linux/seq_file.h>
|
|
|
|
#include "internal.h"
|
|
|
|
/*
|
|
* TODO: teach PAGE_OWNER_STACK_DEPTH (__dump_page_owner and save_stack)
|
|
* to use off stack temporal storage
|
|
*/
|
|
#define PAGE_OWNER_STACK_DEPTH (16)
|
|
|
|
struct page_owner {
|
|
unsigned int order;
|
|
gfp_t gfp_mask;
|
|
int last_migrate_reason;
|
|
depot_stack_handle_t handle;
|
|
};
|
|
|
|
static bool page_owner_disabled =
|
|
!IS_ENABLED(CONFIG_PAGE_OWNER_ENABLE_DEFAULT);
|
|
DEFINE_STATIC_KEY_FALSE(page_owner_inited);
|
|
|
|
static depot_stack_handle_t dummy_handle;
|
|
static depot_stack_handle_t failure_handle;
|
|
static depot_stack_handle_t early_handle;
|
|
|
|
static void init_early_allocated_pages(void);
|
|
|
|
static int early_page_owner_param(char *buf)
|
|
{
|
|
if (!buf)
|
|
return -EINVAL;
|
|
|
|
if (strcmp(buf, "on") == 0)
|
|
page_owner_disabled = false;
|
|
|
|
if (strcmp(buf, "off") == 0)
|
|
page_owner_disabled = true;
|
|
|
|
return 0;
|
|
}
|
|
early_param("page_owner", early_page_owner_param);
|
|
|
|
static bool need_page_owner(void)
|
|
{
|
|
if (page_owner_disabled)
|
|
return false;
|
|
|
|
return true;
|
|
}
|
|
|
|
static __always_inline depot_stack_handle_t create_dummy_stack(void)
|
|
{
|
|
unsigned long entries[4];
|
|
struct stack_trace dummy;
|
|
|
|
dummy.nr_entries = 0;
|
|
dummy.max_entries = ARRAY_SIZE(entries);
|
|
dummy.entries = &entries[0];
|
|
dummy.skip = 0;
|
|
|
|
save_stack_trace(&dummy);
|
|
return depot_save_stack(&dummy, GFP_KERNEL);
|
|
}
|
|
|
|
static noinline void register_dummy_stack(void)
|
|
{
|
|
dummy_handle = create_dummy_stack();
|
|
}
|
|
|
|
static noinline void register_failure_stack(void)
|
|
{
|
|
failure_handle = create_dummy_stack();
|
|
}
|
|
|
|
static noinline void register_early_stack(void)
|
|
{
|
|
early_handle = create_dummy_stack();
|
|
}
|
|
|
|
static void init_page_owner(void)
|
|
{
|
|
if (page_owner_disabled)
|
|
return;
|
|
|
|
register_dummy_stack();
|
|
register_failure_stack();
|
|
register_early_stack();
|
|
static_branch_enable(&page_owner_inited);
|
|
init_early_allocated_pages();
|
|
}
|
|
|
|
struct page_ext_operations page_owner_ops = {
|
|
.size = sizeof(struct page_owner),
|
|
.need = need_page_owner,
|
|
.init = init_page_owner,
|
|
};
|
|
|
|
static inline struct page_owner *get_page_owner(struct page_ext *page_ext)
|
|
{
|
|
return (void *)page_ext + page_owner_ops.offset;
|
|
}
|
|
|
|
void __reset_page_owner(struct page *page, unsigned int order)
|
|
{
|
|
int i;
|
|
struct page_ext *page_ext;
|
|
|
|
for (i = 0; i < (1 << order); i++) {
|
|
page_ext = lookup_page_ext(page + i);
|
|
if (unlikely(!page_ext))
|
|
continue;
|
|
__clear_bit(PAGE_EXT_OWNER, &page_ext->flags);
|
|
}
|
|
}
|
|
|
|
static inline bool check_recursive_alloc(struct stack_trace *trace,
|
|
unsigned long ip)
|
|
{
|
|
int i;
|
|
|
|
if (!trace->nr_entries)
|
|
return false;
|
|
|
|
for (i = 0; i < trace->nr_entries; i++) {
|
|
if (trace->entries[i] == ip)
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
static noinline depot_stack_handle_t save_stack(gfp_t flags)
|
|
{
|
|
unsigned long entries[PAGE_OWNER_STACK_DEPTH];
|
|
struct stack_trace trace = {
|
|
.nr_entries = 0,
|
|
.entries = entries,
|
|
.max_entries = PAGE_OWNER_STACK_DEPTH,
|
|
.skip = 2
|
|
};
|
|
depot_stack_handle_t handle;
|
|
|
|
save_stack_trace(&trace);
|
|
if (trace.nr_entries != 0 &&
|
|
trace.entries[trace.nr_entries-1] == ULONG_MAX)
|
|
trace.nr_entries--;
|
|
|
|
/*
|
|
* We need to check recursion here because our request to stackdepot
|
|
* could trigger memory allocation to save new entry. New memory
|
|
* allocation would reach here and call depot_save_stack() again
|
|
* if we don't catch it. There is still not enough memory in stackdepot
|
|
* so it would try to allocate memory again and loop forever.
|
|
*/
|
|
if (check_recursive_alloc(&trace, _RET_IP_))
|
|
return dummy_handle;
|
|
|
|
handle = depot_save_stack(&trace, flags);
|
|
if (!handle)
|
|
handle = failure_handle;
|
|
|
|
return handle;
|
|
}
|
|
|
|
static inline void __set_page_owner_handle(struct page_ext *page_ext,
|
|
depot_stack_handle_t handle, unsigned int order, gfp_t gfp_mask)
|
|
{
|
|
struct page_owner *page_owner;
|
|
|
|
page_owner = get_page_owner(page_ext);
|
|
page_owner->handle = handle;
|
|
page_owner->order = order;
|
|
page_owner->gfp_mask = gfp_mask;
|
|
page_owner->last_migrate_reason = -1;
|
|
|
|
__set_bit(PAGE_EXT_OWNER, &page_ext->flags);
|
|
}
|
|
|
|
noinline void __set_page_owner(struct page *page, unsigned int order,
|
|
gfp_t gfp_mask)
|
|
{
|
|
struct page_ext *page_ext = lookup_page_ext(page);
|
|
depot_stack_handle_t handle;
|
|
|
|
if (unlikely(!page_ext))
|
|
return;
|
|
|
|
handle = save_stack(gfp_mask);
|
|
__set_page_owner_handle(page_ext, handle, order, gfp_mask);
|
|
}
|
|
|
|
void __set_page_owner_migrate_reason(struct page *page, int reason)
|
|
{
|
|
struct page_ext *page_ext = lookup_page_ext(page);
|
|
struct page_owner *page_owner;
|
|
|
|
if (unlikely(!page_ext))
|
|
return;
|
|
|
|
page_owner = get_page_owner(page_ext);
|
|
page_owner->last_migrate_reason = reason;
|
|
}
|
|
|
|
void __split_page_owner(struct page *page, unsigned int order)
|
|
{
|
|
int i;
|
|
struct page_ext *page_ext = lookup_page_ext(page);
|
|
struct page_owner *page_owner;
|
|
|
|
if (unlikely(!page_ext))
|
|
return;
|
|
|
|
page_owner = get_page_owner(page_ext);
|
|
page_owner->order = 0;
|
|
for (i = 1; i < (1 << order); i++)
|
|
__copy_page_owner(page, page + i);
|
|
}
|
|
|
|
void __copy_page_owner(struct page *oldpage, struct page *newpage)
|
|
{
|
|
struct page_ext *old_ext = lookup_page_ext(oldpage);
|
|
struct page_ext *new_ext = lookup_page_ext(newpage);
|
|
struct page_owner *old_page_owner, *new_page_owner;
|
|
|
|
if (unlikely(!old_ext || !new_ext))
|
|
return;
|
|
|
|
old_page_owner = get_page_owner(old_ext);
|
|
new_page_owner = get_page_owner(new_ext);
|
|
new_page_owner->order = old_page_owner->order;
|
|
new_page_owner->gfp_mask = old_page_owner->gfp_mask;
|
|
new_page_owner->last_migrate_reason =
|
|
old_page_owner->last_migrate_reason;
|
|
new_page_owner->handle = old_page_owner->handle;
|
|
|
|
/*
|
|
* We don't clear the bit on the oldpage as it's going to be freed
|
|
* after migration. Until then, the info can be useful in case of
|
|
* a bug, and the overal stats will be off a bit only temporarily.
|
|
* Also, migrate_misplaced_transhuge_page() can still fail the
|
|
* migration and then we want the oldpage to retain the info. But
|
|
* in that case we also don't need to explicitly clear the info from
|
|
* the new page, which will be freed.
|
|
*/
|
|
__set_bit(PAGE_EXT_OWNER, &new_ext->flags);
|
|
}
|
|
|
|
void pagetypeinfo_showmixedcount_print(struct seq_file *m,
|
|
pg_data_t *pgdat, struct zone *zone)
|
|
{
|
|
struct page *page;
|
|
struct page_ext *page_ext;
|
|
struct page_owner *page_owner;
|
|
unsigned long pfn = zone->zone_start_pfn, block_end_pfn;
|
|
unsigned long end_pfn = pfn + zone->spanned_pages;
|
|
unsigned long count[MIGRATE_TYPES] = { 0, };
|
|
int pageblock_mt, page_mt;
|
|
int i;
|
|
|
|
/* Scan block by block. First and last block may be incomplete */
|
|
pfn = zone->zone_start_pfn;
|
|
|
|
/*
|
|
* Walk the zone in pageblock_nr_pages steps. If a page block spans
|
|
* a zone boundary, it will be double counted between zones. This does
|
|
* not matter as the mixed block count will still be correct
|
|
*/
|
|
for (; pfn < end_pfn; ) {
|
|
if (!pfn_valid(pfn)) {
|
|
pfn = ALIGN(pfn + 1, MAX_ORDER_NR_PAGES);
|
|
continue;
|
|
}
|
|
|
|
block_end_pfn = ALIGN(pfn + 1, pageblock_nr_pages);
|
|
block_end_pfn = min(block_end_pfn, end_pfn);
|
|
|
|
page = pfn_to_page(pfn);
|
|
pageblock_mt = get_pageblock_migratetype(page);
|
|
|
|
for (; pfn < block_end_pfn; pfn++) {
|
|
if (!pfn_valid_within(pfn))
|
|
continue;
|
|
|
|
page = pfn_to_page(pfn);
|
|
|
|
if (page_zone(page) != zone)
|
|
continue;
|
|
|
|
if (PageBuddy(page)) {
|
|
unsigned long freepage_order;
|
|
|
|
freepage_order = page_order_unsafe(page);
|
|
if (freepage_order < MAX_ORDER)
|
|
pfn += (1UL << freepage_order) - 1;
|
|
continue;
|
|
}
|
|
|
|
if (PageReserved(page))
|
|
continue;
|
|
|
|
page_ext = lookup_page_ext(page);
|
|
if (unlikely(!page_ext))
|
|
continue;
|
|
|
|
if (!test_bit(PAGE_EXT_OWNER, &page_ext->flags))
|
|
continue;
|
|
|
|
page_owner = get_page_owner(page_ext);
|
|
page_mt = gfpflags_to_migratetype(
|
|
page_owner->gfp_mask);
|
|
if (pageblock_mt != page_mt) {
|
|
if (is_migrate_cma(pageblock_mt))
|
|
count[MIGRATE_MOVABLE]++;
|
|
else
|
|
count[pageblock_mt]++;
|
|
|
|
pfn = block_end_pfn;
|
|
break;
|
|
}
|
|
pfn += (1UL << page_owner->order) - 1;
|
|
}
|
|
}
|
|
|
|
/* Print counts */
|
|
seq_printf(m, "Node %d, zone %8s ", pgdat->node_id, zone->name);
|
|
for (i = 0; i < MIGRATE_TYPES; i++)
|
|
seq_printf(m, "%12lu ", count[i]);
|
|
seq_putc(m, '\n');
|
|
}
|
|
|
|
static ssize_t
|
|
print_page_owner(char __user *buf, size_t count, unsigned long pfn,
|
|
struct page *page, struct page_owner *page_owner,
|
|
depot_stack_handle_t handle)
|
|
{
|
|
int ret;
|
|
int pageblock_mt, page_mt;
|
|
char *kbuf;
|
|
unsigned long entries[PAGE_OWNER_STACK_DEPTH];
|
|
struct stack_trace trace = {
|
|
.nr_entries = 0,
|
|
.entries = entries,
|
|
.max_entries = PAGE_OWNER_STACK_DEPTH,
|
|
.skip = 0
|
|
};
|
|
|
|
kbuf = kmalloc(count, GFP_KERNEL);
|
|
if (!kbuf)
|
|
return -ENOMEM;
|
|
|
|
ret = snprintf(kbuf, count,
|
|
"Page allocated via order %u, mask %#x(%pGg)\n",
|
|
page_owner->order, page_owner->gfp_mask,
|
|
&page_owner->gfp_mask);
|
|
|
|
if (ret >= count)
|
|
goto err;
|
|
|
|
/* Print information relevant to grouping pages by mobility */
|
|
pageblock_mt = get_pageblock_migratetype(page);
|
|
page_mt = gfpflags_to_migratetype(page_owner->gfp_mask);
|
|
ret += snprintf(kbuf + ret, count - ret,
|
|
"PFN %lu type %s Block %lu type %s Flags %#lx(%pGp)\n",
|
|
pfn,
|
|
migratetype_names[page_mt],
|
|
pfn >> pageblock_order,
|
|
migratetype_names[pageblock_mt],
|
|
page->flags, &page->flags);
|
|
|
|
if (ret >= count)
|
|
goto err;
|
|
|
|
depot_fetch_stack(handle, &trace);
|
|
ret += snprint_stack_trace(kbuf + ret, count - ret, &trace, 0);
|
|
if (ret >= count)
|
|
goto err;
|
|
|
|
if (page_owner->last_migrate_reason != -1) {
|
|
ret += snprintf(kbuf + ret, count - ret,
|
|
"Page has been migrated, last migrate reason: %s\n",
|
|
migrate_reason_names[page_owner->last_migrate_reason]);
|
|
if (ret >= count)
|
|
goto err;
|
|
}
|
|
|
|
ret += snprintf(kbuf + ret, count - ret, "\n");
|
|
if (ret >= count)
|
|
goto err;
|
|
|
|
if (copy_to_user(buf, kbuf, ret))
|
|
ret = -EFAULT;
|
|
|
|
kfree(kbuf);
|
|
return ret;
|
|
|
|
err:
|
|
kfree(kbuf);
|
|
return -ENOMEM;
|
|
}
|
|
|
|
void __dump_page_owner(struct page *page)
|
|
{
|
|
struct page_ext *page_ext = lookup_page_ext(page);
|
|
struct page_owner *page_owner;
|
|
unsigned long entries[PAGE_OWNER_STACK_DEPTH];
|
|
struct stack_trace trace = {
|
|
.nr_entries = 0,
|
|
.entries = entries,
|
|
.max_entries = PAGE_OWNER_STACK_DEPTH,
|
|
.skip = 0
|
|
};
|
|
depot_stack_handle_t handle;
|
|
gfp_t gfp_mask;
|
|
int mt;
|
|
|
|
if (unlikely(!page_ext)) {
|
|
pr_alert("There is not page extension available.\n");
|
|
return;
|
|
}
|
|
|
|
page_owner = get_page_owner(page_ext);
|
|
gfp_mask = page_owner->gfp_mask;
|
|
mt = gfpflags_to_migratetype(gfp_mask);
|
|
|
|
if (!test_bit(PAGE_EXT_OWNER, &page_ext->flags)) {
|
|
pr_alert("page_owner info is not active (free page?)\n");
|
|
return;
|
|
}
|
|
|
|
handle = READ_ONCE(page_owner->handle);
|
|
if (!handle) {
|
|
pr_alert("page_owner info is not active (free page?)\n");
|
|
return;
|
|
}
|
|
|
|
depot_fetch_stack(handle, &trace);
|
|
pr_alert("page allocated via order %u, migratetype %s, gfp_mask %#x(%pGg)\n",
|
|
page_owner->order, migratetype_names[mt], gfp_mask, &gfp_mask);
|
|
print_stack_trace(&trace, 0);
|
|
|
|
if (page_owner->last_migrate_reason != -1)
|
|
pr_alert("page has been migrated, last migrate reason: %s\n",
|
|
migrate_reason_names[page_owner->last_migrate_reason]);
|
|
}
|
|
|
|
static ssize_t
|
|
read_page_owner(struct file *file, char __user *buf, size_t count, loff_t *ppos)
|
|
{
|
|
unsigned long pfn;
|
|
struct page *page;
|
|
struct page_ext *page_ext;
|
|
struct page_owner *page_owner;
|
|
depot_stack_handle_t handle;
|
|
|
|
if (!static_branch_unlikely(&page_owner_inited))
|
|
return -EINVAL;
|
|
|
|
page = NULL;
|
|
pfn = min_low_pfn + *ppos;
|
|
|
|
/* Find a valid PFN or the start of a MAX_ORDER_NR_PAGES area */
|
|
while (!pfn_valid(pfn) && (pfn & (MAX_ORDER_NR_PAGES - 1)) != 0)
|
|
pfn++;
|
|
|
|
drain_all_pages(NULL);
|
|
|
|
/* Find an allocated page */
|
|
for (; pfn < max_pfn; pfn++) {
|
|
/*
|
|
* If the new page is in a new MAX_ORDER_NR_PAGES area,
|
|
* validate the area as existing, skip it if not
|
|
*/
|
|
if ((pfn & (MAX_ORDER_NR_PAGES - 1)) == 0 && !pfn_valid(pfn)) {
|
|
pfn += MAX_ORDER_NR_PAGES - 1;
|
|
continue;
|
|
}
|
|
|
|
/* Check for holes within a MAX_ORDER area */
|
|
if (!pfn_valid_within(pfn))
|
|
continue;
|
|
|
|
page = pfn_to_page(pfn);
|
|
if (PageBuddy(page)) {
|
|
unsigned long freepage_order = page_order_unsafe(page);
|
|
|
|
if (freepage_order < MAX_ORDER)
|
|
pfn += (1UL << freepage_order) - 1;
|
|
continue;
|
|
}
|
|
|
|
page_ext = lookup_page_ext(page);
|
|
if (unlikely(!page_ext))
|
|
continue;
|
|
|
|
/*
|
|
* Some pages could be missed by concurrent allocation or free,
|
|
* because we don't hold the zone lock.
|
|
*/
|
|
if (!test_bit(PAGE_EXT_OWNER, &page_ext->flags))
|
|
continue;
|
|
|
|
page_owner = get_page_owner(page_ext);
|
|
|
|
/*
|
|
* Access to page_ext->handle isn't synchronous so we should
|
|
* be careful to access it.
|
|
*/
|
|
handle = READ_ONCE(page_owner->handle);
|
|
if (!handle)
|
|
continue;
|
|
|
|
/* Record the next PFN to read in the file offset */
|
|
*ppos = (pfn - min_low_pfn) + 1;
|
|
|
|
return print_page_owner(buf, count, pfn, page,
|
|
page_owner, handle);
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
static void init_pages_in_zone(pg_data_t *pgdat, struct zone *zone)
|
|
{
|
|
struct page *page;
|
|
struct page_ext *page_ext;
|
|
unsigned long pfn = zone->zone_start_pfn, block_end_pfn;
|
|
unsigned long end_pfn = pfn + zone->spanned_pages;
|
|
unsigned long count = 0;
|
|
|
|
/* Scan block by block. First and last block may be incomplete */
|
|
pfn = zone->zone_start_pfn;
|
|
|
|
/*
|
|
* Walk the zone in pageblock_nr_pages steps. If a page block spans
|
|
* a zone boundary, it will be double counted between zones. This does
|
|
* not matter as the mixed block count will still be correct
|
|
*/
|
|
for (; pfn < end_pfn; ) {
|
|
if (!pfn_valid(pfn)) {
|
|
pfn = ALIGN(pfn + 1, MAX_ORDER_NR_PAGES);
|
|
continue;
|
|
}
|
|
|
|
block_end_pfn = ALIGN(pfn + 1, pageblock_nr_pages);
|
|
block_end_pfn = min(block_end_pfn, end_pfn);
|
|
|
|
page = pfn_to_page(pfn);
|
|
|
|
for (; pfn < block_end_pfn; pfn++) {
|
|
if (!pfn_valid_within(pfn))
|
|
continue;
|
|
|
|
page = pfn_to_page(pfn);
|
|
|
|
if (page_zone(page) != zone)
|
|
continue;
|
|
|
|
/*
|
|
* To avoid having to grab zone->lock, be a little
|
|
* careful when reading buddy page order. The only
|
|
* danger is that we skip too much and potentially miss
|
|
* some early allocated pages, which is better than
|
|
* heavy lock contention.
|
|
*/
|
|
if (PageBuddy(page)) {
|
|
unsigned long order = page_order_unsafe(page);
|
|
|
|
if (order > 0 && order < MAX_ORDER)
|
|
pfn += (1UL << order) - 1;
|
|
continue;
|
|
}
|
|
|
|
if (PageReserved(page))
|
|
continue;
|
|
|
|
page_ext = lookup_page_ext(page);
|
|
if (unlikely(!page_ext))
|
|
continue;
|
|
|
|
/* Maybe overlapping zone */
|
|
if (test_bit(PAGE_EXT_OWNER, &page_ext->flags))
|
|
continue;
|
|
|
|
/* Found early allocated page */
|
|
__set_page_owner_handle(page_ext, early_handle, 0, 0);
|
|
count++;
|
|
}
|
|
cond_resched();
|
|
}
|
|
|
|
pr_info("Node %d, zone %8s: page owner found early allocated %lu pages\n",
|
|
pgdat->node_id, zone->name, count);
|
|
}
|
|
|
|
static void init_zones_in_node(pg_data_t *pgdat)
|
|
{
|
|
struct zone *zone;
|
|
struct zone *node_zones = pgdat->node_zones;
|
|
|
|
for (zone = node_zones; zone - node_zones < MAX_NR_ZONES; ++zone) {
|
|
if (!populated_zone(zone))
|
|
continue;
|
|
|
|
init_pages_in_zone(pgdat, zone);
|
|
}
|
|
}
|
|
|
|
static void init_early_allocated_pages(void)
|
|
{
|
|
pg_data_t *pgdat;
|
|
|
|
for_each_online_pgdat(pgdat)
|
|
init_zones_in_node(pgdat);
|
|
}
|
|
|
|
static const struct file_operations proc_page_owner_operations = {
|
|
.read = read_page_owner,
|
|
};
|
|
|
|
static int __init pageowner_init(void)
|
|
{
|
|
struct dentry *dentry;
|
|
|
|
if (!static_branch_unlikely(&page_owner_inited)) {
|
|
pr_info("page_owner is disabled\n");
|
|
return 0;
|
|
}
|
|
|
|
dentry = debugfs_create_file("page_owner", S_IRUSR, NULL,
|
|
NULL, &proc_page_owner_operations);
|
|
if (IS_ERR(dentry))
|
|
return PTR_ERR(dentry);
|
|
|
|
return 0;
|
|
}
|
|
late_initcall(pageowner_init)
|