[PATCH] powerpc/pseries: Fix CONFIG_DTL=n build

Guenter Roeck linux at roeck-us.net
Sat Oct 15 04:03:35 AEDT 2022


On Thu, Oct 13, 2022 at 05:31:31PM +1000, Nicholas Piggin wrote:
> The recently moved dtl code must be compiled-in if
> CONFIG_VIRT_CPU_ACCOUNTING_NATIVE=y even if CONFIG_DTL=n.
> 
> Reported-by: Guenter Roeck <linux at roeck-us.net>
> Fixes: 6ba5aa541aaa0 ("powerpc/pseries: Move dtl scanning and steal time accounting to pseries platform")
> Signed-off-by: Nicholas Piggin <npiggin at gmail.com>

Tested-by: Guenter Roeck <linux at roeck-us.net>

> ---
>  arch/powerpc/platforms/pseries/Makefile |   3 +-
>  arch/powerpc/platforms/pseries/dtl.c    | 151 +++++++++++++-----------
>  2 files changed, 80 insertions(+), 74 deletions(-)
> 
> diff --git a/arch/powerpc/platforms/pseries/Makefile b/arch/powerpc/platforms/pseries/Makefile
> index 14e143b946a3..92310202bdd7 100644
> --- a/arch/powerpc/platforms/pseries/Makefile
> +++ b/arch/powerpc/platforms/pseries/Makefile
> @@ -7,7 +7,7 @@ obj-y			:= lpar.o hvCall.o nvram.o reconfig.o \
>  			   setup.o iommu.o event_sources.o ras.o \
>  			   firmware.o power.o dlpar.o mobility.o rng.o \
>  			   pci.o pci_dlpar.o eeh_pseries.o msi.o \
> -			   papr_platform_attributes.o
> +			   papr_platform_attributes.o dtl.o
>  obj-$(CONFIG_SMP)	+= smp.o
>  obj-$(CONFIG_KEXEC_CORE)	+= kexec.o
>  obj-$(CONFIG_PSERIES_ENERGY)	+= pseries_energy.o
> @@ -19,7 +19,6 @@ obj-$(CONFIG_HVC_CONSOLE)	+= hvconsole.o
>  obj-$(CONFIG_HVCS)		+= hvcserver.o
>  obj-$(CONFIG_HCALL_STATS)	+= hvCall_inst.o
>  obj-$(CONFIG_CMM)		+= cmm.o
> -obj-$(CONFIG_DTL)		+= dtl.o
>  obj-$(CONFIG_IO_EVENT_IRQ)	+= io_event_irq.o
>  obj-$(CONFIG_LPARCFG)		+= lparcfg.o
>  obj-$(CONFIG_IBMVIO)		+= vio.o
> diff --git a/arch/powerpc/platforms/pseries/dtl.c b/arch/powerpc/platforms/pseries/dtl.c
> index 1b1977bc78e7..3f1cdccebc9c 100644
> --- a/arch/powerpc/platforms/pseries/dtl.c
> +++ b/arch/powerpc/platforms/pseries/dtl.c
> @@ -18,6 +18,7 @@
>  #include <asm/plpar_wrappers.h>
>  #include <asm/machdep.h>
>  
> +#ifdef CONFIG_DTL
>  struct dtl {
>  	struct dtl_entry	*buf;
>  	int			cpu;
> @@ -57,78 +58,6 @@ static DEFINE_PER_CPU(struct dtl_ring, dtl_rings);
>  
>  static atomic_t dtl_count;
>  
> -/*
> - * Scan the dispatch trace log and count up the stolen time.
> - * Should be called with interrupts disabled.
> - */
> -static notrace u64 scan_dispatch_log(u64 stop_tb)
> -{
> -	u64 i = local_paca->dtl_ridx;
> -	struct dtl_entry *dtl = local_paca->dtl_curr;
> -	struct dtl_entry *dtl_end = local_paca->dispatch_log_end;
> -	struct lppaca *vpa = local_paca->lppaca_ptr;
> -	u64 tb_delta;
> -	u64 stolen = 0;
> -	u64 dtb;
> -
> -	if (!dtl)
> -		return 0;
> -
> -	if (i == be64_to_cpu(vpa->dtl_idx))
> -		return 0;
> -	while (i < be64_to_cpu(vpa->dtl_idx)) {
> -		dtb = be64_to_cpu(dtl->timebase);
> -		tb_delta = be32_to_cpu(dtl->enqueue_to_dispatch_time) +
> -			be32_to_cpu(dtl->ready_to_enqueue_time);
> -		barrier();
> -		if (i + N_DISPATCH_LOG < be64_to_cpu(vpa->dtl_idx)) {
> -			/* buffer has overflowed */
> -			i = be64_to_cpu(vpa->dtl_idx) - N_DISPATCH_LOG;
> -			dtl = local_paca->dispatch_log + (i % N_DISPATCH_LOG);
> -			continue;
> -		}
> -		if (dtb > stop_tb)
> -			break;
> -		if (dtl_consumer)
> -			dtl_consumer(dtl, i);
> -		stolen += tb_delta;
> -		++i;
> -		++dtl;
> -		if (dtl == dtl_end)
> -			dtl = local_paca->dispatch_log;
> -	}
> -	local_paca->dtl_ridx = i;
> -	local_paca->dtl_curr = dtl;
> -	return stolen;
> -}
> -
> -/*
> - * Accumulate stolen time by scanning the dispatch trace log.
> - * Called on entry from user mode.
> - */
> -void notrace pseries_accumulate_stolen_time(void)
> -{
> -	u64 sst, ust;
> -	struct cpu_accounting_data *acct = &local_paca->accounting;
> -
> -	sst = scan_dispatch_log(acct->starttime_user);
> -	ust = scan_dispatch_log(acct->starttime);
> -	acct->stime -= sst;
> -	acct->utime -= ust;
> -	acct->steal_time += ust + sst;
> -}
> -
> -u64 pseries_calculate_stolen_time(u64 stop_tb)
> -{
> -	if (!firmware_has_feature(FW_FEATURE_SPLPAR))
> -		return 0;
> -
> -	if (get_paca()->dtl_ridx != be64_to_cpu(get_lppaca()->dtl_idx))
> -		return scan_dispatch_log(stop_tb);
> -
> -	return 0;
> -}
> -
>  /*
>   * The cpu accounting code controls the DTL ring buffer, and we get
>   * given entries as they are processed.
> @@ -436,3 +365,81 @@ static int dtl_init(void)
>  	return 0;
>  }
>  machine_arch_initcall(pseries, dtl_init);
> +#endif /* CONFIG_DTL */
> +
> +#ifdef CONFIG_VIRT_CPU_ACCOUNTING_NATIVE
> +/*
> + * Scan the dispatch trace log and count up the stolen time.
> + * Should be called with interrupts disabled.
> + */
> +static notrace u64 scan_dispatch_log(u64 stop_tb)
> +{
> +	u64 i = local_paca->dtl_ridx;
> +	struct dtl_entry *dtl = local_paca->dtl_curr;
> +	struct dtl_entry *dtl_end = local_paca->dispatch_log_end;
> +	struct lppaca *vpa = local_paca->lppaca_ptr;
> +	u64 tb_delta;
> +	u64 stolen = 0;
> +	u64 dtb;
> +
> +	if (!dtl)
> +		return 0;
> +
> +	if (i == be64_to_cpu(vpa->dtl_idx))
> +		return 0;
> +	while (i < be64_to_cpu(vpa->dtl_idx)) {
> +		dtb = be64_to_cpu(dtl->timebase);
> +		tb_delta = be32_to_cpu(dtl->enqueue_to_dispatch_time) +
> +			be32_to_cpu(dtl->ready_to_enqueue_time);
> +		barrier();
> +		if (i + N_DISPATCH_LOG < be64_to_cpu(vpa->dtl_idx)) {
> +			/* buffer has overflowed */
> +			i = be64_to_cpu(vpa->dtl_idx) - N_DISPATCH_LOG;
> +			dtl = local_paca->dispatch_log + (i % N_DISPATCH_LOG);
> +			continue;
> +		}
> +		if (dtb > stop_tb)
> +			break;
> +#ifdef CONFIG_DTL
> +		if (dtl_consumer)
> +			dtl_consumer(dtl, i);
> +#endif
> +		stolen += tb_delta;
> +		++i;
> +		++dtl;
> +		if (dtl == dtl_end)
> +			dtl = local_paca->dispatch_log;
> +	}
> +	local_paca->dtl_ridx = i;
> +	local_paca->dtl_curr = dtl;
> +	return stolen;
> +}
> +
> +/*
> + * Accumulate stolen time by scanning the dispatch trace log.
> + * Called on entry from user mode.
> + */
> +void notrace pseries_accumulate_stolen_time(void)
> +{
> +	u64 sst, ust;
> +	struct cpu_accounting_data *acct = &local_paca->accounting;
> +
> +	sst = scan_dispatch_log(acct->starttime_user);
> +	ust = scan_dispatch_log(acct->starttime);
> +	acct->stime -= sst;
> +	acct->utime -= ust;
> +	acct->steal_time += ust + sst;
> +}
> +
> +u64 pseries_calculate_stolen_time(u64 stop_tb)
> +{
> +	if (!firmware_has_feature(FW_FEATURE_SPLPAR))
> +		return 0;
> +
> +	if (get_paca()->dtl_ridx != be64_to_cpu(get_lppaca()->dtl_idx))
> +		return scan_dispatch_log(stop_tb);
> +
> +	return 0;
> +}
> +
> +#endif


More information about the Linuxppc-dev mailing list