Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753134AbdC2GBD (ORCPT ); Wed, 29 Mar 2017 02:01:03 -0400 Received: from Galois.linutronix.de ([146.0.238.70]:55358 "EHLO Galois.linutronix.de" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752847AbdC2GBC (ORCPT ); Wed, 29 Mar 2017 02:01:02 -0400 Date: Wed, 29 Mar 2017 08:00:52 +0200 (CEST) From: Thomas Gleixner To: Kan Liang cc: peterz@infradead.org, mingo@redhat.com, linux-kernel@vger.kernel.org, bp@alien8.de, acme@kernel.org, eranian@google.com, jolsa@kernel.org, ak@linux.intel.com Subject: Re: [PATCH V4 2/2] perf/x86: add sysfs entry to freeze counter on SMI In-Reply-To: <1490751920-44720-3-git-send-email-kan.liang@intel.com> Message-ID: References: <1490751920-44720-1-git-send-email-kan.liang@intel.com> <1490751920-44720-3-git-send-email-kan.liang@intel.com> User-Agent: Alpine 2.20 (DEB 67 2015-01-07) MIME-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Length: 1311 Lines: 56 On Tue, 28 Mar 2017, kan.liang@intel.com wrote: > +static void flip_smm_bit(void *data) > +{ > + int val = *(int *)data; > + > + msr_flip_bit(MSR_IA32_DEBUGCTLMSR, DEBUGCTLMSR_FREEZE_WHILE_SMM_BIT, (bool)val); I asked you before to use line breaks for lines over 80 chars. Is it that hard? > +static DEFINE_MUTEX(freeze_on_smi_mutex); > + > + static ssize_t freeze_on_smi_store(struct device *cdev, > + struct device_attribute *attr, > + const char *buf, size_t count) > +{ > + unsigned long val; > + ssize_t ret; > + > + ret = kstrtoul(buf, 0, &val); > + if (ret) > + return ret; > + > + if (val > 1) > + return -EINVAL; > + > + if (x86_pmu.attr_freeze_on_smi == val) > + return count; > + > + mutex_lock(&freeze_on_smi_mutex); This wants to protect the check above as well. > + > + get_online_cpus(); > + > + flip_smm_bit(&val); Sigh. This still is racy against preemption and interrupts. > + smp_call_function(flip_smm_bit, &val, 1); Yes, I had smp_call_function() in my example, but I'd expected that you figure out yourself to use on_each_cpu(), which calls the function on the calling cpu with interrupts disabled. > + put_online_cpus(); > + > + x86_pmu.attr_freeze_on_smi = val; Crap. So a CPU coming online between put_online_cpus() and the store will not see it. Sigh, tglx