Running PowerTOP on OMAP35x platform

From Texas Instruments Embedded Processors Wiki

Jump to: navigation, search
Translate this page to   

Contents

Introduction

The Linux port on OMAP35x supports multiple C-states (idle states) corresponding to different levels of power savings that can be achieved. The amount of power saved depends upon optimal choice of idle state.

This is exactly where PowerTOP comes handy. It collates various kernel statistics to help us visualize the 'activities' when system is idle. We can, now, confirm if the system is behaving as expected. Or, identify 'rogue' tasks/ events that are stealing power.

This article describes the steps and changes to get PowerTOP running on the OMAP35x platforms. These steps can be replicated on other processors and EVMs as well.

Background

Until recently, timer-tick was a periodic event causing CPU to use power - even when the system is idle. The 'tickless kernel' has enabled systems to stay in low power mode for much longer - enabling better power savings.

PowerTOP is Linux tool that aims at identifying software components that are using power while the CPU is idle. It is one of Intel's "LessWatts.org" projects. It is based on (and driven by) the Intel Processors and released under the GNU General Public License (version 2).

Kernel Configuration

The Linux kernel needs to be instrumented to gather relavent statistics. This section describes changes to default configuration.

  1. Create default configuration for the OMAP3EVM.
    $ make omap3_evm_defconfig
    NOTE: In the Linux PSP versions earlier than version 1.0.x, this command will be: make omap3evm_defconfig.
  2. Invoke Linux Kernel Configuration tool
    $ make menuconfig
  3. On the first screen, select the option Kernel hacking.
    Networking --->
    Device Drivers --->
    File systems --->
    Kernel hacking --->
    Security options --->
  4. Now select the option Collect kernel timers statistics.
    [ ] Collect scheduler statistics
    [*] Collect kernel timers statistics
    [ ] Debug object operations
    [ ] Debug slab memory allocations
  5. Now, build the kernel as usual.
    $ make uImage

Getting necessary sources

For simplicity, this article assumes that all sources are extracted besides the linux kernel sources as shown below:

/home/user/work
  |
  +-- linux
  |
  +-- ncurses
  |
  +-- powertop

Updates to PowerTOP

The changes are described here through "diff" between original and modified code. Consolidated patch containing the changes described below is available here.

Makefile

-WARNFLAGS=-Wall  -W -Wshadow
-CFLAGS?=-O1 -g ${WARNFLAGS}
-CC?=gcc
+WARNFLAGS=-Wall -Wstrict-prototypes
+INCPATH?=-I ../ncurses/include \
+          -I ../ncurses/include/ncurses \
+          -isystem /opt/codesourcery/2008q1/lib/gcc/arm-none-linux-gnueabi/4.2.3/include
+LIBPATH?=-L ../ncurses/lib
+
+CFLAGS?=-march=armv7a -DOMAP3 -pipe -O1 -g ${WARNFLAGS} ${INCPATH} ${LIBPATH}
+ 
+CC=arm-none-linux-gnueabi-gcc
 powertop: $(OBJS) Makefile powertop.h
-	$(CC) ${CFLAGS}  $(OBJS) -lncursesw -o powertop
+	$(CC) ${CFLAGS}  $(OBJS) -l ncurses -o powertop
 	@(cd po/ && $(MAKE))
-	sata.o xrandr.o ethernet.o cpufreqstats.o usb.o urbnum.o intelcstates.o
+	sata.o xrandr.o ethernet.o cpufreqstats.o usb.o urbnum.o intelcstates.o omapcstates.o

powertop.h

 #include <libintl.h>
 
+#if defined(__I386__)
+#define MAX_NUM_CSTATES 4
+#define MAX_NUM_PSTATES 5
+
+#elif defined(OMAP3)
+#define MAX_NUM_CSTATES 7
+#define MAX_NUM_PSTATES 5
+
+#else
+#error "No valid architecture is defined."
+#endif
+
+#define MAX_CSTATE_LINES (MAX_NUM_CSTATES + 3)
+
-extern char cstate_lines[12][200];
-extern char cpufreqstrings[5][80];
+extern char cstate_lines[MAX_CSTATE_LINES][200];
+extern char cpufreqstrings[MAX_NUM_PSTATES][80];

powertop.c

-char cstate_lines[12][200];
+char cstate_lines[MAX_CSTATE_LINES][200];
-		topcstate = -4;
+
+		topcstate = -(MAX_NUM_CSTATES);
+
-			for (i = 0; i < 8; i++)
+
+			for (i = 0; i < MAX_NUM_CSTATES; i++)
+
+#if defined (__I386__)
 	print_intel_cstates();
+#elif defined (OMAP3)
+	print_omap3_cstates();
+#endif
+

display.c

-	for (i=0; i < 10; i++) {
+	for (i=0; i < MAX_CSTATE_LINES; i++) {
-		if (strlen(cstate_lines[i]) && count <= 6) {
+		if (strlen(cstate_lines[i]) && count <= MAX_CSTATE_LINES) {
-	for (i=0; i<5; i++) {
+	for (i=0; i < MAX_NUM_PSTATES; i++) {
+	int yline = MAX_NUM_CSTATES;
+
 	getmaxyx(stdscr, maxy, maxx);
 
 	zap_windows();	
 
 	title_bar_window = subwin(stdscr, 1, maxx, 0, 0);
-	cstate_window = subwin(stdscr, 7, maxx, 2, 0);
-	wakeup_window = subwin(stdscr, 1, maxx, 9, 0);
-	acpi_power_window = subwin(stdscr, 2, maxx, 10, 0);
-	timerstat_window = subwin(stdscr, maxy-16, maxx, 12, 0);
+
+	cstate_window = subwin(stdscr, (yline + 2), maxx, 2, 0);
+	wakeup_window = subwin(stdscr, 1, maxx, (yline + 5), 0);
+	acpi_power_window = subwin(stdscr, 2, maxx, (yline + 6), 0);
+	timerstat_window = subwin(stdscr, maxy-16, maxx, (yline + 8), 0);
+

cpufreqstats.c

-char cpufreqstrings[5][80];
+char cpufreqstrings[MAX_NUM_PSTATES][80];
+

omapcstates.c

/*
 * Copyright 2008, Texas Instruments Incorporated.
 *
 * This file prints the C states supported by the OMAP processor.
 * (Based on intelcstates.c)
 *
 * This program 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; version 2 of the License.
 *
 * This program 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.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program in a file named COPYING; if not, write to the
 * Free Software Foundation, Inc.,
 * 51 Franklin Street, Fifth Floor,
 * Boston, MA 02110-1301 USA
 */

#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
#include <sys/types.h>
#include <dirent.h>
#include <ctype.h>

#include "powertop.h"


#if defined(OMAP3)
/**
 * print_omap3_cstates() - Prints the list of supported C-states.
 *
 * This functions uses standard sysfs interface of the cpuidle framework
 * to extract the information of the C-states supported by the Linux
 * kernel. 
 **/
void print_omap3_cstates(void)
{
	DIR *dir;
	struct dirent *entry;

	dir = opendir("/sys/devices/system/cpu/cpu0/cpuidle");

	if (dir) {
		printf(_("Supported C-states : "));

		while ((entry = readdir(dir))) {
			if (strlen(entry->d_name) < 3)
				continue;

			printf("C%s ", entry->d_name);
		}
		printf("\n");

		closedir(dir);
	}
}
#endif

Build

$ setenv CC  /opt/codesourcery/2008q1/bin/arm-none-linux-gnueabi-gcc
$ setenv CXX /opt/codesourcery/2008q1/bin/arm-none-linux-gnueabi-g++

ncurses

$ ./configure \
        --host=arm-none-linux-gnueabi \
        --target=arm-none-linux-gnueabi \
        --with-shared \
        --without-ada
$ make CROSS_COMPILE=arm-none-linux-gnueabi-
$ make install DESTDIR=/home/user/work/ncurses/_install

The contents of the directory _install need to be copied on the target filesystem.

PowerTOP

$ make CROSS_COMPILE=arm-none-linux-gnueabi-

The executable powertop needs to be copied on target filesystem. The directory /usr/local/bin is a good choice for copying the executable.

Example session

Boot the OMAP3EVM with uImage created earlier (with additional instrumentation enabled).

$ powertop --help
Usage: powertop [OPTION...]
  -d, --dump            read wakeups once and print list of top offenders
  -t, --time=DOUBLE     default time to gather data in seconds
  -h, --help            Show this help message
$ powertop

References

E2e.jpg For technical support on OMAP please post your questions on The OMAP Forum. Please post only comments about the article Running PowerTOP on OMAP35x platform here.
Hyperlink blue.png Links
ARM Microcontroller MCU ARM Processor Digital Media Processor Digital Signal Processing Microcontroller MCU Multi Core Processor
Ultra Low Power DSP 8 bit Microcontroller MCU 16 bit Microcontroller MCU 32 bit Microcontroller MCU

Leave a Comment
Personal tools
Namespaces
Variants
Actions
Navigation
Print/export
Toolbox