[PATCH v6 1/2] depmod: Handle installing modules under a different directory
Some distributions aim at shipping all files in /usr. The path under which kernel modules are installed is hardcoded to /lib which conflicts with this goal. When kmod provides kmod.pc, use it to determine the correct module installation path. With kmod that does not provide the config /lib/modules is used as before. While pkg-config does not return an error when a variable does not exist the kmod configure script puts some effort into ensuring that module_directory is non-empty. With that empty module_directory from pkg-config can be used to detect absence of the variable. Signed-off-by: Michal Suchanek --- v6: - use ?= instead of := to make it easier to override the value - use shorter expression for determining the module directory assuming it's non-empty --- Makefile | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/Makefile b/Makefile index 511b5616aa41..84f32bd563d4 100644 --- a/Makefile +++ b/Makefile @@ -1081,7 +1081,9 @@ export INSTALL_DTBS_PATH ?= $(INSTALL_PATH)/dtbs/$(KERNELRELEASE) # makefile but the argument can be passed to make if needed. # -MODLIB = $(INSTALL_MOD_PATH)/lib/modules/$(KERNELRELEASE) +export KERNEL_MODULE_DIRECTORY ?= $(or $(shell pkg-config --variable=module_directory kmod 2>/dev/null),/lib/modules) + +MODLIB = $(INSTALL_MOD_PATH)$(KERNEL_MODULE_DIRECTORY)/$(KERNELRELEASE) export MODLIB PHONY += prepare0 -- 2.42.0
[PATCH v6 2/2] kbuild: rpm-pkg: Fix build with non-default MODLIB
The default MODLIB value is composed of three variables MODLIB = $(INSTALL_MOD_PATH)$(KERNEL_MODULE_DIRECTORY)/$(KERNELRELEASE) However, the kernel.spec hadcodes the default value of $(KERNEL_MODULE_DIRECTORY), and changed value is not reflected when building the package. Pass KERNEL_MODULE_DIRECTORY to kernel.spec to fix this problem. Signed-off-by: Michal Suchanek --- Build on top of the previous patch adding KERNEL_MODULE_DIRECTORY --- scripts/package/kernel.spec | 8 scripts/package/mkspec | 1 + 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/scripts/package/kernel.spec b/scripts/package/kernel.spec index 3eee0143e0c5..12996ed365f8 100644 --- a/scripts/package/kernel.spec +++ b/scripts/package/kernel.spec @@ -67,7 +67,7 @@ cp $(%{make} %{makeflags} -s image_name) %{buildroot}/boot/vmlinuz-%{KERNELRELEA %{make} %{makeflags} INSTALL_HDR_PATH=%{buildroot}/usr headers_install cp System.map %{buildroot}/boot/System.map-%{KERNELRELEASE} cp .config %{buildroot}/boot/config-%{KERNELRELEASE} -ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}/lib/modules/%{KERNELRELEASE}/build +ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}%{KERNEL_MODULE_DIRECTORY}/%{KERNELRELEASE}/build %if %{with_devel} %{make} %{makeflags} run-command KBUILD_RUN_COMMAND='${srctree}/scripts/package/install-extmod-build %{buildroot}/usr/src/kernels/%{KERNELRELEASE}' %endif @@ -98,8 +98,8 @@ fi %files %defattr (-, root, root) -/lib/modules/%{KERNELRELEASE} -%exclude /lib/modules/%{KERNELRELEASE}/build +%{KERNEL_MODULE_DIRECTORY}/%{KERNELRELEASE} +%exclude %{KERNEL_MODULE_DIRECTORY}/%{KERNELRELEASE}/build /boot/* %files headers @@ -110,5 +110,5 @@ fi %files devel %defattr (-, root, root) /usr/src/kernels/%{KERNELRELEASE} -/lib/modules/%{KERNELRELEASE}/build +%{KERNEL_MODULE_DIRECTORY}/%{KERNELRELEASE}/build %endif diff --git a/scripts/package/mkspec b/scripts/package/mkspec index ce201bfa8377..e952fa4f2937 100755 --- a/scripts/package/mkspec +++ b/scripts/package/mkspec @@ -24,6 +24,7 @@ fi cat<
[PATCH 0/2] kmod /usr support
Hello, This is resend of the last patch in the series that adds prefix support to kernel module location together with additional patch for validating the user supplied input to options that are interpreted as directories. Thanks Michal Michal Suchanek (2): libkmod, depmod, modprobe: Make directory for kernel modules configurable configure: Check that provided paths are absolute Makefile.am | 3 +- configure.ac | 24 ++ libkmod/libkmod.c| 4 +- man/Makefile.am | 1 + man/depmod.d.xml | 6 +- man/depmod.xml | 4 +- man/modinfo.xml | 2 +- man/modprobe.xml | 2 +- man/modules.dep.xml | 6 +- testsuite/module-playground/Makefile | 2 +- testsuite/setup-rootfs.sh| 109 +++ testsuite/test-depmod.c | 16 ++-- testsuite/test-testsuite.c | 8 +- tools/depmod.c | 6 +- tools/kmod.pc.in | 1 + tools/modinfo.c | 4 +- tools/modprobe.c | 4 +- tools/static-nodes.c | 6 +- 18 files changed, 124 insertions(+), 84 deletions(-) -- 2.42.0
[PATCH 1/2] libkmod, depmod, modprobe: Make directory for kernel modules configurable
Now that modprobe.d is searched under ${prefix}/lib, allow a complete transition to files only under ${prefix} by adding a ${module_directory} configuration. This specifies the directory where to search for kernel modules and should match the location where the kernel/distro installs them. With this distributions that do not want to ship files in /lib can also move kernel modules to /usr while others can keep them in /lib. Signed-off-by: Michal Suchanek --- v4: Make the whole path configurable v5: More verbose commit message v6: fix docstring still containing module_prefix --- Makefile.am | 3 +- configure.ac | 7 ++ libkmod/libkmod.c| 4 +- man/Makefile.am | 1 + man/depmod.d.xml | 6 +- man/depmod.xml | 4 +- man/modinfo.xml | 2 +- man/modprobe.xml | 2 +- man/modules.dep.xml | 6 +- testsuite/module-playground/Makefile | 2 +- testsuite/setup-rootfs.sh| 109 +++ testsuite/test-depmod.c | 16 ++-- testsuite/test-testsuite.c | 8 +- tools/depmod.c | 6 +- tools/kmod.pc.in | 1 + tools/modinfo.c | 4 +- tools/modprobe.c | 4 +- tools/static-nodes.c | 6 +- 18 files changed, 107 insertions(+), 84 deletions(-) diff --git a/Makefile.am b/Makefile.am index 2a54c25bd631..4062d81227df 100644 --- a/Makefile.am +++ b/Makefile.am @@ -20,6 +20,7 @@ AM_CPPFLAGS = \ -I$(top_srcdir) \ -DSYSCONFDIR=\""$(sysconfdir)"\" \ -DDISTCONFDIR=\""$(distconfdir)"\" \ + -DMODULE_DIRECTORY=\""$(module_directory)"\" \ ${zlib_CFLAGS} AM_CFLAGS = $(OUR_CFLAGS) @@ -220,7 +221,7 @@ EXTRA_DIST += testsuite/setup-rootfs.sh MODULE_PLAYGROUND = testsuite/module-playground ROOTFS = testsuite/rootfs ROOTFS_PRISTINE = $(top_srcdir)/testsuite/rootfs-pristine -CREATE_ROOTFS = $(AM_V_GEN) $(top_srcdir)/testsuite/setup-rootfs.sh $(ROOTFS_PRISTINE) $(ROOTFS) $(MODULE_PLAYGROUND) $(top_builddir)/config.h $(sysconfdir) +CREATE_ROOTFS = $(AM_V_GEN) MODULE_DIRECTORY=$(module_directory) $(top_srcdir)/testsuite/setup-rootfs.sh $(ROOTFS_PRISTINE) $(ROOTFS) $(MODULE_PLAYGROUND) $(top_builddir)/config.h $(sysconfdir) build-module-playground: $(AM_V_GEN)if test "$(top_srcdir)" != "$(top_builddir)"; then \ diff --git a/configure.ac b/configure.ac index a6b8fa0308b6..d6da5ee9ae9a 100644 --- a/configure.ac +++ b/configure.ac @@ -91,6 +91,12 @@ AC_ARG_WITH([rootlibdir], [], [with_rootlibdir=$libdir]) AC_SUBST([rootlibdir], [$with_rootlibdir]) +# Ideally this would be $prefix/lib/modules but default to /lib/modules for compatibility with earlier versions +AC_ARG_WITH([module_directory], +AS_HELP_STRING([--with-module-directory=DIR], [directory in which to look for kernel modules - typically '/lib/modules' or '${prefix}/lib/modules']), +[], [with_module_directory=/lib/modules]) +AC_SUBST([module_directory], [$with_module_directory]) + AC_ARG_WITH([zstd], AS_HELP_STRING([--with-zstd], [handle Zstandard-compressed modules @<:@default=disabled@:>@]), [], [with_zstd=no]) @@ -319,6 +325,7 @@ AC_MSG_RESULT([ $PACKAGE $VERSION === + module_directory: ${module_directory} prefix: ${prefix} sysconfdir: ${sysconfdir} distconfdir:${distconfdir} diff --git a/libkmod/libkmod.c b/libkmod/libkmod.c index 57fac1cb9f7b..213b42482fb6 100644 --- a/libkmod/libkmod.c +++ b/libkmod/libkmod.c @@ -210,7 +210,7 @@ static int log_priority(const char *priority) return 0; } -static const char *dirname_default_prefix = "/lib/modules"; +static const char *dirname_default_prefix = MODULE_DIRECTORY; static char *get_kernel_release(const char *dirname) { @@ -266,7 +266,7 @@ static enum kmod_file_compression_type get_kernel_compression(struct kmod_ctx *c /** * kmod_new: * @dirname: what to consider as linux module's directory, if NULL - * defaults to /lib/modules/`uname -r`. If it's relative, + * defaults to $MODULE_DIRECTORY/`uname -r`. If it's relative, * it's treated as relative to the current working directory. * Otherwise, give an absolute dirname. * @config_paths: ordered array of paths (directories or files) where diff --git a/man/Makefile.am b/man/Makefile.am index 2fea8e46bf2f..f550091a216a 100644 --- a/man/Makefile.am +++ b/man/Makefile.am @@ -22,6 +22,7 @@ CLEANFILES = $(dist_man_MANS) else \ sed -e '/@DISTCONFDIR@/d' $< ; \ fi | \ + sed -e 's|@MODULE_DIRECTORY@|$(module_directory)|g' | \ $(XSLT) \
[PATCH 2/2] configure: Check that provided paths are absolute
configure checks that its built-in directory options get an absolute path. Copy the check for custom options. Signed-off-by: Michal Suchanek --- v6: new patch --- configure.ac | 17 + 1 file changed, 17 insertions(+) diff --git a/configure.ac b/configure.ac index d6da5ee9ae9a..de01e08cf2e8 100644 --- a/configure.ac +++ b/configure.ac @@ -97,6 +97,23 @@ AC_ARG_WITH([module_directory], [], [with_module_directory=/lib/modules]) AC_SUBST([module_directory], [$with_module_directory]) +# Check all directory arguments for consistency. +for ac_var in distconfdir rootlibdir module_directory +do + eval ac_val=\$$ac_var + # Remove trailing slashes. + case $ac_val in +*/ ) + ac_val=`expr "X$ac_val" : 'X\(.*@<:@^/@:>@\)' \| "X$ac_val" : 'X\(.*\)'` + eval $ac_var=\$ac_val;; + esac + # Be sure to have absolute directory names. + case $ac_val in +@<:@\\/$@:>@* | ?:@<:@\\/@:>@* ) continue;; + esac + as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val" +done + AC_ARG_WITH([zstd], AS_HELP_STRING([--with-zstd], [handle Zstandard-compressed modules @<:@default=disabled@:>@]), [], [with_zstd=no]) -- 2.42.0
[PATCH rebased] kbuild: rpm-pkg: Fix build with non-default MODLIB
The default MODLIB value is composed of two variables and the hardcoded string '/lib/modules/'. MODLIB = $(INSTALL_MOD_PATH)/lib/modules/$(KERNELRELEASE) Defining this middle part as a variable was rejected on the basis that users can pass the whole MODLIB to make, such as make 'MODLIB=$(INSTALL_MOD_PATH)/usr/lib/modules/$(KERNELRELEASE)' However, this middle part of MODLIB is independently hardcoded by rpm-pkg, and when the user alters MODLIB this is not reflected when building the package. Given that $(INSTALL_MOD_PATH) is overridden during the rpm package build it is likely going to be empty. Then MODLIB can be passed to the rpm package, and used in place of the whole /usr/lib/modules/$(KERNELRELEASE) part. Signed-off-by: Michal Suchanek --- scripts/package/kernel.spec | 8 scripts/package/mkspec | 1 + 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/scripts/package/kernel.spec b/scripts/package/kernel.spec index 3eee0143e0c5..15f49c5077db 100644 --- a/scripts/package/kernel.spec +++ b/scripts/package/kernel.spec @@ -67,7 +67,7 @@ cp $(%{make} %{makeflags} -s image_name) %{buildroot}/boot/vmlinuz-%{KERNELRELEA %{make} %{makeflags} INSTALL_HDR_PATH=%{buildroot}/usr headers_install cp System.map %{buildroot}/boot/System.map-%{KERNELRELEASE} cp .config %{buildroot}/boot/config-%{KERNELRELEASE} -ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}/lib/modules/%{KERNELRELEASE}/build +ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}%{MODLIB}/build %if %{with_devel} %{make} %{makeflags} run-command KBUILD_RUN_COMMAND='${srctree}/scripts/package/install-extmod-build %{buildroot}/usr/src/kernels/%{KERNELRELEASE}' %endif @@ -98,8 +98,8 @@ fi %files %defattr (-, root, root) -/lib/modules/%{KERNELRELEASE} -%exclude /lib/modules/%{KERNELRELEASE}/build +%{MODLIB} +%exclude %{MODLIB}/build /boot/* %files headers @@ -110,5 +110,5 @@ fi %files devel %defattr (-, root, root) /usr/src/kernels/%{KERNELRELEASE} -/lib/modules/%{KERNELRELEASE}/build +%{MODLIB}/build %endif diff --git a/scripts/package/mkspec b/scripts/package/mkspec index d41608efb747..d41b2e5304ac 100755 --- a/scripts/package/mkspec +++ b/scripts/package/mkspec @@ -18,6 +18,7 @@ fi cat<
[PATCH] kbuild: rpm-pkg: Fix build with non-default MODLIB
The default MODLIB value is composed of two variables and the hardcoded string '/lib/modules/'. MODLIB = $(INSTALL_MOD_PATH)/lib/modules/$(KERNELRELEASE) Defining this middle part as a variable was rejected on the basis that users can pass the whole MODLIB to make, such as make 'MODLIB=$(INSTALL_MOD_PATH)/usr/lib/modules/$(KERNELRELEASE)' However, this middle part of MODLIB is independently hardcoded by rpm-pkg, and when the user alters MODLIB this is not reflected when building the package. Given that $(INSTALL_MOD_PATH) is overridden during the rpm package build it is likely going to be empty. Then MODLIB can be passed to the rpm package, and used in place of the whole /usr/lib/modules/$(KERNELRELEASE) part. Signed-off-by: Michal Suchanek --- scripts/package/kernel.spec | 14 +++--- scripts/package/mkspec | 1 + 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/scripts/package/kernel.spec b/scripts/package/kernel.spec index ac3f2ee6d7a0..1a727f636f67 100644 --- a/scripts/package/kernel.spec +++ b/scripts/package/kernel.spec @@ -67,8 +67,8 @@ cp $(%{make} %{makeflags} -s image_name) %{buildroot}/boot/vmlinuz-%{KERNELRELEA %{make} %{makeflags} INSTALL_HDR_PATH=%{buildroot}/usr headers_install cp System.map %{buildroot}/boot/System.map-%{KERNELRELEASE} cp .config %{buildroot}/boot/config-%{KERNELRELEASE} -ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}/lib/modules/%{KERNELRELEASE}/build -ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}/lib/modules/%{KERNELRELEASE}/source +ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}%{MODLIB}/build +ln -fns /usr/src/kernels/%{KERNELRELEASE} %{buildroot}%{MODLIB}/source %if %{with_devel} %{make} %{makeflags} run-command KBUILD_RUN_COMMAND='${srctree}/scripts/package/install-extmod-build %{buildroot}/usr/src/kernels/%{KERNELRELEASE}' %endif @@ -99,9 +99,9 @@ fi %files %defattr (-, root, root) -/lib/modules/%{KERNELRELEASE} -%exclude /lib/modules/%{KERNELRELEASE}/build -%exclude /lib/modules/%{KERNELRELEASE}/source +%{MODLIB} +%exclude %{MODLIB}/build +%exclude %{MODLIB}/source /boot/* %files headers @@ -112,6 +112,6 @@ fi %files devel %defattr (-, root, root) /usr/src/kernels/%{KERNELRELEASE} -/lib/modules/%{KERNELRELEASE}/build -/lib/modules/%{KERNELRELEASE}/source +%{MODLIB}/build +%{MODLIB}/source %endif diff --git a/scripts/package/mkspec b/scripts/package/mkspec index d41608efb747..d41b2e5304ac 100755 --- a/scripts/package/mkspec +++ b/scripts/package/mkspec @@ -18,6 +18,7 @@ fi cat<
[PATCH] testing: nvdimm: iomap: make __nfit_test_ioremap a macro
The ioremap passed as argument to __nfit_test_ioremap can be a macro so it cannot be passed as function argument. Make __nfit_test_ioremap into a macro so that ioremap can be passed as untyped macro argument. Signed-off-by: Michal Suchanek --- tools/testing/nvdimm/test/iomap.c | 18 -- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/tools/testing/nvdimm/test/iomap.c b/tools/testing/nvdimm/test/iomap.c index b752ce47ead3..ea956082e6a4 100644 --- a/tools/testing/nvdimm/test/iomap.c +++ b/tools/testing/nvdimm/test/iomap.c @@ -62,16 +62,14 @@ struct nfit_test_resource *get_nfit_res(resource_size_t resource) } EXPORT_SYMBOL(get_nfit_res); -static void __iomem *__nfit_test_ioremap(resource_size_t offset, unsigned long size, - void __iomem *(*fallback_fn)(resource_size_t, unsigned long)) -{ - struct nfit_test_resource *nfit_res = get_nfit_res(offset); - - if (nfit_res) - return (void __iomem *) nfit_res->buf + offset - - nfit_res->res.start; - return fallback_fn(offset, size); -} +#define __nfit_test_ioremap(offset, size, fallback_fn) ({ \ + struct nfit_test_resource *nfit_res = get_nfit_res(offset); \ + nfit_res ? \ + (void __iomem *) nfit_res->buf + (offset) \ + - nfit_res->res.start \ + : \ + fallback_fn((offset), (size)) ; \ +}) void __iomem *__wrap_devm_ioremap(struct device *dev, resource_size_t offset, unsigned long size) -- 2.34.1
[PATCH] testing: nvdimm: asm/mce.h is not needed in nfit.c
asm/mce.h is not available on arm, and it is not needed to build nfit.c. Remove the include. It was likely needed for COPY_MC_TEST Fixes: 3adb776384f2 ("x86, libnvdimm/test: Remove COPY_MC_TEST") Signed-off-by: Michal Suchanek --- tools/testing/nvdimm/test/nfit.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/tools/testing/nvdimm/test/nfit.c b/tools/testing/nvdimm/test/nfit.c index 0bc91ffee257..b4743ba65b96 100644 --- a/tools/testing/nvdimm/test/nfit.c +++ b/tools/testing/nvdimm/test/nfit.c @@ -23,8 +23,6 @@ #include "nfit_test.h" #include "../watermark.h" -#include - /* * Generate an NFIT table to describe the following topology: * -- 2.34.1
[PATCH 2/2] MAINTAINERS: add pattern for dummy-tools.
scripts/get_maintainer.pl does not find a maintainer for new files otherwise. Signed-off-by: Michal Suchanek --- MAINTAINERS | 1 + 1 file changed, 1 insertion(+) diff --git a/MAINTAINERS b/MAINTAINERS index c80ad735b384..ce631ec44e1a 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -9690,6 +9690,7 @@ F:scripts/*vmlinux* F: scripts/Kbuild* F: scripts/Makefile* F: scripts/basic/ +F: scripts/dummy-tools/ F: scripts/mk* F: scripts/mod/ F: scripts/package/ -- 2.26.2
[PATCH 1/2] kbuild: dummy-tools: Add elfedit.
elfedit is used in Makefile Makefile:GCC_TOOLCHAIN_DIR := $(dir $(shell which $(CROSS_COMPILE)elfedit)) which causes this error getting printed which: no elfedit in (./scripts/dummy-tools) Add elfedit to dummy-tools to avoid this error. Signed-off-by: Michal Suchanek --- scripts/dummy-tools/elfedit | 1 + 1 file changed, 1 insertion(+) create mode 12 scripts/dummy-tools/elfedit diff --git a/scripts/dummy-tools/elfedit b/scripts/dummy-tools/elfedit new file mode 12 index ..c0648b38dd42 --- /dev/null +++ b/scripts/dummy-tools/elfedit @@ -0,0 +1 @@ +ld \ No newline at end of file -- 2.26.2
[PATCH] arm64: make STACKPROTECTOR_PER_TASK configurable.
When using dummy-tools STACKPROTECTOR_PER_TASK is unconditionally selected. This defeats the purpose of the all-enabled tool. Description copied from arm Cc: Masahiro Yamada Signed-off-by: Michal Suchanek --- arch/arm64/Kconfig | 13 - 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig index a8ff7cd5f096..f59d391e31a4 100644 --- a/arch/arm64/Kconfig +++ b/arch/arm64/Kconfig @@ -1549,9 +1549,20 @@ config RANDOMIZE_MODULE_REGION_FULL config CC_HAVE_STACKPROTECTOR_SYSREG def_bool $(cc-option,-mstack-protector-guard=sysreg -mstack-protector-guard-reg=sp_el0 -mstack-protector-guard-offset=0) + config STACKPROTECTOR_PER_TASK - def_bool y + bool "Use a unique stack canary value for each task" depends on STACKPROTECTOR && CC_HAVE_STACKPROTECTOR_SYSREG + default y + help + Due to the fact that GCC uses an ordinary symbol reference from + which to load the value of the stack canary, this value can only + change at reboot time on SMP systems, and all tasks running in the + kernel's address space are forced to use the same canary value for + the entire duration that the system is up. + + Enable this option to switch to a different method that uses a + different canary value for each task. endmenu -- 2.26.2
[PATCH] ibmvnic: Fix possibly uninitialized old_num_tx_queues variable warning.
GCC 7.5 reports: ../drivers/net/ethernet/ibm/ibmvnic.c: In function 'ibmvnic_reset_init': ../drivers/net/ethernet/ibm/ibmvnic.c:5373:51: warning: 'old_num_tx_queues' may be used uninitialized in this function [-Wmaybe-uninitialized] ../drivers/net/ethernet/ibm/ibmvnic.c:5373:6: warning: 'old_num_rx_queues' may be used uninitialized in this function [-Wmaybe-uninitialized] The variable is initialized only if(reset) and used only if(reset && something) so this is a false positive. However, there is no reason to not initialize the variables unconditionally avoiding the warning. Fixes: 635e442f4a48 ("ibmvnic: merge ibmvnic_reset_init and ibmvnic_init") Signed-off-by: Michal Suchanek --- drivers/net/ethernet/ibm/ibmvnic.c | 8 +++- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/drivers/net/ethernet/ibm/ibmvnic.c b/drivers/net/ethernet/ibm/ibmvnic.c index 118a4bd3f877..3bad762083c5 100644 --- a/drivers/net/ethernet/ibm/ibmvnic.c +++ b/drivers/net/ethernet/ibm/ibmvnic.c @@ -5219,16 +5219,14 @@ static int ibmvnic_reset_init(struct ibmvnic_adapter *adapter, bool reset) { struct device *dev = >vdev->dev; unsigned long timeout = msecs_to_jiffies(2); - u64 old_num_rx_queues, old_num_tx_queues; + u64 old_num_rx_queues = adapter->req_rx_queues; + u64 old_num_tx_queues = adapter->req_tx_queues; int rc; adapter->from_passive_init = false; - if (reset) { - old_num_rx_queues = adapter->req_rx_queues; - old_num_tx_queues = adapter->req_tx_queues; + if (reset) reinit_completion(>init_done); - } adapter->init_done_rc = 0; rc = ibmvnic_send_crq_init(adapter); -- 2.26.2
[PATCH] powerpc: Fix build error in paravirt.h
./arch/powerpc/include/asm/paravirt.h:83:44: error: implicit declaration of function 'smp_processor_id'; did you mean 'raw_smp_processor_id'? smp_processor_id is defined in linux/smp.h but it is not included. The build error happens only when the patch is applied to 5.3 kernel but it only works by chance in mainline. Fixes: ca3f969dcb11 ("powerpc/paravirt: Use is_kvm_guest() in vcpu_is_preempted()") Signed-off-by: Michal Suchanek --- arch/powerpc/include/asm/paravirt.h | 1 + 1 file changed, 1 insertion(+) diff --git a/arch/powerpc/include/asm/paravirt.h b/arch/powerpc/include/asm/paravirt.h index edc08f04aef7..5d1726bb28e7 100644 --- a/arch/powerpc/include/asm/paravirt.h +++ b/arch/powerpc/include/asm/paravirt.h @@ -10,6 +10,7 @@ #endif #ifdef CONFIG_PPC_SPLPAR +#include #include #include -- 2.26.2
[PATCH] powerpc: Stop exporting __clear_user which is now inlined.
Stable commit 452e2a83ea23 ("powerpc: Fix __clear_user() with KUAP enabled") redefines __clear_user as inline function but does not remove the export. Fixes: 452e2a83ea23 ("powerpc: Fix __clear_user() with KUAP enabled") Signed-off-by: Michal Suchanek --- arch/powerpc/lib/ppc_ksyms.c | 1 - 1 file changed, 1 deletion(-) diff --git a/arch/powerpc/lib/ppc_ksyms.c b/arch/powerpc/lib/ppc_ksyms.c index c7f8e9586316..4b81fd96aa3e 100644 --- a/arch/powerpc/lib/ppc_ksyms.c +++ b/arch/powerpc/lib/ppc_ksyms.c @@ -24,7 +24,6 @@ EXPORT_SYMBOL(csum_tcpudp_magic); #endif EXPORT_SYMBOL(__copy_tofrom_user); -EXPORT_SYMBOL(__clear_user); EXPORT_SYMBOL(copy_page); #ifdef CONFIG_PPC64 -- 2.26.2
[PATCH 2/2] ext4: show the dax option in mount options
ext4 accepts both dax and dax_always option but shows only dax_always. Show both options. Fixes: 9cb20f94afcd ("fs/ext4: Make DAX mount option a tri-state") Signed-off-by: Michal Suchanek --- fs/ext4/super.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/ext4/super.c b/fs/ext4/super.c index ef4734b40e2a..7656c519cbe6 100644 --- a/fs/ext4/super.c +++ b/fs/ext4/super.c @@ -2647,7 +2647,7 @@ static int _ext4_show_options(struct seq_file *seq, struct super_block *sb, if (IS_EXT2_SB(sb)) SEQ_OPTS_PUTS("dax"); else - SEQ_OPTS_PUTS("dax=always"); + SEQ_OPTS_PUTS("dax,dax=always"); } else if (test_opt2(sb, DAX_NEVER)) { SEQ_OPTS_PUTS("dax=never"); } else if (test_opt2(sb, DAX_INODE)) { -- 2.26.2
[PATCH 1/2] xfs: show the dax option in mount options.
xfs accepts both dax and dax_enum but shows only dax_enum. Show both options. Fixes: 8d6c3446ec23 ("fs/xfs: Make DAX mount option a tri-state") Signed-off-by: Michal Suchanek --- fs/xfs/xfs_super.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/xfs/xfs_super.c b/fs/xfs/xfs_super.c index e3e229e52512..a3b3840d 100644 --- a/fs/xfs/xfs_super.c +++ b/fs/xfs/xfs_super.c @@ -163,7 +163,7 @@ xfs_fs_show_options( { XFS_MOUNT_GRPID, ",grpid" }, { XFS_MOUNT_DISCARD,",discard" }, { XFS_MOUNT_LARGEIO,",largeio" }, - { XFS_MOUNT_DAX_ALWAYS, ",dax=always" }, + { XFS_MOUNT_DAX_ALWAYS, ",dax,dax=always" }, { XFS_MOUNT_DAX_NEVER, ",dax=never" }, { 0, NULL } }; -- 2.26.2
[PATCH 0/2] Tristate moount option comatibility fixup
Hello, after the tristate dax option change some applications fail to detect pmem devices because the dax option no longer shows in mtab when device is mounted with -o dax. At first it might seem stupid to detect pmem by looking at the mount options. However, if the application actually wants a mount point properly configured for dax rather than just backed by pmem I do not see any other easy way. Also this happens during early installtion steps when the mounted filesystem is typically empty and you want to perform non-destructive detection. If there are better ways to detect dax enabled mount poins I want to hear all about it. In the meantime we have legacy applications to support. It also makes sense that when you mount a device with -o dax it actually shows dax in the mount options. Not doind so is confusing for humans as well. Thanks Michal Michal Suchanek (2): xfs: show the dax option in mount options. ext4: show the dax option in mount options References: bsc#1178366 fs/ext4/super.c| 2 +- fs/xfs/xfs_super.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) -- 2.26.2
[PATCH] ibmveth: Fix use of ibmveth in a bridge.
From: Thomas Bogendoerfer The check for src mac address in ibmveth_is_packet_unsupported is wrong. Commit 6f2275433a2f wanted to shut down messages for loopback packets, but now suppresses bridged frames, which are accepted by the hypervisor otherwise bridging won't work at all. Fixes: 6f2275433a2f ("ibmveth: Detect unsupported packets before sending to the hypervisor") Signed-off-by: Michal Suchanek --- ms: added commit message --- drivers/net/ethernet/ibm/ibmveth.c | 6 -- 1 file changed, 6 deletions(-) diff --git a/drivers/net/ethernet/ibm/ibmveth.c b/drivers/net/ethernet/ibm/ibmveth.c index 7ef3369953b6..c3ec9ceed833 100644 --- a/drivers/net/ethernet/ibm/ibmveth.c +++ b/drivers/net/ethernet/ibm/ibmveth.c @@ -1031,12 +1031,6 @@ static int ibmveth_is_packet_unsupported(struct sk_buff *skb, ret = -EOPNOTSUPP; } - if (!ether_addr_equal(ether_header->h_source, netdev->dev_addr)) { - netdev_dbg(netdev, "source packet MAC address does not match veth device's, dropping packet.\n"); - netdev->stats.tx_dropped++; - ret = -EOPNOTSUPP; - } - return ret; } -- 2.28.0
[PATCH 1/2] ARM: dts: sun8i: h2+: Fix Orange Pi Zero device description.
There are two models of Orange Pi zero which are confusingly marketed under the same name. Old model comes without a flash memory and current model does have a flash memory. Build device tree for each model. Signed-off-by: Michal Suchanek --- arch/arm/boot/dts/Makefile| 1 + .../sun8i-h2-plus-orangepi-zero-no-flash.dts | 210 ++ .../boot/dts/sun8i-h2-plus-orangepi-zero.dts | 201 + 3 files changed, 215 insertions(+), 197 deletions(-) create mode 100644 arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero-no-flash.dts diff --git a/arch/arm/boot/dts/Makefile b/arch/arm/boot/dts/Makefile index 4572db3fa5ae..f2853cea0c9c 100644 --- a/arch/arm/boot/dts/Makefile +++ b/arch/arm/boot/dts/Makefile @@ -1168,6 +1168,7 @@ dtb-$(CONFIG_MACH_SUN8I) += \ sun8i-h2-plus-libretech-all-h3-cc.dtb \ sun8i-h2-plus-orangepi-r1.dtb \ sun8i-h2-plus-orangepi-zero.dtb \ + sun8i-h2-plus-orangepi-zero-no-flash.dtb \ sun8i-h3-bananapi-m2-plus.dtb \ sun8i-h3-bananapi-m2-plus-v1.2.dtb \ sun8i-h3-beelink-x2.dtb \ diff --git a/arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero-no-flash.dts b/arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero-no-flash.dts new file mode 100644 index ..3859b663e3f0 --- /dev/null +++ b/arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero-no-flash.dts @@ -0,0 +1,210 @@ +/* + * Copyright (C) 2016 Icenowy Zheng + * + * Based on sun8i-h3-orangepi-one.dts, which is: + * Copyright (C) 2016 Hans de Goede + * + * This file is dual-licensed: you can use it either under the terms + * of the GPL or the X11 license, at your option. Note that this dual + * licensing only applies to this file, and not this project as a + * whole. + * + * a) This file is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of the + * License, or (at your option) any later version. + * + * This file is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * Or, alternatively, + * + * b) Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without + * restriction, including without limitation the rights to use, + * copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following + * conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +/dts-v1/; +#include "sun8i-h3.dtsi" +#include "sunxi-common-regulators.dtsi" + +#include +#include + +/ { + model = "Xunlong Orange Pi Zero (old model without flash memory)"; + compatible = "xunlong,orangepi-zero-no-flash", + "xunlong,orangepi-zero", "allwinner,sun8i-h2-plus"; + + aliases { + serial0 = + /* ethernet0 is the H3 emac, defined in sun8i-h3.dtsi */ + ethernet0 = + ethernet1 = + }; + + chosen { + stdout-path = "serial0:115200n8"; + }; + + leds { + compatible = "gpio-leds"; + + pwr_led { + label = "orangepi:green:pwr"; + gpios = <_pio 0 10 GPIO_ACTIVE_HIGH>; + default-state = "on"; + }; + + status_led { + label = "orangepi:red:status"; + gpios = < 0 17 GPIO_ACTIVE_HIGH>; + }; + }; + + reg_vcc_wifi: reg_vcc_wifi { + compatible = "regulator-fixed"; + regulator-min-microvolt = <330>; + regulator-max-microvolt = <330>; + regulator-name = "vcc-wifi"; + enable-active-high; + gpio
[PATCH 2/2] dt-bindings: arm: sunxi: Fix Orange Pi Zero bindings
There are two models of Orange Pi zero which are confusingly marketed under the same name. Old model comes without a flash memory and current model does have a flash memory. Add bindings for each model. Signed-off-by: Michal Suchanek --- Documentation/devicetree/bindings/arm/sunxi.yaml | 7 +++ 1 file changed, 7 insertions(+) diff --git a/Documentation/devicetree/bindings/arm/sunxi.yaml b/Documentation/devicetree/bindings/arm/sunxi.yaml index efc9118233b4..7e76ea544bf7 100644 --- a/Documentation/devicetree/bindings/arm/sunxi.yaml +++ b/Documentation/devicetree/bindings/arm/sunxi.yaml @@ -864,8 +864,15 @@ properties: - const: xunlong,orangepi-win - const: allwinner,sun50i-a64 + - description: Xunlong OrangePi Zero (old model without flash memory) +items: + - const: xunlong,orangepi-zero-no-flash + - const: xunlong,orangepi-zero + - const: allwinner,sun8i-h2-plus + - description: Xunlong OrangePi Zero items: + - const: xunlong,orangepi-zero-with-flash - const: xunlong,orangepi-zero - const: allwinner,sun8i-h2-plus -- 2.28.0
[PATCH] ARM: dts: sun8i: h2+: Enable optional SPI flash on Orange Pi Zero board
The flash is present on all new boards and users went out of their way to add it on the old ones. Enabling it makes a more reasonable default. Signed-off-by: Michal Suchanek --- arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero.dts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero.dts b/arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero.dts index f19ed981da9d..061d295bbba7 100644 --- a/arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero.dts +++ b/arch/arm/boot/dts/sun8i-h2-plus-orangepi-zero.dts @@ -163,8 +163,8 @@ { }; { - /* Disable SPI NOR by default: it optional on Orange Pi Zero boards */ - status = "disabled"; + /* Enable optional SPI NOR by default */ + status = "okay"; flash@0 { #address-cells = <1>; -- 2.28.0
[PATCH] Revert "powerpc/64s: machine check interrupt update NMI accounting"
This reverts commit 116ac378bb3ff844df333e7609e7604651a0db9d. This commit causes the kernel to oops and reboot when injecting a SLB multihit which causes a MCE. Before this commit a SLB multihit was corrected by the kernel and the system continued to operate normally. cc: sta...@vger.kernel.org Fixes: 116ac378bb3f ("powerpc/64s: machine check interrupt update NMI accounting") Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/mce.c | 7 --- arch/powerpc/kernel/traps.c | 18 +++--- 2 files changed, 3 insertions(+), 22 deletions(-) diff --git a/arch/powerpc/kernel/mce.c b/arch/powerpc/kernel/mce.c index ada59f6c4298..2e13528dcc92 100644 --- a/arch/powerpc/kernel/mce.c +++ b/arch/powerpc/kernel/mce.c @@ -591,14 +591,10 @@ EXPORT_SYMBOL_GPL(machine_check_print_event_info); long notrace machine_check_early(struct pt_regs *regs) { long handled = 0; - bool nested = in_nmi(); u8 ftrace_enabled = this_cpu_get_ftrace_enabled(); this_cpu_set_ftrace_enabled(0); - if (!nested) - nmi_enter(); - hv_nmi_check_nonrecoverable(regs); /* @@ -607,9 +603,6 @@ long notrace machine_check_early(struct pt_regs *regs) if (ppc_md.machine_check_early) handled = ppc_md.machine_check_early(regs); - if (!nested) - nmi_exit(); - this_cpu_set_ftrace_enabled(ftrace_enabled); return handled; diff --git a/arch/powerpc/kernel/traps.c b/arch/powerpc/kernel/traps.c index d1ebe152f210..7853b770918d 100644 --- a/arch/powerpc/kernel/traps.c +++ b/arch/powerpc/kernel/traps.c @@ -827,19 +827,7 @@ void machine_check_exception(struct pt_regs *regs) { int recover = 0; - /* -* BOOK3S_64 does not call this handler as a non-maskable interrupt -* (it uses its own early real-mode handler to handle the MCE proper -* and then raises irq_work to call this handler when interrupts are -* enabled). -* -* This is silly. The BOOK3S_64 should just call a different function -* rather than expecting semantics to magically change. Something -* like 'non_nmi_machine_check_exception()', perhaps? -*/ - const bool nmi = !IS_ENABLED(CONFIG_PPC_BOOK3S_64); - - if (nmi) nmi_enter(); + nmi_enter(); __this_cpu_inc(irq_stat.mce_exceptions); @@ -865,7 +853,7 @@ void machine_check_exception(struct pt_regs *regs) if (check_io_access(regs)) goto bail; - if (nmi) nmi_exit(); + nmi_exit(); die("Machine check", regs, SIGBUS); @@ -876,7 +864,7 @@ void machine_check_exception(struct pt_regs *regs) return; bail: - if (nmi) nmi_exit(); + nmi_exit(); } void SMIException(struct pt_regs *regs) -- 2.28.0
[PATCH] char: virtio: Select VIRTIO from VIRTIO_CONSOLE.
Make it possible to have virtio console built-in when other virtio drivers are modular. Signed-off-by: Michal Suchanek --- drivers/char/Kconfig | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig index 3a144c000a38..9bd9917ca9af 100644 --- a/drivers/char/Kconfig +++ b/drivers/char/Kconfig @@ -93,8 +93,9 @@ config PPDEV config VIRTIO_CONSOLE tristate "Virtio console" - depends on VIRTIO && TTY + depends on TTY select HVC_DRIVER + select VIRTIO help Virtio console for use with hypervisors. -- 2.28.0
[PATCH v3] dm writecache: reject asynchronous pmem.
The writecache driver does not handle asynchronous pmem. Reject it when supplied as cache. Link: https://lore.kernel.org/linux-nvdimm/87lfk5hahc@linux.ibm.com/ Fixes: 6e84200c0a29 ("virtio-pmem: Add virtio pmem driver") Signed-off-by: Michal Suchanek --- drivers/md/dm-writecache.c | 6 ++ 1 file changed, 6 insertions(+) diff --git a/drivers/md/dm-writecache.c b/drivers/md/dm-writecache.c index 30505d70f423..5358894bb9fd 100644 --- a/drivers/md/dm-writecache.c +++ b/drivers/md/dm-writecache.c @@ -2266,6 +2266,12 @@ static int writecache_ctr(struct dm_target *ti, unsigned argc, char **argv) } if (WC_MODE_PMEM(wc)) { + if (!dax_synchronous(wc->ssd_dev->dax_dev)) { + r = -EOPNOTSUPP; + ti->error = "Asynchronous persistent memory not supported as pmem cache"; + goto bad; + } + r = persistent_memory_claim(wc); if (r) { ti->error = "Unable to map persistent memory for cache"; -- 2.26.2
[PATCH v2] dm writecache: reject asynchronous pmem.
The writecache driver does not handle asynchronous pmem. Reject it when supplied as cache. Link: https://lore.kernel.org/linux-nvdimm/87lfk5hahc@linux.ibm.com/ Fixes: 6e84200c0a29 ("virtio-pmem: Add virtio pmem driver") Signed-off-by: Michal Suchanek --- drivers/md/dm-writecache.c | 6 ++ 1 file changed, 6 insertions(+) diff --git a/drivers/md/dm-writecache.c b/drivers/md/dm-writecache.c index 30505d70f423..1e4f37249e28 100644 --- a/drivers/md/dm-writecache.c +++ b/drivers/md/dm-writecache.c @@ -2271,6 +2271,12 @@ static int writecache_ctr(struct dm_target *ti, unsigned argc, char **argv) ti->error = "Unable to map persistent memory for cache"; goto bad; } + + if (!dax_synchronous(wc->ssd_dev->dax_dev)) { + r = -EOPNOTSUPP; + ti->error = "Asynchronous persistent memory not supported as pmem cache"; + goto bad; + } } else { size_t n_blocks, n_metadata_blocks; uint64_t n_bitmap_bits; -- 2.26.2
[PATCH] dm writecache: reject asynchronous pmem.
The writecache driver does not handle asynchronous pmem. Reject it when supplied as cache. Link: https://lore.kernel.org/linux-nvdimm/87lfk5hahc@linux.ibm.com/ Fixes: 6e84200c0a29 ("virtio-pmem: Add virtio pmem driver") Signed-off-by: Michal Suchanek --- drivers/md/dm-writecache.c | 6 ++ 1 file changed, 6 insertions(+) diff --git a/drivers/md/dm-writecache.c b/drivers/md/dm-writecache.c index 30505d70f423..57b0a972f6fd 100644 --- a/drivers/md/dm-writecache.c +++ b/drivers/md/dm-writecache.c @@ -2277,6 +2277,12 @@ static int writecache_ctr(struct dm_target *ti, unsigned argc, char **argv) wc->memory_map_size -= (uint64_t)wc->start_sector << SECTOR_SHIFT; + if (!dax_synchronous(wc->ssd_dev->dax_dev)) { + r = -EOPNOTSUPP; + ti->error = "Asynchronous persistent memory not supported as pmem cache"; + goto bad; + } + bio_list_init(>flush_list); wc->flush_thread = kthread_create(writecache_flush_thread, wc, "dm_writecache_flush"); if (IS_ERR(wc->flush_thread)) { -- 2.26.2
[PATCH] powerpc/fadump: Remove duplicate message.
There is duplicate message about lack of support by firmware in fadump_reserve_mem and setup_fadump. Due to different capitalization it is clear that the one in setup_fadump is shown on boot. Remove the duplicate that is not shown. Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/fadump.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/arch/powerpc/kernel/fadump.c b/arch/powerpc/kernel/fadump.c index cdcdea6c6453..f40dc713f089 100644 --- a/arch/powerpc/kernel/fadump.c +++ b/arch/powerpc/kernel/fadump.c @@ -438,10 +438,8 @@ int __init fadump_reserve_mem(void) if (!fw_dump.fadump_enabled) return 0; - if (!fw_dump.fadump_supported) { - pr_info("Firmware-Assisted Dump is not supported on this hardware\n"); + if (!fw_dump.fadump_supported) goto error_out; - } /* * Initialize boot memory size -- 2.23.0
[PATCH v2 0/8] Fix cdrom autoclose.
Link: https://lore.kernel.org/lkml/cover.1513263482.git.msucha...@suse.de/ Hello, there is cdrom autoclose feature that is supposed to close the tray, wait for the disc to become ready, and then open the device. This used to work in ancient times. Then in old times there was a hack in util-linux which worked around the breakage which probably resulted from switching to scsi emulation. Currently util-linux maintainer refuses to merge another hack on the basis that kernel still has the feature so it should be fixed there. The code needs not be replicated in every userspace utility like mount or dd which has no business knowing which devices are CD-roms and where the autoclose setting is in the kernel. Michal Suchanek (8): cdrom: add poll_event_interruptible cdrom: factor out common open_for_* code cdrom: wait for the tray to close cdrom: separate autoclose into an IOCTL docs: cdrom: Add autoclose IOCTL bdev: add open_finish. scsi: sr: workaround VMware ESXi cdrom emulation bug scsi: sr: wait for the medium to become ready Documentation/filesystems/locking.rst | 2 + Documentation/ioctl/cdrom.rst | 25 drivers/cdrom/cdrom.c | 188 ++ drivers/scsi/sr.c | 60 ++-- fs/block_dev.c| 21 ++- include/linux/blkdev.h| 1 + include/uapi/linux/cdrom.h| 1 + 7 files changed, 198 insertions(+), 100 deletions(-) -- 2.23.0
[PATCH v2 6/8] bdev: add open_finish.
Opening a block device may require a long operation such as waiting for the cdrom tray to close. Performing this operation with locks held locks out other attempts to open the device. These processes waiting to open the device are not killable. To avoid this issue and still be able to perform time-consuming checks at open() time the block device driver can provide open_finish(). If it does opening the device proceeds even when an error is returned from open(), bd_mutex is released and open_finish() is called. If open_finish() succeeds the device is now open, if it fails release() is called. When -ERESTARTSYS is returned from open() blkdev_get may loop without calling open_finish(). On -ERESTARTSYS open_finish() is not called. Move a ret = 0 assignment up in the if/else branching to avoid returning -ENXIO. Previously the return value was ignored on the unhandled branch. Signed-off-by: Michal Suchanek --- Documentation/filesystems/locking.rst | 2 ++ fs/block_dev.c| 21 + include/linux/blkdev.h| 1 + 3 files changed, 20 insertions(+), 4 deletions(-) diff --git a/Documentation/filesystems/locking.rst b/Documentation/filesystems/locking.rst index fc3a0704553c..2471ced5a8cf 100644 --- a/Documentation/filesystems/locking.rst +++ b/Documentation/filesystems/locking.rst @@ -456,6 +456,7 @@ block_device_operations prototypes:: int (*open) (struct block_device *, fmode_t); + int (*open_finish) (struct block_device *, fmode_t, int); int (*release) (struct gendisk *, fmode_t); int (*ioctl) (struct block_device *, fmode_t, unsigned, unsigned long); int (*compat_ioctl) (struct block_device *, fmode_t, unsigned, unsigned long); @@ -473,6 +474,7 @@ locking rules: opsbd_mutex === === open: yes +open_finish: no release: yes ioctl: no compat_ioctl: no diff --git a/fs/block_dev.c b/fs/block_dev.c index 9c073dbdc1b0..009b5dedb1f7 100644 --- a/fs/block_dev.c +++ b/fs/block_dev.c @@ -1526,6 +1526,7 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) int partno; int perm = 0; bool first_open = false; + bool need_finish = false; if (mode & FMODE_READ) perm |= MAY_READ; @@ -1581,6 +1582,8 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) put_disk_and_module(disk); goto restart; } + if (bdev->bd_disk->fops->open_finish) + need_finish = true; } if (!ret) { @@ -1601,7 +1604,7 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) invalidate_partitions(disk, bdev); } - if (ret) + if (ret && !need_finish) goto out_clear; } else { struct block_device *whole; @@ -1627,10 +1630,14 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) if (bdev->bd_bdi == _backing_dev_info) bdev->bd_bdi = bdi_get(disk->queue->backing_dev_info); } else { + ret = 0; if (bdev->bd_contains == bdev) { - ret = 0; - if (bdev->bd_disk->fops->open) + if (bdev->bd_disk->fops->open) { ret = bdev->bd_disk->fops->open(bdev, mode); + if ((ret != -ERESTARTSYS) && + bdev->bd_disk->fops->open_finish) + need_finish = true; + } /* the same as first opener case, read comment there */ if (bdev->bd_invalidated) { if (!ret) @@ -1638,7 +1645,7 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) else if (ret == -ENOMEDIUM) invalidate_partitions(bdev->bd_disk, bdev); } - if (ret) + if (ret && !need_finish) goto out_unlock_bdev; } } @@ -1650,6 +1657,12 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) /* only one opener holds refs to the module and disk */ if (!first_open) put_disk_and_module(disk); +
[PATCH v2 8/8] scsi: sr: wait for the medium to become ready
Use the autoclose IOCLT provided by cdrom driver to wait for drive to close in open_finish, and attempt to open once more after the door closes. Signed-off-by: Michal Suchanek --- drivers/scsi/sr.c | 54 --- 1 file changed, 42 insertions(+), 12 deletions(-) diff --git a/drivers/scsi/sr.c b/drivers/scsi/sr.c index 8090c5bdec09..34d9a818b9e0 100644 --- a/drivers/scsi/sr.c +++ b/drivers/scsi/sr.c @@ -521,29 +521,58 @@ static blk_status_t sr_init_command(struct scsi_cmnd *SCpnt) return ret; } -static int sr_block_open(struct block_device *bdev, fmode_t mode) +static int __sr_block_open(struct block_device *bdev, fmode_t mode) { - struct scsi_cd *cd; - struct scsi_device *sdev; - int ret = -ENXIO; - - cd = scsi_cd_get(bdev->bd_disk); - if (!cd) - goto out; + struct scsi_cd *cd = scsi_cd(bdev->bd_disk); + int ret; - sdev = cd->device; - scsi_autopm_get_device(sdev); check_disk_change(bdev); mutex_lock(_mutex); ret = cdrom_open(>cdi, bdev, mode); mutex_unlock(_mutex); + return ret; +} + +static int sr_block_open(struct block_device *bdev, fmode_t mode) +{ + struct scsi_cd *cd = scsi_cd_get(bdev->bd_disk); + struct scsi_device *sdev; + int ret; + + if (!cd) + return -ENXIO; + + sdev = cd->device; + scsi_autopm_get_device(sdev); + ret = __sr_block_open(bdev, mode); scsi_autopm_put_device(sdev); - if (ret) + + if (ret == -ERESTARTSYS) scsi_cd_put(cd); -out: + return ret; +} + +static int sr_block_open_finish(struct block_device *bdev, fmode_t mode, + int ret) +{ + struct scsi_cd *cd = scsi_cd(bdev->bd_disk); + + /* wait for drive to get ready */ + if ((ret == -ENOMEDIUM) && !(mode & FMODE_NDELAY)) { + struct scsi_device *sdev = cd->device; + /* +* Cannot use sr_block_ioctl because it locks sr_mutex blocking +* out any processes trying to access the drive +*/ + scsi_autopm_get_device(sdev); + cdrom_ioctl(>cdi, bdev, mode, CDROM_AUTOCLOSE, 0); + ret = __sr_block_open(bdev, mode); + scsi_autopm_put_device(sdev); + } + return ret; } @@ -639,6 +668,7 @@ static const struct block_device_operations sr_bdops = { .owner = THIS_MODULE, .open = sr_block_open, + .open_finish= sr_block_open_finish, .release= sr_block_release, .ioctl = sr_block_ioctl, .check_events = sr_block_check_events, -- 2.23.0
[PATCH v2 5/8] docs: cdrom: Add autoclose IOCTL
This IOCTL will be used internally by the sr driver but there is no reason to not document it for userspace. Signed-off-by: Michal Suchanek --- Documentation/ioctl/cdrom.rst | 25 + 1 file changed, 25 insertions(+) diff --git a/Documentation/ioctl/cdrom.rst b/Documentation/ioctl/cdrom.rst index 3b4c0506de46..9372ff1b2b47 100644 --- a/Documentation/ioctl/cdrom.rst +++ b/Documentation/ioctl/cdrom.rst @@ -60,6 +60,7 @@ are as follows: CDROM_LOCKDOOR lock or unlock door CDROM_DEBUG Turn debug messages on/off CDROM_GET_CAPABILITYget capabilities + CDROM_AUTOCLOSE If autoclose enabled close the tray CDROMAUDIOBUFSIZset the audio buffer size DVD_READ_STRUCT Read structure DVD_WRITE_STRUCTWrite structure @@ -1056,6 +1057,30 @@ CDROM_GET_CAPABILITY +CDROM_AUTOCLOSE + Close the tray if the device has one, and autoclose is enabled. + Wait for drive to become ready. + + + usage:: + + ioctl(fd, CDROM_AUTOCLOSE, 0); + + + inputs: + none + + + outputs: + The ioctl return value is 0 or an error code. + + + error return: + - ENOMEDIUM No medium found or drive error. + - ERESTARTSYS Received a signal while waiting for drive to become ready. + + + CDROMAUDIOBUFSIZ set the audio buffer size -- 2.23.0
[PATCH v2 1/2] soundwire: depend on ACPI
The device cannot be probed on !ACPI and gives this warning: drivers/soundwire/slave.c:16:12: warning: ‘sdw_slave_add’ defined but not used [-Wunused-function] static int sdw_slave_add(struct sdw_bus *bus, ^ Cc: sta...@vger.kernel.org Fixes: 7c3cd189b86d ("soundwire: Add Master registration") Signed-off-by: Michal Suchanek --- drivers/soundwire/Kconfig | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/soundwire/Kconfig b/drivers/soundwire/Kconfig index f518273cfbe3..c73bfbaa2659 100644 --- a/drivers/soundwire/Kconfig +++ b/drivers/soundwire/Kconfig @@ -5,6 +5,7 @@ menuconfig SOUNDWIRE tristate "SoundWire support" + depends on ACPI help SoundWire is a 2-Pin interface with data and clock line ratified by the MIPI Alliance. SoundWire is used for transporting data -- 2.23.0
[PATCH v2 2/2] soundwire: depend on ACPI || OF
Now devicetree is supported for probing soundwire as well. On platforms built with !ACPI !OF (ie s390x) the device still cannot be probed and gives a build warning. Cc: sta...@vger.kernel.org Fixes: a2e484585ad3 ("soundwire: core: add device tree support for slave devices") Signed-off-by: Michal Suchanek --- drivers/soundwire/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/soundwire/Kconfig b/drivers/soundwire/Kconfig index c73bfbaa2659..c8c80df090d1 100644 --- a/drivers/soundwire/Kconfig +++ b/drivers/soundwire/Kconfig @@ -5,7 +5,7 @@ menuconfig SOUNDWIRE tristate "SoundWire support" - depends on ACPI + depends on ACPI || OF help SoundWire is a 2-Pin interface with data and clock line ratified by the MIPI Alliance. SoundWire is used for transporting data -- 2.23.0
[PATCH 2/2] soundwire: depend on ACPI || OF
Now devicetree is supposrted for probing sondwire as well. Fixes: a2e484585ad3 ("soundwire: core: add device tree support for slave devices") Signed-off-by: Michal Suchanek --- drivers/soundwire/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/soundwire/Kconfig b/drivers/soundwire/Kconfig index c73bfbaa2659..c8c80df090d1 100644 --- a/drivers/soundwire/Kconfig +++ b/drivers/soundwire/Kconfig @@ -5,7 +5,7 @@ menuconfig SOUNDWIRE tristate "SoundWire support" - depends on ACPI + depends on ACPI || OF help SoundWire is a 2-Pin interface with data and clock line ratified by the MIPI Alliance. SoundWire is used for transporting data -- 2.23.0
[PATCH 1/2] soundwire: depend on ACPI
The device cannot be probed on !ACPI and gives this warning: drivers/soundwire/slave.c:16:12: warning: ‘sdw_slave_add’ defined but not used [-Wunused-function] static int sdw_slave_add(struct sdw_bus *bus, ^ Fixes: 7c3cd189b86d ("soundwire: Add Master registration") Signed-off-by: Michal Suchanek --- drivers/soundwire/Kconfig | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/soundwire/Kconfig b/drivers/soundwire/Kconfig index f518273cfbe3..c73bfbaa2659 100644 --- a/drivers/soundwire/Kconfig +++ b/drivers/soundwire/Kconfig @@ -5,6 +5,7 @@ menuconfig SOUNDWIRE tristate "SoundWire support" + depends on ACPI help SoundWire is a 2-Pin interface with data and clock line ratified by the MIPI Alliance. SoundWire is used for transporting data -- 2.23.0
[PATCH v2 rebased] powerpc/fadump: when fadump is supported register the fadump sysfs files.
Currently it is not possible to distinguish the case when fadump is supported by firmware and disabled in kernel and completely unsupported using the kernel sysfs interface. User can investigate the devicetree but it is more reasonable to provide sysfs files in case we get some fadumpv2 in the future. With this patch sysfs files are available whenever fadump is supported by firmware. Signed-off-by: Michal Suchanek Acked-by: Hari Bathini --- v2: move the sysfs initialization earlier to avoid condition nesting rebase: on top of the powernv fadump support --- arch/powerpc/kernel/fadump.c | 16 +--- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/arch/powerpc/kernel/fadump.c b/arch/powerpc/kernel/fadump.c index ed59855430b9..cdcdea6c6453 100644 --- a/arch/powerpc/kernel/fadump.c +++ b/arch/powerpc/kernel/fadump.c @@ -1466,16 +1466,20 @@ static void fadump_init_files(void) */ int __init setup_fadump(void) { - if (!fw_dump.fadump_enabled) - return 0; - - if (!fw_dump.fadump_supported) { + if (!fw_dump.fadump_supported && fw_dump.fadump_enabled) { printk(KERN_ERR "Firmware-assisted dump is not supported on" " this hardware\n"); - return 0; } + if (!fw_dump.fadump_supported) + return 0; + + fadump_init_files(); fadump_show_config(); + + if (!fw_dump.fadump_enabled) + return 1; + /* * If dump data is available then see if it is valid and prepare for * saving it to the disk. @@ -1492,8 +1496,6 @@ int __init setup_fadump(void) else if (fw_dump.reserve_dump_area_size) fw_dump.ops->fadump_init_mem_struct(_dump); - fadump_init_files(); - return 1; } subsys_initcall(setup_fadump); -- 2.23.0
[PATCH v9 0/8] Disable compat cruft on ppc64le v9
Less code means less bugs so add a knob to skip the compat stuff. This is tested on ppc64le top of https://patchwork.ozlabs.org/patch/1153850/ https://patchwork.ozlabs.org/patch/1158412/ Changes in v2: saner CONFIG_COMPAT ifdefs Changes in v3: - change llseek to 32bit instead of builing it unconditionally in fs - clanup the makefile conditionals - remove some ifdefs or convert to IS_DEFINED where possible Changes in v4: - cleanup is_32bit_task and current_is_64bit - more makefile cleanup Changes in v5: - more current_is_64bit cleanup - split off callchain.c 32bit and 64bit parts Changes in v6: - cleanup makefile after split - consolidate read_user_stack_32 - fix some checkpatch warnings Changes in v7: - add back __ARCH_WANT_SYS_LLSEEK to fix build with llseek - remove leftover hunk - add review tags Changes in v8: - consolidate valid_user_sp to fix it in the split callchain.c - fix build errors/warnings with PPC64 !COMPAT and PPC32 Changes in v9: - remove current_is_64bit() Michal Suchanek (8): powerpc: Add back __ARCH_WANT_SYS_LLSEEK macro powerpc: move common register copy functions from signal_32.c to signal.c powerpc/perf: consolidate read_user_stack_32 powerpc/perf: consolidate valid_user_sp powerpc/perf: remove current_is_64bit() powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Make COMPAT user-selectable disabled on littleendian by default. powerpc/perf: split callchain.c by bitness arch/powerpc/Kconfig | 5 +- arch/powerpc/include/asm/thread_info.h | 4 +- arch/powerpc/include/asm/unistd.h | 1 + arch/powerpc/kernel/Makefile | 7 +- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 144 - arch/powerpc/kernel/signal_32.c| 140 - arch/powerpc/kernel/syscall_64.c | 6 +- arch/powerpc/kernel/vdso.c | 3 +- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c | 387 + arch/powerpc/perf/callchain.h | 25 ++ arch/powerpc/perf/callchain_32.c | 197 + arch/powerpc/perf/callchain_64.c | 178 fs/read_write.c| 3 +- 15 files changed, 565 insertions(+), 542 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c -- 2.23.0
[PATCH v9 4/8] powerpc/perf: consolidate valid_user_sp
Merge the 32bit and 64bit version. Halve the check constants on 32bit. Use STACK_TOP since it is defined. This removes a page from the valid 32bit area on 64bit: #define TASK_SIZE_USER32 (0x0001UL - (1 * PAGE_SIZE)) #define STACK_TOP_USER32 TASK_SIZE_USER32 Signed-off-by: Michal Suchanek --- v8: new patch --- arch/powerpc/perf/callchain.c | 28 ++-- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index d86bdbffda9e..7863ee0a0e69 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -102,6 +102,20 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } +static inline int valid_user_sp(unsigned long sp, int is_64) +{ + unsigned long stack_top; + + if (IS_ENABLED(CONFIG_PPC32)) + stack_top = STACK_TOP; + else/* STACK_TOP uses is_32bit_task() but we want is_64 */ + stack_top = is_64 ? STACK_TOP_USER64 : STACK_TOP_USER32; + + if (!sp || (sp & (is_64 ? 7 : 3)) || sp > stack_top - (is_64 ? 32 : 16)) + return 0; + return 1; +} + #ifdef CONFIG_PPC64 /* * On 64-bit we don't want to invoke hash_page on user addresses from @@ -165,13 +179,6 @@ static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) return read_user_stack_slow(ptr, ret, 8); } -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) - return 0; - return 1; -} - /* * 64-bit user processes use the same stack frame for RT and non-RT signals. */ @@ -294,13 +301,6 @@ static inline int current_is_64bit(void) return 0; } -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - if (!sp || (sp & 7) || sp > TASK_SIZE - 32) - return 0; - return 1; -} - #define __SIGNAL_FRAMESIZE32 __SIGNAL_FRAMESIZE #define sigcontext32 sigcontext #define mcontext32 mcontext -- 2.23.0
[PATCH v9 8/8] powerpc/perf: split callchain.c by bitness
Building callchain.c with !COMPAT proved quite ugly with all the defines. Splitting out the 32bit and 64bit parts looks better. No code change intended. Signed-off-by: Michal Suchanek --- v6: - move current_is_64bit consolidetaion to earlier patch - move defines to the top of callchain_32.c - Makefile cleanup v8: - fix valid_user_sp --- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c| 367 +-- arch/powerpc/perf/callchain.h| 25 +++ arch/powerpc/perf/callchain_32.c | 197 + arch/powerpc/perf/callchain_64.c | 178 +++ 5 files changed, 405 insertions(+), 367 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c diff --git a/arch/powerpc/perf/Makefile b/arch/powerpc/perf/Makefile index c155dcbb8691..53d614e98537 100644 --- a/arch/powerpc/perf/Makefile +++ b/arch/powerpc/perf/Makefile @@ -1,6 +1,9 @@ # SPDX-License-Identifier: GPL-2.0 -obj-$(CONFIG_PERF_EVENTS) += callchain.o perf_regs.o +obj-$(CONFIG_PERF_EVENTS) += callchain.o callchain_$(BITS).o perf_regs.o +ifdef CONFIG_COMPAT +obj-$(CONFIG_PERF_EVENTS) += callchain_32.o +endif obj-$(CONFIG_PPC_PERF_CTRS)+= core-book3s.o bhrb.o obj64-$(CONFIG_PPC_PERF_CTRS) += ppc970-pmu.o power5-pmu.o \ diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index d6ab1a734a6a..dd5051015008 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -15,11 +15,9 @@ #include #include #include -#ifdef CONFIG_COMPAT -#include "../kernel/ppc32.h" -#endif #include +#include "callchain.h" /* * Is sp valid as the address of the next kernel stack frame after prev_sp? @@ -102,369 +100,6 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - unsigned long stack_top; - - if (IS_ENABLED(CONFIG_PPC32)) - stack_top = STACK_TOP; - else/* STACK_TOP uses is_32bit_task() but we want is_64 */ - stack_top = is_64 ? STACK_TOP_USER64 : STACK_TOP_USER32; - - if (!sp || (sp & (is_64 ? 7 : 3)) || sp > stack_top - (is_64 ? 32 : 16)) - return 0; - return 1; -} - -#ifdef CONFIG_PPC64 -/* - * On 64-bit we don't want to invoke hash_page on user addresses from - * interrupt context, so if the access faults, we read the page tables - * to find which page (if any) is mapped and access it directly. - */ -static int read_user_stack_slow(void __user *ptr, void *buf, int nb) -{ - int ret = -EFAULT; - pgd_t *pgdir; - pte_t *ptep, pte; - unsigned shift; - unsigned long addr = (unsigned long) ptr; - unsigned long offset; - unsigned long pfn, flags; - void *kaddr; - - pgdir = current->mm->pgd; - if (!pgdir) - return -EFAULT; - - local_irq_save(flags); - ptep = find_current_mm_pte(pgdir, addr, NULL, ); - if (!ptep) - goto err_out; - if (!shift) - shift = PAGE_SHIFT; - - /* align address to page boundary */ - offset = addr & ((1UL << shift) - 1); - - pte = READ_ONCE(*ptep); - if (!pte_present(pte) || !pte_user(pte)) - goto err_out; - pfn = pte_pfn(pte); - if (!page_is_ram(pfn)) - goto err_out; - - /* no highmem to worry about here */ - kaddr = pfn_to_kaddr(pfn); - memcpy(buf, kaddr + offset, nb); - ret = 0; -err_out: - local_irq_restore(flags); - return ret; -} - -static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned long) || - ((unsigned long)ptr & 7)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 8); -} - -/* - * 64-bit user processes use the same stack frame for RT and non-RT signals. - */ -struct signal_frame_64 { - chardummy[__SIGNAL_FRAMESIZE]; - struct ucontext uc; - unsigned long unused[2]; - unsigned inttramp[6]; - struct siginfo *pinfo; - void*puc; - struct siginfo info; - charabigap[288]; -}; - -static int is_sigreturn_64_address(unsigned long nip, unsigned long fp) -{ - if (nip == fp + offsetof(struct signal_frame_64, tramp)) - return 1; - if (vdso64_rt_sigtramp && current->mm->context.vdso_base && - nip == current->mm->context.vdso_base + vdso64_rt_sigtramp) - return 1; - retur
[PATCH v9 2/8] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->
[PATCH v9 1/8] powerpc: Add back __ARCH_WANT_SYS_LLSEEK macro
This partially reverts commit caf6f9c8a326 ("asm-generic: Remove unneeded __ARCH_WANT_SYS_LLSEEK macro") When CONFIG_COMPAT is disabled on ppc64 the kernel does not build. There is resistance to both removing the llseek syscall from the 64bit syscall tables and building the llseek interface unconditionally. Link: https://lore.kernel.org/lkml/20190828151552.ga16...@infradead.org/ Link: https://lore.kernel.org/lkml/20190829214319.498c7de2@naga/ Signed-off-by: Michal Suchanek Reviewed-by: Arnd Bergmann --- arch/powerpc/include/asm/unistd.h | 1 + fs/read_write.c | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/arch/powerpc/include/asm/unistd.h b/arch/powerpc/include/asm/unistd.h index b0720c7c3fcf..700fcdac2e3c 100644 --- a/arch/powerpc/include/asm/unistd.h +++ b/arch/powerpc/include/asm/unistd.h @@ -31,6 +31,7 @@ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLD_GETRLIMIT #define __ARCH_WANT_SYS_OLD_UNAME diff --git a/fs/read_write.c b/fs/read_write.c index 5bbf587f5bc1..89aa2701dbeb 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -331,7 +331,8 @@ COMPAT_SYSCALL_DEFINE3(lseek, unsigned int, fd, compat_off_t, offset, unsigned i } #endif -#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) +#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) || \ + defined(__ARCH_WANT_SYS_LLSEEK) SYSCALL_DEFINE5(llseek, unsigned int, fd, unsigned long, offset_high, unsigned long, offset_low, loff_t __user *, result, unsigned int, whence) -- 2.23.0
[PATCH v9 7/8] powerpc/64: Make COMPAT user-selectable disabled on littleendian by default.
On bigendian ppc64 it is common to have 32bit legacy binaries but much less so on littleendian. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- v3: make configurable --- arch/powerpc/Kconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..b0339e892329 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -264,8 +264,9 @@ config PANIC_TIMEOUT default 180 config COMPAT - bool - default y if PPC64 + bool "Enable support for 32bit binaries" + depends on PPC64 + default y if !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.23.0
[PATCH v9 3/8] powerpc/perf: consolidate read_user_stack_32
There are two almost identical copies for 32bit and 64bit. The function is used only in 32bit code which will be split out in next patch so consolidate to one function. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- v6: new patch v8: move the consolidated function out of the ifdef block. --- arch/powerpc/perf/callchain.c | 59 +++ 1 file changed, 25 insertions(+), 34 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index c84bbd4298a0..d86bdbffda9e 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -165,22 +165,6 @@ static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) return read_user_stack_slow(ptr, ret, 8); } -static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || - ((unsigned long)ptr & 3)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 4); -} - static inline int valid_user_sp(unsigned long sp, int is_64) { if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) @@ -295,25 +279,9 @@ static inline int current_is_64bit(void) } #else /* CONFIG_PPC64 */ -/* - * On 32-bit we just access the address and let hash_page create a - * HPTE if necessary, so there is no need to fall back to reading - * the page tables. Since this is called at interrupt level, - * do_page_fault() won't treat a DSI as a page fault. - */ -static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) +static int read_user_stack_slow(void __user *ptr, void *buf, int nb) { - int rc; - - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || - ((unsigned long)ptr & 3)) - return -EFAULT; - - pagefault_disable(); - rc = __get_user_inatomic(*ret, ptr); - pagefault_enable(); - - return rc; + return 0; } static inline void perf_callchain_user_64(struct perf_callchain_entry_ctx *entry, @@ -341,6 +309,29 @@ static inline int valid_user_sp(unsigned long sp, int is_64) #endif /* CONFIG_PPC64 */ +/* + * On 32-bit we just access the address and let hash_page create a + * HPTE if necessary, so there is no need to fall back to reading + * the page tables. Since this is called at interrupt level, + * do_page_fault() won't treat a DSI as a page fault. + */ +static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) +{ + int rc; + + if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || + ((unsigned long)ptr & 3)) + return -EFAULT; + + pagefault_disable(); + rc = __get_user_inatomic(*ret, ptr); + pagefault_enable(); + + if (IS_ENABLED(CONFIG_PPC64) && rc) + return read_user_stack_slow(ptr, ret, 4); + return rc; +} + /* * Layout for non-RT signal frames */ -- 2.23.0
[PATCH v9 6/8] powerpc/64: make buildable without CONFIG_COMPAT
There are numerous references to 32bit functions in generic and 64bit code so ifdef them out. Signed-off-by: Michal Suchanek --- v2: - fix 32bit ifdef condition in signal.c - simplify the compat ifdef condition in vdso.c - 64bit is redundant - simplify the compat ifdef condition in callchain.c - 64bit is redundant v3: - use IS_ENABLED and maybe_unused where possible - do not ifdef declarations - clean up Makefile v4: - further makefile cleanup - simplify is_32bit_task conditions - avoid ifdef in condition by using return v5: - avoid unreachable code on 32bit - make is_current_64bit constant on !COMPAT - add stub perf_callchain_user_32 to avoid some ifdefs v6: - consolidate current_is_64bit v7: - remove leftover perf_callchain_user_32 stub from previous series version v8: - fix build again - too trigger-happy with stub removal - remove a vdso.c hunk that causes warning according to kbuild test robot v9: - removed current_is_64bit in previous patch --- arch/powerpc/include/asm/thread_info.h | 4 ++-- arch/powerpc/kernel/Makefile | 7 +++ arch/powerpc/kernel/entry_64.S | 2 ++ arch/powerpc/kernel/signal.c | 3 +-- arch/powerpc/kernel/syscall_64.c | 6 ++ arch/powerpc/kernel/vdso.c | 3 ++- arch/powerpc/perf/callchain.c | 8 +++- 7 files changed, 19 insertions(+), 14 deletions(-) diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h index 8e1d0195ac36..c128d8a48ea3 100644 --- a/arch/powerpc/include/asm/thread_info.h +++ b/arch/powerpc/include/asm/thread_info.h @@ -144,10 +144,10 @@ static inline bool test_thread_local_flags(unsigned int flags) return (ti->local_flags & flags) != 0; } -#ifdef CONFIG_PPC64 +#ifdef CONFIG_COMPAT #define is_32bit_task()(test_thread_flag(TIF_32BIT)) #else -#define is_32bit_task()(1) +#define is_32bit_task()(IS_ENABLED(CONFIG_PPC32)) #endif #if defined(CONFIG_PPC64) diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 1d646a94d96c..9d8772e863b9 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile @@ -44,16 +44,15 @@ CFLAGS_btext.o += -DDISABLE_BRANCH_PROFILING endif obj-y := cputable.o ptrace.o syscalls.o \ - irq.o align.o signal_32.o pmc.o vdso.o \ + irq.o align.o signal_$(BITS).o pmc.o vdso.o \ process.o systbl.o idle.o \ signal.o sysfs.o cacheinfo.o time.o \ prom.o traps.o setup-common.o \ udbg.o misc.o io.o misc_$(BITS).o \ of_platform.o prom_parse.o -obj-$(CONFIG_PPC64)+= setup_64.o sys_ppc32.o \ - signal_64.o ptrace32.o \ - paca.o nvram_64.o firmware.o \ +obj-$(CONFIG_PPC64)+= setup_64.o paca.o nvram_64.o firmware.o \ syscall_64.o +obj-$(CONFIG_COMPAT) += sys_ppc32.o ptrace32.o signal_32.o obj-$(CONFIG_VDSO32) += vdso32/ obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 15bc2a872a76..cd390300930c 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -51,8 +51,10 @@ SYS_CALL_TABLE: .tc sys_call_table[TC],sys_call_table +#ifdef CONFIG_COMPAT COMPAT_SYS_CALL_TABLE: .tc compat_sys_call_table[TC],compat_sys_call_table +#endif /* This value is used to mark exception frames on the stack. */ exception_marker: diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index 60436432399f..61678cb0e6a1 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -247,7 +247,6 @@ static void do_signal(struct task_struct *tsk) sigset_t *oldset = sigmask_to_save(); struct ksignal ksig = { .sig = 0 }; int ret; - int is32 = is_32bit_task(); BUG_ON(tsk != current); @@ -277,7 +276,7 @@ static void do_signal(struct task_struct *tsk) rseq_signal_deliver(, tsk->thread.regs); - if (is32) { + if (is_32bit_task()) { if (ksig.ka.sa.sa_flags & SA_SIGINFO) ret = handle_rt_signal32(, oldset, tsk); else diff --git a/arch/powerpc/kernel/syscall_64.c b/arch/powerpc/kernel/syscall_64.c index 3787ec54c727..65cb58b01aea 100644 --- a/arch/powerpc/kernel/syscall_64.c +++ b/arch/powerpc/kernel/syscall_64.c @@ -17,7 +17,6 @@ typedef long (*syscall_fn)(long, long, long, long, long, long); long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, unsigned long r0, struct pt_regs *regs) { - unsigned long ti_flags;
[PATCH v9 5/8] powerpc/perf: remove current_is_64bit()
Since commit ed1cd6deb013 ("powerpc: Activate CONFIG_THREAD_INFO_IN_TASK") current_is_64bit() is quivalent to !is_32bit_task(). Remove the redundant function. Link: https://github.com/linuxppc/issues/issues/275 Link: https://lkml.org/lkml/2019/9/12/540 Fixes: linuxppc#275 Suggested-by: Christophe Leroy Signed-off-by: Michal Suchanek --- arch/powerpc/perf/callchain.c | 17 + 1 file changed, 1 insertion(+), 16 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index 7863ee0a0e69..fbf76cb01026 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -275,16 +275,6 @@ static void perf_callchain_user_64(struct perf_callchain_entry_ctx *entry, } } -static inline int current_is_64bit(void) -{ - /* -* We can't use test_thread_flag() here because we may be on an -* interrupt stack, and the thread flags don't get copied over -* from the thread_info on the main stack to the interrupt stack. -*/ - return !test_ti_thread_flag(task_thread_info(current), TIF_32BIT); -} - #else /* CONFIG_PPC64 */ static int read_user_stack_slow(void __user *ptr, void *buf, int nb) { @@ -296,11 +286,6 @@ static inline void perf_callchain_user_64(struct perf_callchain_entry_ctx *entry { } -static inline int current_is_64bit(void) -{ - return 0; -} - #define __SIGNAL_FRAMESIZE32 __SIGNAL_FRAMESIZE #define sigcontext32 sigcontext #define mcontext32 mcontext @@ -477,7 +462,7 @@ static void perf_callchain_user_32(struct perf_callchain_entry_ctx *entry, void perf_callchain_user(struct perf_callchain_entry_ctx *entry, struct pt_regs *regs) { - if (current_is_64bit()) + if (!is_32bit_task()) perf_callchain_user_64(entry, regs); else perf_callchain_user_32(entry, regs); -- 2.23.0
[PATCH] powerpc/perf: remove current_is_64bit()
Since commit ed1cd6deb013 ("powerpc: Activate CONFIG_THREAD_INFO_IN_TASK") current_is_64bit() is quivalent to !is_32bit_task(). Remove the redundant function. Link: https://github.com/linuxppc/issues/issues/275 Link: https://lkml.org/lkml/2019/9/12/540 Fixes: linuxppc#275 Suggested-by: Christophe Leroy Signed-off-by: Michal Suchanek --- arch/powerpc/perf/callchain.c | 14 +- 1 file changed, 1 insertion(+), 13 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index 8f30f1b47c78..dd5051015008 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -100,22 +100,10 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } -static inline int current_is_64bit(void) -{ - if (!IS_ENABLED(CONFIG_COMPAT)) - return IS_ENABLED(CONFIG_PPC64); - /* -* We can't use test_thread_flag() here because we may be on an -* interrupt stack, and the thread flags don't get copied over -* from the thread_info on the main stack to the interrupt stack. -*/ - return !test_ti_thread_flag(task_thread_info(current), TIF_32BIT); -} - void perf_callchain_user(struct perf_callchain_entry_ctx *entry, struct pt_regs *regs) { - if (current_is_64bit()) + if (!is_32bit_task()) perf_callchain_user_64(entry, regs); else perf_callchain_user_32(entry, regs); -- 2.23.0
[PATCH v8 0/7] Disable compat cruft on ppc64le v8
Less code means less bugs so add a knob to skip the compat stuff. This is tested on ppc64le top of https://patchwork.ozlabs.org/patch/1153850/ https://patchwork.ozlabs.org/patch/1158412/ Changes in v2: saner CONFIG_COMPAT ifdefs Changes in v3: - change llseek to 32bit instead of builing it unconditionally in fs - clanup the makefile conditionals - remove some ifdefs or convert to IS_DEFINED where possible Changes in v4: - cleanup is_32bit_task and current_is_64bit - more makefile cleanup Changes in v5: - more current_is_64bit cleanup - split off callchain.c 32bit and 64bit parts Changes in v6: - cleanup makefile after split - consolidate read_user_stack_32 - fix some checkpatch warnings Changes in v7: - add back __ARCH_WANT_SYS_LLSEEK to fix build with llseek - remove leftover hunk - add review tags Changes in v8: - consolidate valid_user_sp to fix it in the split callchain.c - fix build errors/warnings with PPC64 !COMPAT and PPC32 Michal Suchanek (7): powerpc: Add back __ARCH_WANT_SYS_LLSEEK macro powerpc: move common register copy functions from signal_32.c to signal.c powerpc/perf: consolidate read_user_stack_32 powerpc/perf: consolidate valid_user_sp powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Make COMPAT user-selectable disabled on littleendian by default. powerpc/perf: split callchain.c by bitness arch/powerpc/Kconfig | 5 +- arch/powerpc/include/asm/thread_info.h | 4 +- arch/powerpc/include/asm/unistd.h | 1 + arch/powerpc/kernel/Makefile | 7 +- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 144 +- arch/powerpc/kernel/signal_32.c| 140 - arch/powerpc/kernel/syscall_64.c | 6 +- arch/powerpc/kernel/vdso.c | 3 +- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c | 377 + arch/powerpc/perf/callchain.h | 25 ++ arch/powerpc/perf/callchain_32.c | 197 + arch/powerpc/perf/callchain_64.c | 178 fs/read_write.c| 3 +- 15 files changed, 566 insertions(+), 531 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c -- 2.23.0
[PATCH v8 2/7] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->
[PATCH v8 6/7] powerpc/64: Make COMPAT user-selectable disabled on littleendian by default.
On bigendian ppc64 it is common to have 32bit legacy binaries but much less so on littleendian. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- v3: make configurable --- arch/powerpc/Kconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..b0339e892329 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -264,8 +264,9 @@ config PANIC_TIMEOUT default 180 config COMPAT - bool - default y if PPC64 + bool "Enable support for 32bit binaries" + depends on PPC64 + default y if !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.23.0
[PATCH v8 5/7] powerpc/64: make buildable without CONFIG_COMPAT
There are numerous references to 32bit functions in generic and 64bit code so ifdef them out. Signed-off-by: Michal Suchanek --- v2: - fix 32bit ifdef condition in signal.c - simplify the compat ifdef condition in vdso.c - 64bit is redundant - simplify the compat ifdef condition in callchain.c - 64bit is redundant v3: - use IS_ENABLED and maybe_unused where possible - do not ifdef declarations - clean up Makefile v4: - further makefile cleanup - simplify is_32bit_task conditions - avoid ifdef in condition by using return v5: - avoid unreachable code on 32bit - make is_current_64bit constant on !COMPAT - add stub perf_callchain_user_32 to avoid some ifdefs v6: - consolidate current_is_64bit v7: - remove leftover perf_callchain_user_32 stub from previous series version v8: - fix build again - too trigger-happy with stub removal - remove a vdso.c hunk that causes warning according to kbuild test robot --- arch/powerpc/include/asm/thread_info.h | 4 +-- arch/powerpc/kernel/Makefile | 7 ++--- arch/powerpc/kernel/entry_64.S | 2 ++ arch/powerpc/kernel/signal.c | 3 +- arch/powerpc/kernel/syscall_64.c | 6 ++-- arch/powerpc/kernel/vdso.c | 3 +- arch/powerpc/perf/callchain.c | 39 ++ 7 files changed, 33 insertions(+), 31 deletions(-) diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h index 8e1d0195ac36..c128d8a48ea3 100644 --- a/arch/powerpc/include/asm/thread_info.h +++ b/arch/powerpc/include/asm/thread_info.h @@ -144,10 +144,10 @@ static inline bool test_thread_local_flags(unsigned int flags) return (ti->local_flags & flags) != 0; } -#ifdef CONFIG_PPC64 +#ifdef CONFIG_COMPAT #define is_32bit_task()(test_thread_flag(TIF_32BIT)) #else -#define is_32bit_task()(1) +#define is_32bit_task()(IS_ENABLED(CONFIG_PPC32)) #endif #if defined(CONFIG_PPC64) diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 1d646a94d96c..9d8772e863b9 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile @@ -44,16 +44,15 @@ CFLAGS_btext.o += -DDISABLE_BRANCH_PROFILING endif obj-y := cputable.o ptrace.o syscalls.o \ - irq.o align.o signal_32.o pmc.o vdso.o \ + irq.o align.o signal_$(BITS).o pmc.o vdso.o \ process.o systbl.o idle.o \ signal.o sysfs.o cacheinfo.o time.o \ prom.o traps.o setup-common.o \ udbg.o misc.o io.o misc_$(BITS).o \ of_platform.o prom_parse.o -obj-$(CONFIG_PPC64)+= setup_64.o sys_ppc32.o \ - signal_64.o ptrace32.o \ - paca.o nvram_64.o firmware.o \ +obj-$(CONFIG_PPC64)+= setup_64.o paca.o nvram_64.o firmware.o \ syscall_64.o +obj-$(CONFIG_COMPAT) += sys_ppc32.o ptrace32.o signal_32.o obj-$(CONFIG_VDSO32) += vdso32/ obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 15bc2a872a76..cd390300930c 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -51,8 +51,10 @@ SYS_CALL_TABLE: .tc sys_call_table[TC],sys_call_table +#ifdef CONFIG_COMPAT COMPAT_SYS_CALL_TABLE: .tc compat_sys_call_table[TC],compat_sys_call_table +#endif /* This value is used to mark exception frames on the stack. */ exception_marker: diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index 60436432399f..61678cb0e6a1 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -247,7 +247,6 @@ static void do_signal(struct task_struct *tsk) sigset_t *oldset = sigmask_to_save(); struct ksignal ksig = { .sig = 0 }; int ret; - int is32 = is_32bit_task(); BUG_ON(tsk != current); @@ -277,7 +276,7 @@ static void do_signal(struct task_struct *tsk) rseq_signal_deliver(, tsk->thread.regs); - if (is32) { + if (is_32bit_task()) { if (ksig.ka.sa.sa_flags & SA_SIGINFO) ret = handle_rt_signal32(, oldset, tsk); else diff --git a/arch/powerpc/kernel/syscall_64.c b/arch/powerpc/kernel/syscall_64.c index 3787ec54c727..65cb58b01aea 100644 --- a/arch/powerpc/kernel/syscall_64.c +++ b/arch/powerpc/kernel/syscall_64.c @@ -17,7 +17,6 @@ typedef long (*syscall_fn)(long, long, long, long, long, long); long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, unsigned long r0, struct pt_regs *regs) { - unsigned long ti_flags; syscall_fn f; BUG_
[PATCH v8 4/7] powerpc/perf: consolidate valid_user_sp
Merge the 32bit and 64bit version. Halve the check constants on 32bit. Use STACK_TOP since it is defined. This removes a page from the valid 32bit area on 64bit: #define TASK_SIZE_USER32 (0x0001UL - (1 * PAGE_SIZE)) #define STACK_TOP_USER32 TASK_SIZE_USER32 Signed-off-by: Michal Suchanek --- v8: new patch --- arch/powerpc/perf/callchain.c | 28 ++-- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index d86bdbffda9e..7863ee0a0e69 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -102,6 +102,20 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } +static inline int valid_user_sp(unsigned long sp, int is_64) +{ + unsigned long stack_top; + + if (IS_ENABLED(CONFIG_PPC32)) + stack_top = STACK_TOP; + else/* STACK_TOP uses is_32bit_task() but we want is_64 */ + stack_top = is_64 ? STACK_TOP_USER64 : STACK_TOP_USER32; + + if (!sp || (sp & (is_64 ? 7 : 3)) || sp > stack_top - (is_64 ? 32 : 16)) + return 0; + return 1; +} + #ifdef CONFIG_PPC64 /* * On 64-bit we don't want to invoke hash_page on user addresses from @@ -165,13 +179,6 @@ static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) return read_user_stack_slow(ptr, ret, 8); } -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) - return 0; - return 1; -} - /* * 64-bit user processes use the same stack frame for RT and non-RT signals. */ @@ -294,13 +301,6 @@ static inline int current_is_64bit(void) return 0; } -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - if (!sp || (sp & 7) || sp > TASK_SIZE - 32) - return 0; - return 1; -} - #define __SIGNAL_FRAMESIZE32 __SIGNAL_FRAMESIZE #define sigcontext32 sigcontext #define mcontext32 mcontext -- 2.23.0
[PATCH v8 7/7] powerpc/perf: split callchain.c by bitness
Building callchain.c with !COMPAT proved quite ugly with all the defines. Splitting out the 32bit and 64bit parts looks better. No code change intended. Signed-off-by: Michal Suchanek --- v6: - move current_is_64bit consolidetaion to earlier patch - move defines to the top of callchain_32.c - Makefile cleanup v8: - fix valid_user_sp --- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c| 367 +-- arch/powerpc/perf/callchain.h| 25 +++ arch/powerpc/perf/callchain_32.c | 197 + arch/powerpc/perf/callchain_64.c | 178 +++ 5 files changed, 405 insertions(+), 367 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c diff --git a/arch/powerpc/perf/Makefile b/arch/powerpc/perf/Makefile index c155dcbb8691..53d614e98537 100644 --- a/arch/powerpc/perf/Makefile +++ b/arch/powerpc/perf/Makefile @@ -1,6 +1,9 @@ # SPDX-License-Identifier: GPL-2.0 -obj-$(CONFIG_PERF_EVENTS) += callchain.o perf_regs.o +obj-$(CONFIG_PERF_EVENTS) += callchain.o callchain_$(BITS).o perf_regs.o +ifdef CONFIG_COMPAT +obj-$(CONFIG_PERF_EVENTS) += callchain_32.o +endif obj-$(CONFIG_PPC_PERF_CTRS)+= core-book3s.o bhrb.o obj64-$(CONFIG_PPC_PERF_CTRS) += ppc970-pmu.o power5-pmu.o \ diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index 2c8b0a9534fd..8f30f1b47c78 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -15,11 +15,9 @@ #include #include #include -#ifdef CONFIG_COMPAT -#include "../kernel/ppc32.h" -#endif #include +#include "callchain.h" /* * Is sp valid as the address of the next kernel stack frame after prev_sp? @@ -102,369 +100,6 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - unsigned long stack_top; - - if (IS_ENABLED(CONFIG_PPC32)) - stack_top = STACK_TOP; - else/* STACK_TOP uses is_32bit_task() but we want is_64 */ - stack_top = is_64 ? STACK_TOP_USER64 : STACK_TOP_USER32; - - if (!sp || (sp & (is_64 ? 7 : 3)) || sp > stack_top - (is_64 ? 32 : 16)) - return 0; - return 1; -} - -#ifdef CONFIG_PPC64 -/* - * On 64-bit we don't want to invoke hash_page on user addresses from - * interrupt context, so if the access faults, we read the page tables - * to find which page (if any) is mapped and access it directly. - */ -static int read_user_stack_slow(void __user *ptr, void *buf, int nb) -{ - int ret = -EFAULT; - pgd_t *pgdir; - pte_t *ptep, pte; - unsigned shift; - unsigned long addr = (unsigned long) ptr; - unsigned long offset; - unsigned long pfn, flags; - void *kaddr; - - pgdir = current->mm->pgd; - if (!pgdir) - return -EFAULT; - - local_irq_save(flags); - ptep = find_current_mm_pte(pgdir, addr, NULL, ); - if (!ptep) - goto err_out; - if (!shift) - shift = PAGE_SHIFT; - - /* align address to page boundary */ - offset = addr & ((1UL << shift) - 1); - - pte = READ_ONCE(*ptep); - if (!pte_present(pte) || !pte_user(pte)) - goto err_out; - pfn = pte_pfn(pte); - if (!page_is_ram(pfn)) - goto err_out; - - /* no highmem to worry about here */ - kaddr = pfn_to_kaddr(pfn); - memcpy(buf, kaddr + offset, nb); - ret = 0; -err_out: - local_irq_restore(flags); - return ret; -} - -static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned long) || - ((unsigned long)ptr & 7)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 8); -} - -/* - * 64-bit user processes use the same stack frame for RT and non-RT signals. - */ -struct signal_frame_64 { - chardummy[__SIGNAL_FRAMESIZE]; - struct ucontext uc; - unsigned long unused[2]; - unsigned inttramp[6]; - struct siginfo *pinfo; - void*puc; - struct siginfo info; - charabigap[288]; -}; - -static int is_sigreturn_64_address(unsigned long nip, unsigned long fp) -{ - if (nip == fp + offsetof(struct signal_frame_64, tramp)) - return 1; - if (vdso64_rt_sigtramp && current->mm->context.vdso_base && - nip == current->mm->context.vdso_base + vdso64_rt_sigtramp) - return 1; - retur
[PATCH v8 3/7] powerpc/perf: consolidate read_user_stack_32
There are two almost identical copies for 32bit and 64bit. The function is used only in 32bit code which will be split out in next patch so consolidate to one function. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- v6: new patch v8: move the consolidated function out of the ifdef block. --- arch/powerpc/perf/callchain.c | 59 +++ 1 file changed, 25 insertions(+), 34 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index c84bbd4298a0..d86bdbffda9e 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -165,22 +165,6 @@ static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) return read_user_stack_slow(ptr, ret, 8); } -static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || - ((unsigned long)ptr & 3)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 4); -} - static inline int valid_user_sp(unsigned long sp, int is_64) { if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) @@ -295,25 +279,9 @@ static inline int current_is_64bit(void) } #else /* CONFIG_PPC64 */ -/* - * On 32-bit we just access the address and let hash_page create a - * HPTE if necessary, so there is no need to fall back to reading - * the page tables. Since this is called at interrupt level, - * do_page_fault() won't treat a DSI as a page fault. - */ -static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) +static int read_user_stack_slow(void __user *ptr, void *buf, int nb) { - int rc; - - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || - ((unsigned long)ptr & 3)) - return -EFAULT; - - pagefault_disable(); - rc = __get_user_inatomic(*ret, ptr); - pagefault_enable(); - - return rc; + return 0; } static inline void perf_callchain_user_64(struct perf_callchain_entry_ctx *entry, @@ -341,6 +309,29 @@ static inline int valid_user_sp(unsigned long sp, int is_64) #endif /* CONFIG_PPC64 */ +/* + * On 32-bit we just access the address and let hash_page create a + * HPTE if necessary, so there is no need to fall back to reading + * the page tables. Since this is called at interrupt level, + * do_page_fault() won't treat a DSI as a page fault. + */ +static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) +{ + int rc; + + if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || + ((unsigned long)ptr & 3)) + return -EFAULT; + + pagefault_disable(); + rc = __get_user_inatomic(*ret, ptr); + pagefault_enable(); + + if (IS_ENABLED(CONFIG_PPC64) && rc) + return read_user_stack_slow(ptr, ret, 4); + return rc; +} + /* * Layout for non-RT signal frames */ -- 2.23.0
[PATCH v8 1/7] powerpc: Add back __ARCH_WANT_SYS_LLSEEK macro
This partially reverts commit caf6f9c8a326 ("asm-generic: Remove unneeded __ARCH_WANT_SYS_LLSEEK macro") When CONFIG_COMPAT is disabled on ppc64 the kernel does not build. There is resistance to both removing the llseek syscall from the 64bit syscall tables and building the llseek interface unconditionally. Link: https://lore.kernel.org/lkml/20190828151552.ga16...@infradead.org/ Link: https://lore.kernel.org/lkml/20190829214319.498c7de2@naga/ Signed-off-by: Michal Suchanek Reviewed-by: Arnd Bergmann --- arch/powerpc/include/asm/unistd.h | 1 + fs/read_write.c | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/arch/powerpc/include/asm/unistd.h b/arch/powerpc/include/asm/unistd.h index b0720c7c3fcf..700fcdac2e3c 100644 --- a/arch/powerpc/include/asm/unistd.h +++ b/arch/powerpc/include/asm/unistd.h @@ -31,6 +31,7 @@ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLD_GETRLIMIT #define __ARCH_WANT_SYS_OLD_UNAME diff --git a/fs/read_write.c b/fs/read_write.c index 5bbf587f5bc1..89aa2701dbeb 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -331,7 +331,8 @@ COMPAT_SYSCALL_DEFINE3(lseek, unsigned int, fd, compat_off_t, offset, unsigned i } #endif -#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) +#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) || \ + defined(__ARCH_WANT_SYS_LLSEEK) SYSCALL_DEFINE5(llseek, unsigned int, fd, unsigned long, offset_high, unsigned long, offset_low, loff_t __user *, result, unsigned int, whence) -- 2.23.0
[PATCH] net/ibmvnic: Fix missing { in __ibmvnic_reset
Commit 1c2977c09499 ("net/ibmvnic: free reset work of removed device from queue") adds a } without corresponding { causing build break. Fixes: 1c2977c09499 ("net/ibmvnic: free reset work of removed device from queue") Signed-off-by: Michal Suchanek --- drivers/net/ethernet/ibm/ibmvnic.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/net/ethernet/ibm/ibmvnic.c b/drivers/net/ethernet/ibm/ibmvnic.c index 6644cabc8e75..5cb55ea671e3 100644 --- a/drivers/net/ethernet/ibm/ibmvnic.c +++ b/drivers/net/ethernet/ibm/ibmvnic.c @@ -1984,7 +1984,7 @@ static void __ibmvnic_reset(struct work_struct *work) rwi = get_next_rwi(adapter); while (rwi) { if (adapter->state == VNIC_REMOVING || - adapter->state == VNIC_REMOVED) + adapter->state == VNIC_REMOVED) { kfree(rwi); rc = EBUSY; break; -- 2.22.0
[PATCH] Revert "powerpc: Add barrier_nospec to raw_copy_in_user()"
This reverts commit 6fbcdd59094ade30db63f32316e9502425d7b256. Not needed. Data handled by raw_copy_in_user must be loaded through copy_from_user to be used in the kernel which already has the barrier. Signed-off-by: Michal Suchanek --- arch/powerpc/include/asm/uaccess.h | 1 - 1 file changed, 1 deletion(-) diff --git a/arch/powerpc/include/asm/uaccess.h b/arch/powerpc/include/asm/uaccess.h index 8b03eb44e876..76f34346b642 100644 --- a/arch/powerpc/include/asm/uaccess.h +++ b/arch/powerpc/include/asm/uaccess.h @@ -312,7 +312,6 @@ raw_copy_in_user(void __user *to, const void __user *from, unsigned long n) { unsigned long ret; - barrier_nospec(); allow_user_access(to, from, n); ret = __copy_tofrom_user(to, from, n); prevent_user_access(to, from, n); -- 2.22.0
[PATCH v7 6/6] powerpc/perf: split callchain.c by bitness
Building callchain.c with !COMPAT proved quite ugly with all the defines. Splitting out the 32bit and 64bit parts looks better. No code change intended. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- v6: - move current_is_64bit consolidetaion to earlier patch - move defines to the top of callchain_32.c - Makefile cleanup --- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c| 365 +-- arch/powerpc/perf/callchain.h| 11 + arch/powerpc/perf/callchain_32.c | 204 + arch/powerpc/perf/callchain_64.c | 185 5 files changed, 405 insertions(+), 365 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c diff --git a/arch/powerpc/perf/Makefile b/arch/powerpc/perf/Makefile index c155dcbb8691..53d614e98537 100644 --- a/arch/powerpc/perf/Makefile +++ b/arch/powerpc/perf/Makefile @@ -1,6 +1,9 @@ # SPDX-License-Identifier: GPL-2.0 -obj-$(CONFIG_PERF_EVENTS) += callchain.o perf_regs.o +obj-$(CONFIG_PERF_EVENTS) += callchain.o callchain_$(BITS).o perf_regs.o +ifdef CONFIG_COMPAT +obj-$(CONFIG_PERF_EVENTS) += callchain_32.o +endif obj-$(CONFIG_PPC_PERF_CTRS)+= core-book3s.o bhrb.o obj64-$(CONFIG_PPC_PERF_CTRS) += ppc970-pmu.o power5-pmu.o \ diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index 9b8dc822f531..8f30f1b47c78 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -15,11 +15,9 @@ #include #include #include -#ifdef CONFIG_COMPAT -#include "../kernel/ppc32.h" -#endif #include +#include "callchain.h" /* * Is sp valid as the address of the next kernel stack frame after prev_sp? @@ -102,367 +100,6 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } -#ifdef CONFIG_PPC64 -/* - * On 64-bit we don't want to invoke hash_page on user addresses from - * interrupt context, so if the access faults, we read the page tables - * to find which page (if any) is mapped and access it directly. - */ -static int read_user_stack_slow(void __user *ptr, void *buf, int nb) -{ - int ret = -EFAULT; - pgd_t *pgdir; - pte_t *ptep, pte; - unsigned shift; - unsigned long addr = (unsigned long) ptr; - unsigned long offset; - unsigned long pfn, flags; - void *kaddr; - - pgdir = current->mm->pgd; - if (!pgdir) - return -EFAULT; - - local_irq_save(flags); - ptep = find_current_mm_pte(pgdir, addr, NULL, ); - if (!ptep) - goto err_out; - if (!shift) - shift = PAGE_SHIFT; - - /* align address to page boundary */ - offset = addr & ((1UL << shift) - 1); - - pte = READ_ONCE(*ptep); - if (!pte_present(pte) || !pte_user(pte)) - goto err_out; - pfn = pte_pfn(pte); - if (!page_is_ram(pfn)) - goto err_out; - - /* no highmem to worry about here */ - kaddr = pfn_to_kaddr(pfn); - memcpy(buf, kaddr + offset, nb); - ret = 0; -err_out: - local_irq_restore(flags); - return ret; -} - -static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned long) || - ((unsigned long)ptr & 7)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 8); -} - -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) - return 0; - return 1; -} - -/* - * 64-bit user processes use the same stack frame for RT and non-RT signals. - */ -struct signal_frame_64 { - chardummy[__SIGNAL_FRAMESIZE]; - struct ucontext uc; - unsigned long unused[2]; - unsigned inttramp[6]; - struct siginfo *pinfo; - void*puc; - struct siginfo info; - charabigap[288]; -}; - -static int is_sigreturn_64_address(unsigned long nip, unsigned long fp) -{ - if (nip == fp + offsetof(struct signal_frame_64, tramp)) - return 1; - if (vdso64_rt_sigtramp && current->mm->context.vdso_base && - nip == current->mm->context.vdso_base + vdso64_rt_sigtramp) - return 1; - return 0; -} - -/* - * Do some sanity checking on the signal frame pointed to by sp. - * We check the pinfo and puc pointers in the frame. - */ -static int sane_signal_64_frame(unsigned long sp) -{ - struct signal_frame_64 __user *sf; -
[PATCH v7 4/6] powerpc/64: make buildable without CONFIG_COMPAT
There are numerous references to 32bit functions in generic and 64bit code so ifdef them out. Signed-off-by: Michal Suchanek --- v2: - fix 32bit ifdef condition in signal.c - simplify the compat ifdef condition in vdso.c - 64bit is redundant - simplify the compat ifdef condition in callchain.c - 64bit is redundant v3: - use IS_ENABLED and maybe_unused where possible - do not ifdef declarations - clean up Makefile v4: - further makefile cleanup - simplify is_32bit_task conditions - avoid ifdef in condition by using return v5: - avoid unreachable code on 32bit - make is_current_64bit constant on !COMPAT - add stub perf_callchain_user_32 to avoid some ifdefs v6: - consolidate current_is_64bit v7: - remove leftover perf_callchain_user_32 stub from previous series version --- arch/powerpc/include/asm/thread_info.h | 4 ++-- arch/powerpc/kernel/Makefile | 7 +++--- arch/powerpc/kernel/entry_64.S | 2 ++ arch/powerpc/kernel/signal.c | 3 +-- arch/powerpc/kernel/syscall_64.c | 6 ++--- arch/powerpc/kernel/vdso.c | 5 ++--- arch/powerpc/perf/callchain.c | 31 +- 7 files changed, 27 insertions(+), 31 deletions(-) diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h index 8e1d0195ac36..c128d8a48ea3 100644 --- a/arch/powerpc/include/asm/thread_info.h +++ b/arch/powerpc/include/asm/thread_info.h @@ -144,10 +144,10 @@ static inline bool test_thread_local_flags(unsigned int flags) return (ti->local_flags & flags) != 0; } -#ifdef CONFIG_PPC64 +#ifdef CONFIG_COMPAT #define is_32bit_task()(test_thread_flag(TIF_32BIT)) #else -#define is_32bit_task()(1) +#define is_32bit_task()(IS_ENABLED(CONFIG_PPC32)) #endif #if defined(CONFIG_PPC64) diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 1d646a94d96c..9d8772e863b9 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile @@ -44,16 +44,15 @@ CFLAGS_btext.o += -DDISABLE_BRANCH_PROFILING endif obj-y := cputable.o ptrace.o syscalls.o \ - irq.o align.o signal_32.o pmc.o vdso.o \ + irq.o align.o signal_$(BITS).o pmc.o vdso.o \ process.o systbl.o idle.o \ signal.o sysfs.o cacheinfo.o time.o \ prom.o traps.o setup-common.o \ udbg.o misc.o io.o misc_$(BITS).o \ of_platform.o prom_parse.o -obj-$(CONFIG_PPC64)+= setup_64.o sys_ppc32.o \ - signal_64.o ptrace32.o \ - paca.o nvram_64.o firmware.o \ +obj-$(CONFIG_PPC64)+= setup_64.o paca.o nvram_64.o firmware.o \ syscall_64.o +obj-$(CONFIG_COMPAT) += sys_ppc32.o ptrace32.o signal_32.o obj-$(CONFIG_VDSO32) += vdso32/ obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 2ec825a85f5b..a2dbf216f607 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -51,8 +51,10 @@ SYS_CALL_TABLE: .tc sys_call_table[TC],sys_call_table +#ifdef CONFIG_COMPAT COMPAT_SYS_CALL_TABLE: .tc compat_sys_call_table[TC],compat_sys_call_table +#endif /* This value is used to mark exception frames on the stack. */ exception_marker: diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index 60436432399f..61678cb0e6a1 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -247,7 +247,6 @@ static void do_signal(struct task_struct *tsk) sigset_t *oldset = sigmask_to_save(); struct ksignal ksig = { .sig = 0 }; int ret; - int is32 = is_32bit_task(); BUG_ON(tsk != current); @@ -277,7 +276,7 @@ static void do_signal(struct task_struct *tsk) rseq_signal_deliver(, tsk->thread.regs); - if (is32) { + if (is_32bit_task()) { if (ksig.ka.sa.sa_flags & SA_SIGINFO) ret = handle_rt_signal32(, oldset, tsk); else diff --git a/arch/powerpc/kernel/syscall_64.c b/arch/powerpc/kernel/syscall_64.c index 98ed970796d5..0d5cbbe54cf1 100644 --- a/arch/powerpc/kernel/syscall_64.c +++ b/arch/powerpc/kernel/syscall_64.c @@ -38,7 +38,6 @@ typedef long (*syscall_fn)(long, long, long, long, long, long); long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, unsigned long r0, struct pt_regs *regs) { - unsigned long ti_flags; syscall_fn f; BUG_ON(!(regs->msr & MSR_PR)); @@ -83,8 +82,7 @@ long system_call_exception(long r3, long r4, long r5, long
[PATCH v7 2/6] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->
[PATCH v7 5/6] powerpc/64: Make COMPAT user-selectable disabled on littleendian by default.
On bigendian ppc64 it is common to have 32bit legacy binaries but much less so on littleendian. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- v3: make configurable --- arch/powerpc/Kconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..b0339e892329 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -264,8 +264,9 @@ config PANIC_TIMEOUT default 180 config COMPAT - bool - default y if PPC64 + bool "Enable support for 32bit binaries" + depends on PPC64 + default y if !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.22.0
[PATCH v7 3/6] powerpc/perf: consolidate read_user_stack_32
There are two almost identical copies for 32bit and 64bit. The function is used only in 32bit code which will be split out in next patch so consolidate to one function. Signed-off-by: Michal Suchanek Reviewed-by: Christophe Leroy --- new patch in v6 --- arch/powerpc/perf/callchain.c | 25 + 1 file changed, 9 insertions(+), 16 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index c84bbd4298a0..b7cdcce20280 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -165,22 +165,6 @@ static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) return read_user_stack_slow(ptr, ret, 8); } -static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || - ((unsigned long)ptr & 3)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 4); -} - static inline int valid_user_sp(unsigned long sp, int is_64) { if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) @@ -295,6 +279,12 @@ static inline int current_is_64bit(void) } #else /* CONFIG_PPC64 */ +static int read_user_stack_slow(void __user *ptr, void *buf, int nb) +{ + return 0; +} +#endif /* CONFIG_PPC64 */ + /* * On 32-bit we just access the address and let hash_page create a * HPTE if necessary, so there is no need to fall back to reading @@ -313,9 +303,12 @@ static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) rc = __get_user_inatomic(*ret, ptr); pagefault_enable(); + if (IS_ENABLED(CONFIG_PPC64) && rc) + return read_user_stack_slow(ptr, ret, 4); return rc; } +#ifndef CONFIG_PPC64 static inline void perf_callchain_user_64(struct perf_callchain_entry_ctx *entry, struct pt_regs *regs) { -- 2.22.0
[PATCH v7 0/6] Disable compat cruft on ppc64le v7
Less code means less bugs so add a knob to skip the compat stuff. This is tested on ppc64le top of https://patchwork.ozlabs.org/cover/1153556/ Changes in v2: saner CONFIG_COMPAT ifdefs Changes in v3: - change llseek to 32bit instead of builing it unconditionally in fs - clanup the makefile conditionals - remove some ifdefs or convert to IS_DEFINED where possible Changes in v4: - cleanup is_32bit_task and current_is_64bit - more makefile cleanup Changes in v5: - more current_is_64bit cleanup - split off callchain.c 32bit and 64bit parts Changes in v6: - cleanup makefile after split - consolidate read_user_stack_32 - fix some checkpatch warnings Changes in v7: - add back __ARCH_WANT_SYS_LLSEEK to fix build with llseek - remove leftover hunk - add review tags Michal Suchanek (6): powerpc: Add back __ARCH_WANT_SYS_LLSEEK macro powerpc: move common register copy functions from signal_32.c to signal.c powerpc/perf: consolidate read_user_stack_32 powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Make COMPAT user-selectable disabled on littleendian by default. powerpc/perf: split callchain.c by bitness arch/powerpc/Kconfig | 5 +- arch/powerpc/include/asm/thread_info.h | 4 +- arch/powerpc/include/asm/unistd.h | 1 + arch/powerpc/kernel/Makefile | 7 +- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 144 +- arch/powerpc/kernel/signal_32.c| 140 - arch/powerpc/kernel/syscall_64.c | 6 +- arch/powerpc/kernel/vdso.c | 5 +- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c | 377 + arch/powerpc/perf/callchain.h | 11 + arch/powerpc/perf/callchain_32.c | 204 + arch/powerpc/perf/callchain_64.c | 185 fs/read_write.c| 3 +- 15 files changed, 566 insertions(+), 533 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c -- 2.22.0
[PATCH v7 1/6] powerpc: Add back __ARCH_WANT_SYS_LLSEEK macro
This partially reverts commit caf6f9c8a326 ("asm-generic: Remove unneeded __ARCH_WANT_SYS_LLSEEK macro") When CONFIG_COMPAT is disabled on ppc64 the kernel does not build. There is resistance to both removing the llseek syscall from the 64bit syscall tables and building the llseek interface unconditionally. Link: https://lore.kernel.org/lkml/20190828151552.ga16...@infradead.org/ Link: https://lore.kernel.org/lkml/20190829214319.498c7de2@naga/ Signed-off-by: Michal Suchanek Reviewed-by: Arnd Bergmann --- arch/powerpc/include/asm/unistd.h | 1 + fs/read_write.c | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/arch/powerpc/include/asm/unistd.h b/arch/powerpc/include/asm/unistd.h index b0720c7c3fcf..700fcdac2e3c 100644 --- a/arch/powerpc/include/asm/unistd.h +++ b/arch/powerpc/include/asm/unistd.h @@ -31,6 +31,7 @@ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLD_GETRLIMIT #define __ARCH_WANT_SYS_OLD_UNAME diff --git a/fs/read_write.c b/fs/read_write.c index 5bbf587f5bc1..89aa2701dbeb 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -331,7 +331,8 @@ COMPAT_SYSCALL_DEFINE3(lseek, unsigned int, fd, compat_off_t, offset, unsigned i } #endif -#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) +#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) || \ + defined(__ARCH_WANT_SYS_LLSEEK) SYSCALL_DEFINE5(llseek, unsigned int, fd, unsigned long, offset_high, unsigned long, offset_low, loff_t __user *, result, unsigned int, whence) -- 2.22.0
[no subject]
Subject: [PATCH] powerpc: Add back __ARCH_WANT_SYS_LLSEEK macro This partially reverts commit caf6f9c8a326 ("asm-generic: Remove unneeded __ARCH_WANT_SYS_LLSEEK macro") When CONFIG_COMPAT is disabled on ppc64 the kernel does not build. There is resistance to both removing the llseek syscall from the 64bit syscall tables and building the llseek interface unconditionally. Link: https://lore.kernel.org/lkml/20190828151552.ga16...@infradead.org/ Link: https://lore.kernel.org/lkml/20190829214319.498c7de2@naga/ Signed-off-by: Michal Suchanek --- arch/powerpc/include/asm/unistd.h | 1 + fs/read_write.c | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/arch/powerpc/include/asm/unistd.h b/arch/powerpc/include/asm/unistd.h index b0720c7c3fcf..700fcdac2e3c 100644 --- a/arch/powerpc/include/asm/unistd.h +++ b/arch/powerpc/include/asm/unistd.h @@ -31,6 +31,7 @@ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLD_GETRLIMIT #define __ARCH_WANT_SYS_OLD_UNAME diff --git a/fs/read_write.c b/fs/read_write.c index 5bbf587f5bc1..89aa2701dbeb 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -331,7 +331,8 @@ COMPAT_SYSCALL_DEFINE3(lseek, unsigned int, fd, compat_off_t, offset, unsigned i } #endif -#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) +#if !defined(CONFIG_64BIT) || defined(CONFIG_COMPAT) || \ + defined(__ARCH_WANT_SYS_LLSEEK) SYSCALL_DEFINE5(llseek, unsigned int, fd, unsigned long, offset_high, unsigned long, offset_low, loff_t __user *, result, unsigned int, whence) -- 2.22.0
[PATCH] Revert "asm-generic: Remove unneeded __ARCH_WANT_SYS_LLSEEK macro"
This reverts commit caf6f9c8a326cffd1d4b3ff3f1cfba75d159d70b. Maybe it was needed after all. When CONFIG_COMPAT is disabled on ppc64 the kernel does not build. There is resistance to both removing the llseek syscall from the 64bit syscall tables and building the llseek interface unconditionally. Link: https://lore.kernel.org/lkml/20190828151552.ga16...@infradead.org/ Link: https://lore.kernel.org/lkml/20190829214319.498c7de2@naga/ Signed-off-by: Michal Suchanek --- arch/arm/include/asm/unistd.h| 1 + arch/arm64/include/asm/unistd.h | 1 + arch/csky/include/asm/unistd.h | 2 +- arch/m68k/include/asm/unistd.h | 1 + arch/microblaze/include/asm/unistd.h | 1 + arch/mips/include/asm/unistd.h | 1 + arch/parisc/include/asm/unistd.h | 1 + arch/powerpc/include/asm/unistd.h| 1 + arch/s390/include/asm/unistd.h | 1 + arch/sh/include/asm/unistd.h | 1 + arch/sparc/include/asm/unistd.h | 1 + arch/x86/include/asm/unistd.h| 1 + arch/xtensa/include/asm/unistd.h | 1 + fs/read_write.c | 2 +- include/asm-generic/unistd.h | 12 15 files changed, 26 insertions(+), 2 deletions(-) create mode 100644 include/asm-generic/unistd.h diff --git a/arch/arm/include/asm/unistd.h b/arch/arm/include/asm/unistd.h index 3676e82cf95c..e35ec8100a21 100644 --- a/arch/arm/include/asm/unistd.h +++ b/arch/arm/include/asm/unistd.h @@ -18,6 +18,7 @@ #define __ARCH_WANT_SYS_GETHOSTNAME #define __ARCH_WANT_SYS_PAUSE #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_SIGPENDING #define __ARCH_WANT_SYS_SIGPROCMASK diff --git a/arch/arm64/include/asm/unistd.h b/arch/arm64/include/asm/unistd.h index 2629a68b8724..2c9d8d91e347 100644 --- a/arch/arm64/include/asm/unistd.h +++ b/arch/arm64/include/asm/unistd.h @@ -7,6 +7,7 @@ #define __ARCH_WANT_SYS_GETHOSTNAME #define __ARCH_WANT_SYS_PAUSE #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_SIGPENDING #define __ARCH_WANT_SYS_SIGPROCMASK diff --git a/arch/csky/include/asm/unistd.h b/arch/csky/include/asm/unistd.h index da7a18295615..bee8ba8309e7 100644 --- a/arch/csky/include/asm/unistd.h +++ b/arch/csky/include/asm/unistd.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 */ // Copyright (C) 2018 Hangzhou C-SKY Microsystems co.,ltd. -#include +#include #define NR_syscalls (__NR_syscalls) diff --git a/arch/m68k/include/asm/unistd.h b/arch/m68k/include/asm/unistd.h index 2e0047cf86f8..54c04eb4495a 100644 --- a/arch/m68k/include/asm/unistd.h +++ b/arch/m68k/include/asm/unistd.h @@ -21,6 +21,7 @@ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLD_GETRLIMIT #define __ARCH_WANT_SYS_OLD_MMAP diff --git a/arch/microblaze/include/asm/unistd.h b/arch/microblaze/include/asm/unistd.h index d79d35ac6253..c5fcbce1f997 100644 --- a/arch/microblaze/include/asm/unistd.h +++ b/arch/microblaze/include/asm/unistd.h @@ -27,6 +27,7 @@ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE /* #define __ARCH_WANT_SYS_OLD_GETRLIMIT */ #define __ARCH_WANT_SYS_OLDUMOUNT diff --git a/arch/mips/include/asm/unistd.h b/arch/mips/include/asm/unistd.h index 071053ece677..8e8c7cab95ca 100644 --- a/arch/mips/include/asm/unistd.h +++ b/arch/mips/include/asm/unistd.h @@ -38,6 +38,7 @@ #define __ARCH_WANT_SYS_WAITPID #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLD_UNAME #define __ARCH_WANT_SYS_OLDUMOUNT diff --git a/arch/parisc/include/asm/unistd.h b/arch/parisc/include/asm/unistd.h index cd438e4150f6..29bd46381f2e 100644 --- a/arch/parisc/include/asm/unistd.h +++ b/arch/parisc/include/asm/unistd.h @@ -159,6 +159,7 @@ type name(type1 arg1, type2 arg2, type3 arg3, type4 arg4, type5 arg5) \ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLDUMOUNT #define __ARCH_WANT_SYS_SIGPENDING diff --git a/arch/powerpc/include/asm/unistd.h b/arch/powerpc/include/asm/unistd.h index b0720c7c3fcf..700fcdac2e3c 100644 --- a/arch/powerpc/include/asm/unistd.h +++ b/arch/powerpc/include/asm/unistd.h @@ -31,6 +31,7 @@ #define __ARCH_WANT_SYS_SOCKETCALL #define __ARCH_WANT_SYS_FADVISE64 #define __ARCH_WANT_SYS_GETPGRP +#define __ARCH_WANT_SYS_LLSEEK #define __ARCH_WANT_SYS_NICE #define __ARCH_WANT_SYS_OLD_GETRLIMIT #define __ARCH_WANT_SYS_OLD_UNAME diff --git a/arch/s390/include/asm/unistd.h b/arch/s390/include/asm/unistd.h index 9e9f75ef046a
[PATCH v6 0/6] Disable compat cruft on ppc64le v6
Less code means less bugs so add a knob to skip the compat stuff. This is tested on ppc64le top of https://patchwork.ozlabs.org/cover/1153556/ Changes in v2: saner CONFIG_COMPAT ifdefs Changes in v3: - change llseek to 32bit instead of builing it unconditionally in fs - clanup the makefile conditionals - remove some ifdefs or convert to IS_DEFINED where possible Changes in v4: - cleanup is_32bit_task and current_is_64bit - more makefile cleanup Changes in v5: - more current_is_64bit cleanup - split off callchain.c 32bit and 64bit parts Changes in v6: - cleanup makefile after split - consolidate read_user_stack_32 - fix some checkpatch warnings Michal Suchanek (6): powerpc: make llseek 32bit-only. powerpc: move common register copy functions from signal_32.c to signal.c powerpc/perf: consolidate read_user_stack_32 powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Make COMPAT user-selectable disabled on littleendian by default. powerpc/perf: split callchain.c by bitness arch/powerpc/Kconfig | 5 +- arch/powerpc/include/asm/thread_info.h | 4 +- arch/powerpc/kernel/Makefile | 7 +- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 144 - arch/powerpc/kernel/signal_32.c | 140 - arch/powerpc/kernel/syscall_64.c | 6 +- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- arch/powerpc/kernel/vdso.c | 5 +- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c| 377 +-- arch/powerpc/perf/callchain.h| 11 + arch/powerpc/perf/callchain_32.c | 204 arch/powerpc/perf/callchain_64.c | 185 +++ 14 files changed, 564 insertions(+), 533 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c -- 2.22.0
[PATCH v6 2/6] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->thread.ckfp_state.fpr, +
[PATCH v6 5/6] powerpc/64: Make COMPAT user-selectable disabled on littleendian by default.
On bigendian ppc64 it is common to have 32bit legacy binaries but much less so on littleendian. Signed-off-by: Michal Suchanek --- v3: make configurable --- arch/powerpc/Kconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..b0339e892329 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -264,8 +264,9 @@ config PANIC_TIMEOUT default 180 config COMPAT - bool - default y if PPC64 + bool "Enable support for 32bit binaries" + depends on PPC64 + default y if !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.22.0
[PATCH v6 3/6] powerpc/perf: consolidate read_user_stack_32
There are two almost identical copies for 32bit and 64bit. The function is used only in 32bit code which will be split out in next patch so consolidate to one function. Signed-off-by: Michal Suchanek --- new patch in v6 --- arch/powerpc/perf/callchain.c | 25 + 1 file changed, 9 insertions(+), 16 deletions(-) diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index c84bbd4298a0..b7cdcce20280 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -165,22 +165,6 @@ static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) return read_user_stack_slow(ptr, ret, 8); } -static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || - ((unsigned long)ptr & 3)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 4); -} - static inline int valid_user_sp(unsigned long sp, int is_64) { if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) @@ -295,6 +279,12 @@ static inline int current_is_64bit(void) } #else /* CONFIG_PPC64 */ +static int read_user_stack_slow(void __user *ptr, void *buf, int nb) +{ + return 0; +} +#endif /* CONFIG_PPC64 */ + /* * On 32-bit we just access the address and let hash_page create a * HPTE if necessary, so there is no need to fall back to reading @@ -313,9 +303,12 @@ static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) rc = __get_user_inatomic(*ret, ptr); pagefault_enable(); + if (IS_ENABLED(CONFIG_PPC64) && rc) + return read_user_stack_slow(ptr, ret, 4); return rc; } +#ifndef CONFIG_PPC64 static inline void perf_callchain_user_64(struct perf_callchain_entry_ctx *entry, struct pt_regs *regs) { -- 2.22.0
[PATCH v6 1/6] powerpc: make llseek 32bit-only.
The llseek syscall is not built in fs/read_write.c when !64bit && !COMPAT With the syscall marked as common in syscall.tbl build fails in this case. The llseek interface does not make sense on 64bit and it is explicitly described as 32bit interface. Use on 64bit is not well-defined so just drop it for 64bit. Fixes: caf6f9c8a326 ("asm-generic: Remove unneeded __ARCH_WANT_SYS_LLSEEK macro") Link: https://lore.kernel.org/lkml/20190828151552.ga16...@infradead.org/ Link: https://lore.kernel.org/lkml/20190829214319.498c7de2@naga/ Signed-off-by: Michal Suchanek --- v5: update commit message. --- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/powerpc/kernel/syscalls/syscall.tbl b/arch/powerpc/kernel/syscalls/syscall.tbl index 010b9f445586..53e427606f6c 100644 --- a/arch/powerpc/kernel/syscalls/syscall.tbl +++ b/arch/powerpc/kernel/syscalls/syscall.tbl @@ -188,7 +188,7 @@ 137common afs_syscall sys_ni_syscall 138common setfsuidsys_setfsuid 139common setfsgidsys_setfsgid -140common _llseek sys_llseek +14032 _llseek sys_llseek 141common getdentssys_getdents compat_sys_getdents 142common _newselect sys_select compat_sys_select 143common flock sys_flock -- 2.22.0
[PATCH v6 6/6] powerpc/perf: split callchain.c by bitness
Building callchain.c with !COMPAT proved quite ugly with all the defines. Splitting out the 32bit and 64bit parts looks better. No code change intended. Signed-off-by: Michal Suchanek --- v6: - move current_is_64bit consolidetaion to earlier patch - move defines to the top of callchain_32.c - Makefile cleanup --- arch/powerpc/perf/Makefile | 5 +- arch/powerpc/perf/callchain.c| 371 +-- arch/powerpc/perf/callchain.h| 11 + arch/powerpc/perf/callchain_32.c | 204 + arch/powerpc/perf/callchain_64.c | 185 +++ 5 files changed, 405 insertions(+), 371 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c diff --git a/arch/powerpc/perf/Makefile b/arch/powerpc/perf/Makefile index c155dcbb8691..53d614e98537 100644 --- a/arch/powerpc/perf/Makefile +++ b/arch/powerpc/perf/Makefile @@ -1,6 +1,9 @@ # SPDX-License-Identifier: GPL-2.0 -obj-$(CONFIG_PERF_EVENTS) += callchain.o perf_regs.o +obj-$(CONFIG_PERF_EVENTS) += callchain.o callchain_$(BITS).o perf_regs.o +ifdef CONFIG_COMPAT +obj-$(CONFIG_PERF_EVENTS) += callchain_32.o +endif obj-$(CONFIG_PPC_PERF_CTRS)+= core-book3s.o bhrb.o obj64-$(CONFIG_PPC_PERF_CTRS) += ppc970-pmu.o power5-pmu.o \ diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index 788ad2c63f18..8f30f1b47c78 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -15,11 +15,9 @@ #include #include #include -#ifdef CONFIG_COMPAT -#include "../kernel/ppc32.h" -#endif #include +#include "callchain.h" /* * Is sp valid as the address of the next kernel stack frame after prev_sp? @@ -102,373 +100,6 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } -#ifdef CONFIG_PPC64 -/* - * On 64-bit we don't want to invoke hash_page on user addresses from - * interrupt context, so if the access faults, we read the page tables - * to find which page (if any) is mapped and access it directly. - */ -static int read_user_stack_slow(void __user *ptr, void *buf, int nb) -{ - int ret = -EFAULT; - pgd_t *pgdir; - pte_t *ptep, pte; - unsigned shift; - unsigned long addr = (unsigned long) ptr; - unsigned long offset; - unsigned long pfn, flags; - void *kaddr; - - pgdir = current->mm->pgd; - if (!pgdir) - return -EFAULT; - - local_irq_save(flags); - ptep = find_current_mm_pte(pgdir, addr, NULL, ); - if (!ptep) - goto err_out; - if (!shift) - shift = PAGE_SHIFT; - - /* align address to page boundary */ - offset = addr & ((1UL << shift) - 1); - - pte = READ_ONCE(*ptep); - if (!pte_present(pte) || !pte_user(pte)) - goto err_out; - pfn = pte_pfn(pte); - if (!page_is_ram(pfn)) - goto err_out; - - /* no highmem to worry about here */ - kaddr = pfn_to_kaddr(pfn); - memcpy(buf, kaddr + offset, nb); - ret = 0; -err_out: - local_irq_restore(flags); - return ret; -} - -static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned long) || - ((unsigned long)ptr & 7)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 8); -} - -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) - return 0; - return 1; -} - -/* - * 64-bit user processes use the same stack frame for RT and non-RT signals. - */ -struct signal_frame_64 { - chardummy[__SIGNAL_FRAMESIZE]; - struct ucontext uc; - unsigned long unused[2]; - unsigned inttramp[6]; - struct siginfo *pinfo; - void*puc; - struct siginfo info; - charabigap[288]; -}; - -static int is_sigreturn_64_address(unsigned long nip, unsigned long fp) -{ - if (nip == fp + offsetof(struct signal_frame_64, tramp)) - return 1; - if (vdso64_rt_sigtramp && current->mm->context.vdso_base && - nip == current->mm->context.vdso_base + vdso64_rt_sigtramp) - return 1; - return 0; -} - -/* - * Do some sanity checking on the signal frame pointed to by sp. - * We check the pinfo and puc pointers in the frame. - */ -static int sane_signal_64_frame(unsigned long sp) -{ - struct signal_frame_64 __user *sf; - unsigned long pinfo, puc; - - sf = (stru
[PATCH v6 4/6] powerpc/64: make buildable without CONFIG_COMPAT
There are numerous references to 32bit functions in generic and 64bit code so ifdef them out. Signed-off-by: Michal Suchanek --- v2: - fix 32bit ifdef condition in signal.c - simplify the compat ifdef condition in vdso.c - 64bit is redundant - simplify the compat ifdef condition in callchain.c - 64bit is redundant v3: - use IS_ENABLED and maybe_unused where possible - do not ifdef declarations - clean up Makefile v4: - further makefile cleanup - simplify is_32bit_task conditions - avoid ifdef in condition by using return v5: - avoid unreachable code on 32bit - make is_current_64bit constant on !COMPAT - add stub perf_callchain_user_32 to avoid some ifdefs v6: - consolidate current_is_64bit --- arch/powerpc/include/asm/thread_info.h | 4 +-- arch/powerpc/kernel/Makefile | 7 +++-- arch/powerpc/kernel/entry_64.S | 2 ++ arch/powerpc/kernel/signal.c | 3 +-- arch/powerpc/kernel/syscall_64.c | 6 ++--- arch/powerpc/kernel/vdso.c | 5 ++-- arch/powerpc/perf/callchain.c | 37 +++--- 7 files changed, 33 insertions(+), 31 deletions(-) diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h index 8e1d0195ac36..c128d8a48ea3 100644 --- a/arch/powerpc/include/asm/thread_info.h +++ b/arch/powerpc/include/asm/thread_info.h @@ -144,10 +144,10 @@ static inline bool test_thread_local_flags(unsigned int flags) return (ti->local_flags & flags) != 0; } -#ifdef CONFIG_PPC64 +#ifdef CONFIG_COMPAT #define is_32bit_task()(test_thread_flag(TIF_32BIT)) #else -#define is_32bit_task()(1) +#define is_32bit_task()(IS_ENABLED(CONFIG_PPC32)) #endif #if defined(CONFIG_PPC64) diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 1d646a94d96c..9d8772e863b9 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile @@ -44,16 +44,15 @@ CFLAGS_btext.o += -DDISABLE_BRANCH_PROFILING endif obj-y := cputable.o ptrace.o syscalls.o \ - irq.o align.o signal_32.o pmc.o vdso.o \ + irq.o align.o signal_$(BITS).o pmc.o vdso.o \ process.o systbl.o idle.o \ signal.o sysfs.o cacheinfo.o time.o \ prom.o traps.o setup-common.o \ udbg.o misc.o io.o misc_$(BITS).o \ of_platform.o prom_parse.o -obj-$(CONFIG_PPC64)+= setup_64.o sys_ppc32.o \ - signal_64.o ptrace32.o \ - paca.o nvram_64.o firmware.o \ +obj-$(CONFIG_PPC64)+= setup_64.o paca.o nvram_64.o firmware.o \ syscall_64.o +obj-$(CONFIG_COMPAT) += sys_ppc32.o ptrace32.o signal_32.o obj-$(CONFIG_VDSO32) += vdso32/ obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 2ec825a85f5b..a2dbf216f607 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -51,8 +51,10 @@ SYS_CALL_TABLE: .tc sys_call_table[TC],sys_call_table +#ifdef CONFIG_COMPAT COMPAT_SYS_CALL_TABLE: .tc compat_sys_call_table[TC],compat_sys_call_table +#endif /* This value is used to mark exception frames on the stack. */ exception_marker: diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index 60436432399f..61678cb0e6a1 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -247,7 +247,6 @@ static void do_signal(struct task_struct *tsk) sigset_t *oldset = sigmask_to_save(); struct ksignal ksig = { .sig = 0 }; int ret; - int is32 = is_32bit_task(); BUG_ON(tsk != current); @@ -277,7 +276,7 @@ static void do_signal(struct task_struct *tsk) rseq_signal_deliver(, tsk->thread.regs); - if (is32) { + if (is_32bit_task()) { if (ksig.ka.sa.sa_flags & SA_SIGINFO) ret = handle_rt_signal32(, oldset, tsk); else diff --git a/arch/powerpc/kernel/syscall_64.c b/arch/powerpc/kernel/syscall_64.c index 98ed970796d5..0d5cbbe54cf1 100644 --- a/arch/powerpc/kernel/syscall_64.c +++ b/arch/powerpc/kernel/syscall_64.c @@ -38,7 +38,6 @@ typedef long (*syscall_fn)(long, long, long, long, long, long); long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, unsigned long r0, struct pt_regs *regs) { - unsigned long ti_flags; syscall_fn f; BUG_ON(!(regs->msr & MSR_PR)); @@ -83,8 +82,7 @@ long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, */ regs->softe = IRQS_ENABLED; - ti_flags = curr
[PATCH] soundwire: slave: Fix unused function warning on !ACPI
Fixes the following warning on !ACPI systems: drivers/soundwire/slave.c:16:12: warning: ‘sdw_slave_add’ defined but not used [-Wunused-function] static int sdw_slave_add(struct sdw_bus *bus, ^ Signed-off-by: Michal Suchanek --- drivers/soundwire/slave.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/soundwire/slave.c b/drivers/soundwire/slave.c index f39a5815e25d..34c7e65831d1 100644 --- a/drivers/soundwire/slave.c +++ b/drivers/soundwire/slave.c @@ -6,6 +6,7 @@ #include #include "bus.h" +#if IS_ENABLED(CONFIG_ACPI) static void sdw_slave_release(struct device *dev) { struct sdw_slave *slave = dev_to_sdw_dev(dev); @@ -60,7 +61,6 @@ static int sdw_slave_add(struct sdw_bus *bus, return ret; } -#if IS_ENABLED(CONFIG_ACPI) /* * sdw_acpi_find_slaves() - Find Slave devices in Master ACPI node * @bus: SDW bus instance -- 2.22.0
[PATCH v5 2/5] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->thread.ckfp_state.fpr, +
[PATCH v5 3/5] powerpc/64: make buildable without CONFIG_COMPAT
There are numerous references to 32bit functions in generic and 64bit code so ifdef them out. Signed-off-by: Michal Suchanek --- v2: - fix 32bit ifdef condition in signal.c - simplify the compat ifdef condition in vdso.c - 64bit is redundant - simplify the compat ifdef condition in callchain.c - 64bit is redundant v3: - use IS_ENABLED and maybe_unused where possible - do not ifdef declarations - clean up Makefile v4: - further makefile cleanup - simplify is_32bit_task conditions - avoid ifdef in condition by using return v5: - avoid unreachable code on 32bit - make is_current_64bit constant on !COMPAT - add stub perf_callchain_user_32 to avoid some ifdefs --- arch/powerpc/include/asm/thread_info.h | 4 ++-- arch/powerpc/kernel/Makefile | 7 +++ arch/powerpc/kernel/entry_64.S | 2 ++ arch/powerpc/kernel/signal.c | 3 +-- arch/powerpc/kernel/syscall_64.c | 6 ++ arch/powerpc/kernel/vdso.c | 5 ++--- arch/powerpc/perf/callchain.c | 13 +++-- 7 files changed, 23 insertions(+), 17 deletions(-) diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h index 8e1d0195ac36..c128d8a48ea3 100644 --- a/arch/powerpc/include/asm/thread_info.h +++ b/arch/powerpc/include/asm/thread_info.h @@ -144,10 +144,10 @@ static inline bool test_thread_local_flags(unsigned int flags) return (ti->local_flags & flags) != 0; } -#ifdef CONFIG_PPC64 +#ifdef CONFIG_COMPAT #define is_32bit_task()(test_thread_flag(TIF_32BIT)) #else -#define is_32bit_task()(1) +#define is_32bit_task()(IS_ENABLED(CONFIG_PPC32)) #endif #if defined(CONFIG_PPC64) diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 1d646a94d96c..9d8772e863b9 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile @@ -44,16 +44,15 @@ CFLAGS_btext.o += -DDISABLE_BRANCH_PROFILING endif obj-y := cputable.o ptrace.o syscalls.o \ - irq.o align.o signal_32.o pmc.o vdso.o \ + irq.o align.o signal_$(BITS).o pmc.o vdso.o \ process.o systbl.o idle.o \ signal.o sysfs.o cacheinfo.o time.o \ prom.o traps.o setup-common.o \ udbg.o misc.o io.o misc_$(BITS).o \ of_platform.o prom_parse.o -obj-$(CONFIG_PPC64)+= setup_64.o sys_ppc32.o \ - signal_64.o ptrace32.o \ - paca.o nvram_64.o firmware.o \ +obj-$(CONFIG_PPC64)+= setup_64.o paca.o nvram_64.o firmware.o \ syscall_64.o +obj-$(CONFIG_COMPAT) += sys_ppc32.o ptrace32.o signal_32.o obj-$(CONFIG_VDSO32) += vdso32/ obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 2ec825a85f5b..a2dbf216f607 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -51,8 +51,10 @@ SYS_CALL_TABLE: .tc sys_call_table[TC],sys_call_table +#ifdef CONFIG_COMPAT COMPAT_SYS_CALL_TABLE: .tc compat_sys_call_table[TC],compat_sys_call_table +#endif /* This value is used to mark exception frames on the stack. */ exception_marker: diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index 60436432399f..61678cb0e6a1 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -247,7 +247,6 @@ static void do_signal(struct task_struct *tsk) sigset_t *oldset = sigmask_to_save(); struct ksignal ksig = { .sig = 0 }; int ret; - int is32 = is_32bit_task(); BUG_ON(tsk != current); @@ -277,7 +276,7 @@ static void do_signal(struct task_struct *tsk) rseq_signal_deliver(, tsk->thread.regs); - if (is32) { + if (is_32bit_task()) { if (ksig.ka.sa.sa_flags & SA_SIGINFO) ret = handle_rt_signal32(, oldset, tsk); else diff --git a/arch/powerpc/kernel/syscall_64.c b/arch/powerpc/kernel/syscall_64.c index 98ed970796d5..0d5cbbe54cf1 100644 --- a/arch/powerpc/kernel/syscall_64.c +++ b/arch/powerpc/kernel/syscall_64.c @@ -38,7 +38,6 @@ typedef long (*syscall_fn)(long, long, long, long, long, long); long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, unsigned long r0, struct pt_regs *regs) { - unsigned long ti_flags; syscall_fn f; BUG_ON(!(regs->msr & MSR_PR)); @@ -83,8 +82,7 @@ long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, */ regs->softe = IRQS_ENABLED; - ti_flags = current_thread_info()->flags; -
[PATCH v5 1/5] powerpc: make llseek 32bit-only.
The llseek syscall is not built in fs/read_write.c when !64bit && !COMPAT With the syscall marked as common in syscall.tbl build fails in this case. The llseek inteface does not make sense on 64bit and it is explicitly described as 32bit interface. Use on 64bit is not well-defined so just drop it for 64bit. Fixes: caf6f9c8a326 ("asm-generic: Remove unneeded __ARCH_WANT_SYS_LLSEEK macro") Signed-off-by: Michal Suchanek --- v5: update commit message. --- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/powerpc/kernel/syscalls/syscall.tbl b/arch/powerpc/kernel/syscalls/syscall.tbl index 010b9f445586..53e427606f6c 100644 --- a/arch/powerpc/kernel/syscalls/syscall.tbl +++ b/arch/powerpc/kernel/syscalls/syscall.tbl @@ -188,7 +188,7 @@ 137common afs_syscall sys_ni_syscall 138common setfsuidsys_setfsuid 139common setfsgidsys_setfsgid -140common _llseek sys_llseek +14032 _llseek sys_llseek 141common getdentssys_getdents compat_sys_getdents 142common _newselect sys_select compat_sys_select 143common flock sys_flock -- 2.22.0
[PATCH v5 0/5] Disable compat cruft on ppc64le v5
Less code means less bugs so add a knob to skip the compat stuff. This is tested on ppc64le top of https://patchwork.ozlabs.org/cover/1153556/ Changes in v2: saner CONFIG_COMPAT ifdefs Changes in v3: - change llseek to 32bit instead of builing it unconditionally in fs - clanup the makefile conditionals - remove some ifdefs or convert to IS_DEFINED where possible Changes in v4: - cleanup is_32bit_task and current_is_64bit - more makefile cleanup Changes in v5: - more current_is_64bit cleanup - split off callchain.c 32bit and 64bit parts Michal Suchanek (5): powerpc: make llseek 32bit-only. powerpc: move common register copy functions from signal_32.c to signal.c powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Make COMPAT user-selectable disabled on littleendian by default. powerpc/perf: split callchain.c by bitness arch/powerpc/Kconfig | 5 +- arch/powerpc/include/asm/thread_info.h | 4 +- arch/powerpc/kernel/Makefile | 7 +- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 144 - arch/powerpc/kernel/signal_32.c | 140 - arch/powerpc/kernel/syscall_64.c | 6 +- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- arch/powerpc/kernel/vdso.c | 5 +- arch/powerpc/perf/Makefile | 4 + arch/powerpc/perf/callchain.c| 379 +-- arch/powerpc/perf/callchain.h| 11 + arch/powerpc/perf/callchain_32.c | 218 + arch/powerpc/perf/callchain_64.c | 185 +++ 14 files changed, 579 insertions(+), 533 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c -- 2.22.0
[PATCH v5 4/5] powerpc/64: Make COMPAT user-selectable disabled on littleendian by default.
On bigendian ppc64 it is common to have 32bit legacy binaries but much less so on littleendian. Signed-off-by: Michal Suchanek --- v3: make configurable --- arch/powerpc/Kconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..b0339e892329 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -264,8 +264,9 @@ config PANIC_TIMEOUT default 180 config COMPAT - bool - default y if PPC64 + bool "Enable support for 32bit binaries" + depends on PPC64 + default y if !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.22.0
[PATCH v5 5/5] powerpc/perf: split callchain.c by bitness
Building callchain.c with !COMPAT proved quite ugly with all the defines. Splitting out the 32bit and 64bit parts looks better. Also rewrite current_is_64bit as common function. No other code change intended. Signed-off-by: Michal Suchanek --- arch/powerpc/perf/Makefile | 4 + arch/powerpc/perf/callchain.c| 388 +-- arch/powerpc/perf/callchain.h| 11 + arch/powerpc/perf/callchain_32.c | 218 + arch/powerpc/perf/callchain_64.c | 185 +++ 5 files changed, 422 insertions(+), 384 deletions(-) create mode 100644 arch/powerpc/perf/callchain.h create mode 100644 arch/powerpc/perf/callchain_32.c create mode 100644 arch/powerpc/perf/callchain_64.c diff --git a/arch/powerpc/perf/Makefile b/arch/powerpc/perf/Makefile index c155dcbb8691..e9f3202251d0 100644 --- a/arch/powerpc/perf/Makefile +++ b/arch/powerpc/perf/Makefile @@ -1,6 +1,10 @@ # SPDX-License-Identifier: GPL-2.0 obj-$(CONFIG_PERF_EVENTS) += callchain.o perf_regs.o +ifdef CONFIG_PERF_EVENTS +obj-y += callchain_$(BITS).o +obj-$(CONFIG_COMPAT) += callchain_32.o +endif obj-$(CONFIG_PPC_PERF_CTRS)+= core-book3s.o bhrb.o obj64-$(CONFIG_PPC_PERF_CTRS) += ppc970-pmu.o power5-pmu.o \ diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index 881be5c4e9bb..981005625c05 100644 --- a/arch/powerpc/perf/callchain.c +++ b/arch/powerpc/perf/callchain.c @@ -15,11 +15,9 @@ #include #include #include -#ifdef CONFIG_COMPAT -#include "../kernel/ppc32.h" -#endif #include +#include "callchain.h" /* * Is sp valid as the address of the next kernel stack frame after prev_sp? @@ -102,188 +100,6 @@ perf_callchain_kernel(struct perf_callchain_entry_ctx *entry, struct pt_regs *re } } -#ifdef CONFIG_PPC64 -/* - * On 64-bit we don't want to invoke hash_page on user addresses from - * interrupt context, so if the access faults, we read the page tables - * to find which page (if any) is mapped and access it directly. - */ -static int read_user_stack_slow(void __user *ptr, void *buf, int nb) -{ - int ret = -EFAULT; - pgd_t *pgdir; - pte_t *ptep, pte; - unsigned shift; - unsigned long addr = (unsigned long) ptr; - unsigned long offset; - unsigned long pfn, flags; - void *kaddr; - - pgdir = current->mm->pgd; - if (!pgdir) - return -EFAULT; - - local_irq_save(flags); - ptep = find_current_mm_pte(pgdir, addr, NULL, ); - if (!ptep) - goto err_out; - if (!shift) - shift = PAGE_SHIFT; - - /* align address to page boundary */ - offset = addr & ((1UL << shift) - 1); - - pte = READ_ONCE(*ptep); - if (!pte_present(pte) || !pte_user(pte)) - goto err_out; - pfn = pte_pfn(pte); - if (!page_is_ram(pfn)) - goto err_out; - - /* no highmem to worry about here */ - kaddr = pfn_to_kaddr(pfn); - memcpy(buf, kaddr + offset, nb); - ret = 0; -err_out: - local_irq_restore(flags); - return ret; -} - -static int read_user_stack_64(unsigned long __user *ptr, unsigned long *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned long) || - ((unsigned long)ptr & 7)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 8); -} - -static int read_user_stack_32(unsigned int __user *ptr, unsigned int *ret) -{ - if ((unsigned long)ptr > TASK_SIZE - sizeof(unsigned int) || - ((unsigned long)ptr & 3)) - return -EFAULT; - - pagefault_disable(); - if (!__get_user_inatomic(*ret, ptr)) { - pagefault_enable(); - return 0; - } - pagefault_enable(); - - return read_user_stack_slow(ptr, ret, 4); -} - -static inline int valid_user_sp(unsigned long sp, int is_64) -{ - if (!sp || (sp & 7) || sp > (is_64 ? TASK_SIZE : 0x1UL) - 32) - return 0; - return 1; -} - -/* - * 64-bit user processes use the same stack frame for RT and non-RT signals. - */ -struct signal_frame_64 { - chardummy[__SIGNAL_FRAMESIZE]; - struct ucontext uc; - unsigned long unused[2]; - unsigned inttramp[6]; - struct siginfo *pinfo; - void*puc; - struct siginfo info; - charabigap[288]; -}; - -static int is_sigreturn_64_address(unsigned long nip, unsigned long fp) -{ - if (nip == fp + offsetof(struct signal_frame_64, tramp)) - return 1; - if (vdso64_rt_sigtramp && current->mm->context.vdso_base && - nip == current->mm-&
[PATCH 1/3] scsi: cxlflash: Fix fallthrough warnings.
Add fallthrough comments where missing. Signed-off-by: Michal Suchanek --- drivers/scsi/cxlflash/main.c | 8 1 file changed, 8 insertions(+) diff --git a/drivers/scsi/cxlflash/main.c b/drivers/scsi/cxlflash/main.c index b1f4724efde2..f402fa9a7bec 100644 --- a/drivers/scsi/cxlflash/main.c +++ b/drivers/scsi/cxlflash/main.c @@ -753,10 +753,13 @@ static void term_intr(struct cxlflash_cfg *cfg, enum undo_level level, /* SISL_MSI_ASYNC_ERROR is setup only for the primary HWQ */ if (index == PRIMARY_HWQ) cfg->ops->unmap_afu_irq(hwq->ctx_cookie, 3, hwq); + /* fall through */ case UNMAP_TWO: cfg->ops->unmap_afu_irq(hwq->ctx_cookie, 2, hwq); + /* fall through */ case UNMAP_ONE: cfg->ops->unmap_afu_irq(hwq->ctx_cookie, 1, hwq); + /* fall through */ case FREE_IRQ: cfg->ops->free_afu_irqs(hwq->ctx_cookie); /* fall through */ @@ -973,14 +976,18 @@ static void cxlflash_remove(struct pci_dev *pdev) switch (cfg->init_state) { case INIT_STATE_CDEV: cxlflash_release_chrdev(cfg); + /* fall through */ case INIT_STATE_SCSI: cxlflash_term_local_luns(cfg); scsi_remove_host(cfg->host); + /* fall through */ case INIT_STATE_AFU: term_afu(cfg); + /* fall through */ case INIT_STATE_PCI: cfg->ops->destroy_afu(cfg->afu_cookie); pci_disable_device(pdev); + /* fall through */ case INIT_STATE_NONE: free_mem(cfg); scsi_host_put(cfg->host); @@ -3017,6 +3024,7 @@ static ssize_t num_hwqs_store(struct device *dev, wait_event(cfg->reset_waitq, cfg->state != STATE_RESET); if (cfg->state == STATE_NORMAL) goto retry; + /* fall through */ default: /* Ideally should not happen */ dev_err(dev, "%s: Device is not ready, state=%d\n", -- 2.12.3
[PATCH 2/3] scsi: ibmvfc: Fix fallthrough warnings.
Add fallthrough comments where they are missing. Signed-off-by: Michal Suchanek --- drivers/scsi/ibmvscsi/ibmvfc.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/scsi/ibmvscsi/ibmvfc.c b/drivers/scsi/ibmvscsi/ibmvfc.c index 8cdbac076a1b..2a06a5b4d3a5 100644 --- a/drivers/scsi/ibmvscsi/ibmvfc.c +++ b/drivers/scsi/ibmvscsi/ibmvfc.c @@ -1830,6 +1830,7 @@ static int ibmvfc_bsg_request(struct bsg_job *job) port_id = (bsg_request->rqst_data.h_els.port_id[0] << 16) | (bsg_request->rqst_data.h_els.port_id[1] << 8) | bsg_request->rqst_data.h_els.port_id[2]; + /* fallthrough */ case FC_BSG_RPT_ELS: fc_flags = IBMVFC_FC_ELS; break; @@ -1838,6 +1839,7 @@ static int ibmvfc_bsg_request(struct bsg_job *job) port_id = (bsg_request->rqst_data.h_ct.port_id[0] << 16) | (bsg_request->rqst_data.h_ct.port_id[1] << 8) | bsg_request->rqst_data.h_ct.port_id[2]; + /* fallthrough */ case FC_BSG_RPT_CT: fc_flags = IBMVFC_FC_CT_IU; break; @@ -4020,6 +4022,7 @@ static void ibmvfc_npiv_login_done(struct ibmvfc_event *evt) return; case IBMVFC_MAD_CRQ_ERROR: ibmvfc_retry_host_init(vhost); + /* fallthrough */ case IBMVFC_MAD_DRIVER_FAILED: ibmvfc_free_event(evt); return; -- 2.12.3
[PATCH 3/3] scsi: ibmvscsi: tgt: Fix fallthrough warnings.
Add fallthrough comments where they are missing. Signed-off-by: Michal Suchanek --- drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c b/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c index 7f9535392a93..57475dbcae0f 100644 --- a/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c +++ b/drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c @@ -1581,6 +1581,7 @@ static long ibmvscsis_adapter_info(struct scsi_info *vscsi, case H_PERMISSION: if (connection_broken(vscsi)) flag_bits = (RESPONSE_Q_DOWN | CLIENT_FAILED); + /* fallthrough */ default: dev_err(>dev, "adapter_info: h_copy_rdma to client failed, rc %ld\n", rc); @@ -2492,8 +2493,10 @@ static long ibmvscsis_ping_response(struct scsi_info *vscsi) break; case H_CLOSED: vscsi->flags |= CLIENT_FAILED; + /* fallthrough */ case H_DROPPED: vscsi->flags |= RESPONSE_Q_DOWN; + /* fallthrough */ case H_REMOTE_PARM: dev_err(>dev, "ping_response: h_send_crq failed, rc %ld\n", rc); -- 2.12.3
[PATCH 0/3] Fix fallthrough warnings.
Build with recent compiler results in numerous fallthrough warnings. The code looks correct to me so just adding the comments to quiet gcc. Please review if the fallthrough was really intentional. Thanks Michal Michal Suchanek (3): scsi: cxlflash: Fix fallthrough warnings. scsi: ibmvfc: Fix fallthrough warnings. scsi: ibmvscsi: tgt: Fix fallthrough warnings. drivers/scsi/cxlflash/main.c | 8 drivers/scsi/ibmvscsi/ibmvfc.c | 3 +++ drivers/scsi/ibmvscsi_tgt/ibmvscsi_tgt.c | 3 +++ 3 files changed, 14 insertions(+) -- 2.12.3
[PATCH] Makefile: Convert -Wimplicit-fallthrough to -Wimplicit-fallthrough=2
>From gcc documentation: -Wimplicit-fallthrough=0 disables the warning altogether. -Wimplicit-fallthrough=1 matches .* regular expression, any comment is used as fallthrough comment. -Wimplicit-fallthrough=2 case insensitively matches .*falls?[ \t-]*thr(ough|u).* regular expression. -Wimplicit-fallthrough=3 case sensitively matches one of the following regular expressions: -fallthrough @fallthrough@ lint -fallthrough[ \t]* [ \t.!]*(ELSE,? |INTENTIONAL(LY)? )? FALL(S | |-)?THR(OUGH|U)[ \t.!]*(-[^\n\r]*)? [ \t.!]*(Else,? |Intentional(ly)? )? Fall((s | |-)[Tt]|t)hr(ough|u)[ \t.!]*(-[^\n\r]*)? [ \t.!]*([Ee]lse,? |[Ii]ntentional(ly)? )? fall(s | |-)?thr(ough|u)[ \t.!]*(-[^\n\r]*)? -Wimplicit-fallthrough=4 case sensitively matches one of the following regular expressions: -fallthrough @fallthrough@ lint -fallthrough[ \t]* [ \t]*FALLTHR(OUGH|U)[ \t]* -Wimplicit-fallthrough=5 doesn’t recognize any comments as fallthrough comments, only attributes disable the warning. In particular the default value of 3 does not match the comments like /* falls through to do foobar */ generating suprious warnings on properly annotated code. Signed-off-by: Michal Suchanek --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index f125625efd60..641ec413c2a6 100644 --- a/Makefile +++ b/Makefile @@ -846,7 +846,7 @@ NOSTDINC_FLAGS += -nostdinc -isystem $(shell $(CC) -print-file-name=include) KBUILD_CFLAGS += -Wdeclaration-after-statement # Warn about unmarked fall-throughs in switch statement. -KBUILD_CFLAGS += $(call cc-option,-Wimplicit-fallthrough,) +KBUILD_CFLAGS += $(call cc-option,-Wimplicit-fallthrough=2,) # Variable Length Arrays (VLAs) should not be used anywhere in the kernel KBUILD_CFLAGS += -Wvla -- 2.22.0
[PATCH v4 0/4] Disable compat cruft on ppc64le v4
Less code means less bugs so add a knob to skip the compat stuff. This is tested on ppc64le top of https://patchwork.ozlabs.org/cover/1153556/ Changes in v2: saner CONFIG_COMPAT ifdefs Changes in v3: - change llseek to 32bit instead of builing it unconditionally in fs - clanup the makefile conditionals - remove some ifdefs or convert to IS_DEFINED where possible Changes in v4: - cleanup is_32bit_task and current_is_64bit - more makefile cleanup Michal Suchanek (4): powerpc: make llseek 32bit-only. powerpc: move common register copy functions from signal_32.c to signal.c powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Make COMPAT user-selectable disabled on littleendian by default. arch/powerpc/Kconfig | 5 +- arch/powerpc/include/asm/thread_info.h | 4 +- arch/powerpc/kernel/Makefile | 7 +- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 144 ++- arch/powerpc/kernel/signal_32.c | 140 -- arch/powerpc/kernel/syscall_64.c | 6 +- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- arch/powerpc/kernel/vdso.c | 5 +- arch/powerpc/perf/callchain.c| 14 ++- 10 files changed, 167 insertions(+), 162 deletions(-) -- 2.22.0
[PATCH v4 1/4] powerpc: make llseek 32bit-only.
Fixes: aff850393200 ("powerpc: add system call table generation support") Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/powerpc/kernel/syscalls/syscall.tbl b/arch/powerpc/kernel/syscalls/syscall.tbl index 010b9f445586..53e427606f6c 100644 --- a/arch/powerpc/kernel/syscalls/syscall.tbl +++ b/arch/powerpc/kernel/syscalls/syscall.tbl @@ -188,7 +188,7 @@ 137common afs_syscall sys_ni_syscall 138common setfsuidsys_setfsuid 139common setfsgidsys_setfsgid -140common _llseek sys_llseek +14032 _llseek sys_llseek 141common getdentssys_getdents compat_sys_getdents 142common _newselect sys_select compat_sys_select 143common flock sys_flock -- 2.22.0
[PATCH v4 3/4] powerpc/64: make buildable without CONFIG_COMPAT
There are numerous references to 32bit functions in generic and 64bit code so ifdef them out. Signed-off-by: Michal Suchanek --- v2: - fix 32bit ifdef condition in signal.c - simplify the compat ifdef condition in vdso.c - 64bit is redundant - simplify the compat ifdef condition in callchain.c - 64bit is redundant v3: - use IS_ENABLED and maybe_unused where possible - do not ifdef declarations - clean up Makefile v4: - further makefile cleanup - simplify is_32bit_task conditions - avoid ifdef in condition by using return --- arch/powerpc/include/asm/thread_info.h | 4 ++-- arch/powerpc/kernel/Makefile | 7 +++ arch/powerpc/kernel/entry_64.S | 2 ++ arch/powerpc/kernel/signal.c | 3 +-- arch/powerpc/kernel/syscall_64.c | 6 ++ arch/powerpc/kernel/vdso.c | 5 ++--- arch/powerpc/perf/callchain.c | 14 ++ 7 files changed, 22 insertions(+), 19 deletions(-) diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h index 8e1d0195ac36..c128d8a48ea3 100644 --- a/arch/powerpc/include/asm/thread_info.h +++ b/arch/powerpc/include/asm/thread_info.h @@ -144,10 +144,10 @@ static inline bool test_thread_local_flags(unsigned int flags) return (ti->local_flags & flags) != 0; } -#ifdef CONFIG_PPC64 +#ifdef CONFIG_COMPAT #define is_32bit_task()(test_thread_flag(TIF_32BIT)) #else -#define is_32bit_task()(1) +#define is_32bit_task()(IS_ENABLED(CONFIG_PPC32)) #endif #if defined(CONFIG_PPC64) diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 1d646a94d96c..9d8772e863b9 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile @@ -44,16 +44,15 @@ CFLAGS_btext.o += -DDISABLE_BRANCH_PROFILING endif obj-y := cputable.o ptrace.o syscalls.o \ - irq.o align.o signal_32.o pmc.o vdso.o \ + irq.o align.o signal_$(BITS).o pmc.o vdso.o \ process.o systbl.o idle.o \ signal.o sysfs.o cacheinfo.o time.o \ prom.o traps.o setup-common.o \ udbg.o misc.o io.o misc_$(BITS).o \ of_platform.o prom_parse.o -obj-$(CONFIG_PPC64)+= setup_64.o sys_ppc32.o \ - signal_64.o ptrace32.o \ - paca.o nvram_64.o firmware.o \ +obj-$(CONFIG_PPC64)+= setup_64.o paca.o nvram_64.o firmware.o \ syscall_64.o +obj-$(CONFIG_COMPAT) += sys_ppc32.o ptrace32.o signal_32.o obj-$(CONFIG_VDSO32) += vdso32/ obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 2ec825a85f5b..a2dbf216f607 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -51,8 +51,10 @@ SYS_CALL_TABLE: .tc sys_call_table[TC],sys_call_table +#ifdef CONFIG_COMPAT COMPAT_SYS_CALL_TABLE: .tc compat_sys_call_table[TC],compat_sys_call_table +#endif /* This value is used to mark exception frames on the stack. */ exception_marker: diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index 60436432399f..61678cb0e6a1 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -247,7 +247,6 @@ static void do_signal(struct task_struct *tsk) sigset_t *oldset = sigmask_to_save(); struct ksignal ksig = { .sig = 0 }; int ret; - int is32 = is_32bit_task(); BUG_ON(tsk != current); @@ -277,7 +276,7 @@ static void do_signal(struct task_struct *tsk) rseq_signal_deliver(, tsk->thread.regs); - if (is32) { + if (is_32bit_task()) { if (ksig.ka.sa.sa_flags & SA_SIGINFO) ret = handle_rt_signal32(, oldset, tsk); else diff --git a/arch/powerpc/kernel/syscall_64.c b/arch/powerpc/kernel/syscall_64.c index 98ed970796d5..0d5cbbe54cf1 100644 --- a/arch/powerpc/kernel/syscall_64.c +++ b/arch/powerpc/kernel/syscall_64.c @@ -38,7 +38,6 @@ typedef long (*syscall_fn)(long, long, long, long, long, long); long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, unsigned long r0, struct pt_regs *regs) { - unsigned long ti_flags; syscall_fn f; BUG_ON(!(regs->msr & MSR_PR)); @@ -83,8 +82,7 @@ long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, */ regs->softe = IRQS_ENABLED; - ti_flags = current_thread_info()->flags; - if (unlikely(ti_flags & _TIF_SYSCALL_DOTRACE)) { + if (unlikely(current_thread_info()->flags & _TIF_SYSCALL_DOTRACE)) {
[PATCH v4 4/4] powerpc/64: Make COMPAT user-selectable disabled on littleendian by default.
On bigendian ppc64 it is common to have 32bit legacy binaries but much less so on littleendian. Signed-off-by: Michal Suchanek --- v3: make configurable --- arch/powerpc/Kconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..b0339e892329 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -264,8 +264,9 @@ config PANIC_TIMEOUT default 180 config COMPAT - bool - default y if PPC64 + bool "Enable support for 32bit binaries" + depends on PPC64 + default y if !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.22.0
[PATCH v4 2/4] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->thread.ckfp_state.fpr, +
[PATCH v2] powerpc/fadump: when fadump is supported register the fadump sysfs files.
Currently it is not possible to distinguish the case when fadump is supported by firmware and disabled in kernel and completely unsupported using the kernel sysfs interface. User can investigate the devicetree but it is more reasonable to provide sysfs files in case we get some fadumpv2 in the future. With this patch sysfs files are available whenever fadump is supported by firmware. Signed-off-by: Michal Suchanek --- v2: move the sysfs initialization earlier to avoid condition nesting --- arch/powerpc/kernel/fadump.c | 15 +-- 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/arch/powerpc/kernel/fadump.c b/arch/powerpc/kernel/fadump.c index 4eab97292cc2..13741380b2f7 100644 --- a/arch/powerpc/kernel/fadump.c +++ b/arch/powerpc/kernel/fadump.c @@ -1671,16 +1671,20 @@ static void fadump_init_files(void) */ int __init setup_fadump(void) { - if (!fw_dump.fadump_enabled) - return 0; - - if (!fw_dump.fadump_supported) { + if (!fw_dump.fadump_supported && fw_dump.fadump_enabled) { printk(KERN_ERR "Firmware-assisted dump is not supported on" " this hardware\n"); - return 0; } + if (!fw_dump.fadump_supported) + return 0; + + fadump_init_files(); fadump_show_config(); + + if (!fw_dump.fadump_enabled) + return 1; + /* * If dump data is available then see if it is valid and prepare for * saving it to the disk. @@ -1696,7 +1700,6 @@ int __init setup_fadump(void) /* Initialize the kernel dump memory structure for FAD registration. */ else if (fw_dump.reserve_dump_area_size) init_fadump_mem_struct(, fw_dump.reserve_dump_area_start); - fadump_init_files(); return 1; } -- 2.22.0
[PATCH v3 3/4] powerpc/64: make buildable without CONFIG_COMPAT
There are numerous references to 32bit functions in generic and 64bit code so ifdef them out. Signed-off-by: Michal Suchanek --- v2: - fix 32bit ifdef condition in signal.c - simplify the compat ifdef condition in vdso.c - 64bit is redundant - simplify the compat ifdef condition in callchain.c - 64bit is redundant v3: - use IS_ENABLED and maybe_unused where possible - do not ifdef declarations - clean up Makefile --- arch/powerpc/kernel/Makefile | 9 + arch/powerpc/kernel/entry_64.S | 2 ++ arch/powerpc/kernel/signal.c | 2 +- arch/powerpc/kernel/syscall_64.c | 2 +- arch/powerpc/kernel/vdso.c | 5 ++--- arch/powerpc/perf/callchain.c| 13 + 6 files changed, 20 insertions(+), 13 deletions(-) diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 1d646a94d96c..de1fbb21daf5 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile @@ -44,16 +44,17 @@ CFLAGS_btext.o += -DDISABLE_BRANCH_PROFILING endif obj-y := cputable.o ptrace.o syscalls.o \ - irq.o align.o signal_32.o pmc.o vdso.o \ + irq.o align.o signal_$(BITS).o pmc.o vdso.o \ process.o systbl.o idle.o \ signal.o sysfs.o cacheinfo.o time.o \ prom.o traps.o setup-common.o \ udbg.o misc.o io.o misc_$(BITS).o \ of_platform.o prom_parse.o -obj-$(CONFIG_PPC64)+= setup_64.o sys_ppc32.o \ - signal_64.o ptrace32.o \ - paca.o nvram_64.o firmware.o \ +obj-$(CONFIG_PPC64)+= setup_64.o paca.o nvram_64.o firmware.o \ syscall_64.o +ifdef CONFIG_COMPAT +obj-y += sys_ppc32.o ptrace32.o signal_32.o +endif obj-$(CONFIG_VDSO32) += vdso32/ obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 2ec825a85f5b..a2dbf216f607 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -51,8 +51,10 @@ SYS_CALL_TABLE: .tc sys_call_table[TC],sys_call_table +#ifdef CONFIG_COMPAT COMPAT_SYS_CALL_TABLE: .tc compat_sys_call_table[TC],compat_sys_call_table +#endif /* This value is used to mark exception frames on the stack. */ exception_marker: diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index 60436432399f..73d0f53ffc1a 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -277,7 +277,7 @@ static void do_signal(struct task_struct *tsk) rseq_signal_deliver(, tsk->thread.regs); - if (is32) { + if ((IS_ENABLED(CONFIG_PPC32) || IS_ENABLED(CONFIG_COMPAT)) && is32) { if (ksig.ka.sa.sa_flags & SA_SIGINFO) ret = handle_rt_signal32(, oldset, tsk); else diff --git a/arch/powerpc/kernel/syscall_64.c b/arch/powerpc/kernel/syscall_64.c index 98ed970796d5..bdd9dcf156f8 100644 --- a/arch/powerpc/kernel/syscall_64.c +++ b/arch/powerpc/kernel/syscall_64.c @@ -100,7 +100,7 @@ long system_call_exception(long r3, long r4, long r5, long r6, long r7, long r8, /* May be faster to do array_index_nospec? */ barrier_nospec(); - if (unlikely(ti_flags & _TIF_32BIT)) { + if (IS_ENABLED(CONFIG_COMPAT) && unlikely(ti_flags & _TIF_32BIT)) { f = (void *)compat_sys_call_table[r0]; r3 &= 0xULL; diff --git a/arch/powerpc/kernel/vdso.c b/arch/powerpc/kernel/vdso.c index d60598113a9f..6d4a077f74d6 100644 --- a/arch/powerpc/kernel/vdso.c +++ b/arch/powerpc/kernel/vdso.c @@ -667,9 +667,7 @@ static void __init vdso_setup_syscall_map(void) { unsigned int i; extern unsigned long *sys_call_table; -#ifdef CONFIG_PPC64 extern unsigned long *compat_sys_call_table; -#endif extern unsigned long sys_ni_syscall; @@ -678,7 +676,8 @@ static void __init vdso_setup_syscall_map(void) if (sys_call_table[i] != sys_ni_syscall) vdso_data->syscall_map_64[i >> 5] |= 0x8000UL >> (i & 0x1f); - if (compat_sys_call_table[i] != sys_ni_syscall) + if (IS_ENABLED(CONFIG_COMPAT) && + compat_sys_call_table[i] != sys_ni_syscall) vdso_data->syscall_map_32[i >> 5] |= 0x8000UL >> (i & 0x1f); #else /* CONFIG_PPC64 */ diff --git a/arch/powerpc/perf/callchain.c b/arch/powerpc/perf/callchain.c index c84bbd4298a0..d4e6bf22e0cc 100644 --- a/arch/powerpc/perf/callc
[PATCH v3 4/4] powerpc/64: Make COMPAT user-selectable disabled on littleendian by default.
On bigendian ppc64 it is common to have 32bit legacy binaries but much less so on littleendian. Signed-off-by: Michal Suchanek --- v3: make configurable --- arch/powerpc/Kconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..b0339e892329 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -264,8 +264,9 @@ config PANIC_TIMEOUT default 180 config COMPAT - bool - default y if PPC64 + bool "Enable support for 32bit binaries" + depends on PPC64 + default y if !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.22.0
[PATCH v3 2/4] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->thread.ckfp_state.fpr, +
[PATCH v3 0/4] Disable compat cruft on ppc64le v3
Less code means less bugs so add a knob to skip the compat stuff. This is tested on ppc64le top of https://patchwork.ozlabs.org/cover/1153556/ Changes in v2: saner CONFIG_COMPAT ifdefs Changes in v3: - change llseek to 32bit instead of builing it unconditionally in fs - clanup the makefile conditionals - remove some ifdefs or convert to IS_DEFINED where possible Michal Suchanek (4): powerpc: make llseek 32bit-only. powerpc: move common register copy functions from signal_32.c to signal.c powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Make COMPAT user-selectable disable on littleendian by default. arch/powerpc/Kconfig | 5 +- arch/powerpc/kernel/Makefile | 9 +- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 143 ++- arch/powerpc/kernel/signal_32.c | 140 -- arch/powerpc/kernel/syscall_64.c | 2 +- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- arch/powerpc/kernel/vdso.c | 5 +- arch/powerpc/perf/callchain.c| 13 ++- 9 files changed, 165 insertions(+), 156 deletions(-) -- 2.22.0
[PATCH v3 1/4] powerpc: make llseek 32bit-only.
Fixes: aff850393200 ("powerpc: add system call table generation support") Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/syscalls/syscall.tbl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/powerpc/kernel/syscalls/syscall.tbl b/arch/powerpc/kernel/syscalls/syscall.tbl index 010b9f445586..53e427606f6c 100644 --- a/arch/powerpc/kernel/syscalls/syscall.tbl +++ b/arch/powerpc/kernel/syscalls/syscall.tbl @@ -188,7 +188,7 @@ 137common afs_syscall sys_ni_syscall 138common setfsuidsys_setfsuid 139common setfsgidsys_setfsgid -140common _llseek sys_llseek +14032 _llseek sys_llseek 141common getdentssys_getdents compat_sys_getdents 142common _newselect sys_select compat_sys_select 143common flock sys_flock -- 2.22.0
[PATCH] Revert "Bluetooth: btusb: driver to enable the usb-wakeup feature"
This reverts commit a0085f2510e8976614ad8f766b209448b385492f. After this commit systems wake up at random, most commonly when - put to sleep while bluetooth audio stream is running - connected bluetooth audio device is powered off while system is asleep This is broken since the commit was merged up to 5.3-rc6. Signed-off-by: Michal Suchanek --- drivers/bluetooth/btusb.c | 5 - 1 file changed, 5 deletions(-) diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index 5cf0734eb31b..5c67d41ca254 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -1170,10 +1170,6 @@ static int btusb_open(struct hci_dev *hdev) } data->intf->needs_remote_wakeup = 1; - /* device specific wakeup source enabled and required for USB -* remote wakeup while host is suspended -*/ - device_wakeup_enable(>udev->dev); if (test_and_set_bit(BTUSB_INTR_RUNNING, >flags)) goto done; @@ -1238,7 +1234,6 @@ static int btusb_close(struct hci_dev *hdev) goto failed; data->intf->needs_remote_wakeup = 0; - device_wakeup_disable(>udev->dev); usb_autopm_put_interface(data->intf); failed: -- 2.22.0
[PATCH v2 4/4] powerpc/64: Disable COMPAT if littleendian.
ppc32le was never really a thing. Endian swap is already disabled by default so this 32bit support is kind of useless on ppc64le. Signed-off-by: Michal Suchanek --- arch/powerpc/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 5bab0bb6b833..67cd1c4d1bae 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -265,7 +265,7 @@ config PANIC_TIMEOUT config COMPAT bool - default y if PPC64 + default y if PPC64 && !CPU_LITTLE_ENDIAN select COMPAT_BINFMT_ELF select ARCH_WANT_OLD_COMPAT_IPC select COMPAT_OLD_SIGACTION -- 2.22.0
[PATCH v2 2/4] powerpc: move common register copy functions from signal_32.c to signal.c
These functions are required for 64bit as well. Signed-off-by: Michal Suchanek --- arch/powerpc/kernel/signal.c| 141 arch/powerpc/kernel/signal_32.c | 140 --- 2 files changed, 141 insertions(+), 140 deletions(-) diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index e6c30cee6abf..60436432399f 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c @@ -18,12 +18,153 @@ #include #include #include +#include #include #include #include #include "signal.h" +#ifdef CONFIG_VSX +unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_FPR(i); + buf[i] = task->thread.fp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_fpr_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_FPR(i) = buf[i]; + task->thread.fp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_vsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_vsx_from_user(struct task_struct *task, +void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.fp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +unsigned long copy_ckfpr_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NFPREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + buf[i] = task->thread.TS_CKFPR(i); + buf[i] = task->thread.ckfp_state.fpscr; + return __copy_to_user(to, buf, ELF_NFPREG * sizeof(double)); +} + +unsigned long copy_ckfpr_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NFPREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NFPREG * sizeof(double))) + return 1; + for (i = 0; i < (ELF_NFPREG - 1) ; i++) + task->thread.TS_CKFPR(i) = buf[i]; + task->thread.ckfp_state.fpscr = buf[i]; + + return 0; +} + +unsigned long copy_ckvsx_to_user(void __user *to, + struct task_struct *task) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + /* save FPR copy to local buffer then write to the thread_struct */ + for (i = 0; i < ELF_NVSRHALFREG; i++) + buf[i] = task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET]; + return __copy_to_user(to, buf, ELF_NVSRHALFREG * sizeof(double)); +} + +unsigned long copy_ckvsx_from_user(struct task_struct *task, + void __user *from) +{ + u64 buf[ELF_NVSRHALFREG]; + int i; + + if (__copy_from_user(buf, from, ELF_NVSRHALFREG * sizeof(double))) + return 1; + for (i = 0; i < ELF_NVSRHALFREG ; i++) + task->thread.ckfp_state.fpr[i][TS_VSRLOWOFFSET] = buf[i]; + return 0; +} +#endif /* CONFIG_PPC_TRANSACTIONAL_MEM */ +#else +inline unsigned long copy_fpr_to_user(void __user *to, + struct task_struct *task) +{ + return __copy_to_user(to, task->thread.fp_state.fpr, + ELF_NFPREG * sizeof(double)); +} + +inline unsigned long copy_fpr_from_user(struct task_struct *task, + void __user *from) +{ + return __copy_from_user(task->thread.fp_state.fpr, from, + ELF_NFPREG * sizeof(double)); +} + +#ifdef CONFIG_PPC_TRANSACTIONAL_MEM +inline unsigned long copy_ckfpr_to_user(void __user *to, +struct task_struct *task) +{ + return __copy_to_user(to, task->thread.ckfp_state.fpr, +
[PATCH v2 0/4] Disable compat cruft on ppc64le v2
With endian switch disabled by default the ppc64le compat supports ppc32le only which is something next to nobody has binaries for. Less code means less bugs so drop the compat stuff. I am not particularly sure about the best way to resolve the llseek situation. I don't see anything in the syscal tables making it 32bit-only so I suppose it should be available on 64bit as well. This is tested on ppc64le top of https://patchwork.ozlabs.org/cover/1153556/ Changes in v2: saner CONFIG_COMPAT ifdefs Thanks Michal Michal Suchanek (4): fs: always build llseek. powerpc: move common register copy functions from signal_32.c to signal.c powerpc/64: make buildable without CONFIG_COMPAT powerpc/64: Disable COMPAT if littleendian. arch/powerpc/Kconfig | 2 +- arch/powerpc/include/asm/syscall.h | 2 + arch/powerpc/kernel/Makefile | 15 ++- arch/powerpc/kernel/entry_64.S | 2 + arch/powerpc/kernel/signal.c | 146 - arch/powerpc/kernel/signal_32.c| 140 --- arch/powerpc/kernel/syscall_64.c | 5 +- arch/powerpc/kernel/vdso.c | 4 +- arch/powerpc/perf/callchain.c | 14 ++- fs/read_write.c| 2 - 10 files changed, 177 insertions(+), 155 deletions(-) -- 2.22.0