# git rev-parse -q --verify b6fbf9e64995137a57c19b0aa7f6c76c727439dc^{commit} b6fbf9e64995137a57c19b0aa7f6c76c727439dc already have revision, skipping fetch # git checkout -q -f -B kisskb b6fbf9e64995137a57c19b0aa7f6c76c727439dc # git clean -qxdf # git log -1 commit b6fbf9e64995137a57c19b0aa7f6c76c727439dc Author: Alistair Popple Date: Fri Mar 2 16:18:45 2018 +1100 powerpc/powernv/npu: Fix deadlock in mmio_invalidate() When sending TLB invalidates to the NPU we need to send extra flushes due to a hardware issue. The original implementation would lock the all the ATSD MMIO registers sequentially before unlocking and relocking each of them sequentially to do the extra flush. This introduced a deadlock as it is possible for one thread to hold one ATSD register whilst waiting for another register to be freed while the other thread is holding that register waiting for the one in the first thread to be freed. For example if there are two threads and two ATSD registers: Thread A Thread B ---------------------- Acquire 1 Acquire 2 Release 1 Acquire 1 Wait 1 Wait 2 Both threads will be stuck waiting to acquire a register resulting in an RCU stall warning or soft lockup. This patch solves the deadlock by refactoring the code to ensure registers are not released between flushes and to ensure all registers are either acquired or released together and in order. Fixes: bbd5ff50afff ("powerpc/powernv/npu-dma: Add explicit flush when sending an ATSD") Signed-off-by: Alistair Popple Signed-off-by: Michael Ellerman # < /opt/cross/kisskb/gcc-5.3.0-nolibc/powerpc64-linux/bin/powerpc64-linux-gcc --version # < git log --format=%s --max-count=1 b6fbf9e64995137a57c19b0aa7f6c76c727439dc # < make -s -j 80 ARCH=powerpc O=/kisskb/build/powerpc-next_44x_iss476-smp_defconfig_powerpc-5.3 CROSS_COMPILE=/opt/cross/kisskb/gcc-5.3.0-nolibc/powerpc64-linux/bin/powerpc64-linux- 44x/iss476-smp_defconfig warning: (PPC_PSERIES && PM_SLEEP_SMP) selects HOTPLUG_CPU which has unmet direct dependencies (SMP && (PPC_PSERIES || PPC_PMAC || PPC_POWERNV || FSL_SOC_BOOKE)) warning: (PPC_PSERIES && PM_SLEEP_SMP) selects HOTPLUG_CPU which has unmet direct dependencies (SMP && (PPC_PSERIES || PPC_PMAC || PPC_POWERNV || FSL_SOC_BOOKE)) # make -s -j 80 ARCH=powerpc O=/kisskb/build/powerpc-next_44x_iss476-smp_defconfig_powerpc-5.3 CROSS_COMPILE=/opt/cross/kisskb/gcc-5.3.0-nolibc/powerpc64-linux/bin/powerpc64-linux- warning: (PPC_PSERIES && PM_SLEEP_SMP) selects HOTPLUG_CPU which has unmet direct dependencies (SMP && (PPC_PSERIES || PPC_PMAC || PPC_POWERNV || FSL_SOC_BOOKE)) warning: (PPC_PSERIES && PM_SLEEP_SMP) selects HOTPLUG_CPU which has unmet direct dependencies (SMP && (PPC_PSERIES || PPC_PMAC || PPC_POWERNV || FSL_SOC_BOOKE)) WARNING: modpost: Found 1 section mismatch(es). To see full details build your kernel with: 'make CONFIG_DEBUG_SECTION_MISMATCH=y' INFO: Uncompressed kernel (size 0x60d0c0) overlaps the address of the wrapper(0x400000) INFO: Fixing the link_address of wrapper to (0x700000) INFO: Uncompressed kernel (size 0x60d0c0) overlaps the address of the wrapper(0x400000) INFO: Fixing the link_address of wrapper to (0x700000) Completed OK # rm -rf /kisskb/build/powerpc-next_44x_iss476-smp_defconfig_powerpc-5.3 # Build took: 0:00:57.023203