Power management (PM) allows control of the power consumption by managing voltages and frequencies of the different elements in a SOC. Digi provides an API with a set of functions to control the power consumption of the module by managing the frequency of the CPU and GPU.

To use this API, include the following header file:

#include <libdigiapix/pwr_management.h>

Manage governors

Governors are power schemes for the CPU. Only one governor may be active at a time. You can configure and set the governor with the following functions:

Function Description
governor_mode_t ldx_cpu_get_governor();

Returns the current governor struct.

int ldx_cpu_set_governor(
		governor_mode_t governor);

Sets the CPU governor to the given value.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

int ldx_cpu_is_governor_available(
		governor_mode_t governor);

Checks whether the governor is supported in the CPU.

It returns EXIT_SUCCESS if the governor is supported, EXIT_FAILURE otherwise.

governor_mode_t ldx_cpu_get_governor_type_from_string(
		const char *governor_string);

Returns the governor struct for the given string.

const char *ldx_cpu_get_governor_string_from_type(
		governor_mode_t governor);

Returns the string representation of the given governor struct.

Some governors may not be available for your platform.
List and set governor
int i;
governor_mode_t governor_mode;

/* List available governors */
printf("These are the available governors:\n");
for (i = 0; i < MAX_GOVERNORS; i++) {
	if (ldx_cpu_is_governor_available(i) == EXIT_SUCCESS) {
		printf("\t\t\t%s\n", ldx_cpu_get_governor_string_from_type(i));
	}
}

printf("This is the current governor: %s\n", ldx_cpu_get_governor_string_from_type(ldx_cpu_get_governor()));

/* Set the userspace governor */
governor_mode = ldx_cpu_get_governor_type_from_string("userspace");
if (governor_mode != GOVERNOR_INVALID) {
	ldx_cpu_set_governor(governor_mode);
}

Establish CPU frequencies

You can use the following functions to set and read CPU frequencies:

Function Description
available_frequencies_t
	ldx_cpu_get_available_freq();

Returns an available_frequencies_t struct with the following fields:

  • data: An array with the values of the frequencies.

  • len: The size of the data array.

You must free the requested available_frequencies_t struct when it is no longer required.
void ldx_cpu_free_available_freq(
	available_frequencies_t freq);

Frees a previously requested available_frequencies_t struct.

List available frequencies
int i;
available_frequencies_t freq = ldx_cpu_get_available_freq();

printf("These are the available frequencies:\n");
for (i = 0; i < freq.len; i++) {
	printf("\t\t\t%d\n", freq.data[i]);
}

ldx_cpu_free_available_freq(freq);
Function Description
int ldx_cpu_get_max_freq();

Returns the maximum frequency supported by the CPU, -1 on error.

int ldx_cpu_get_min_freq();

Returns the minimum frequency supported by the CPU, -1 on error.

Get the minimum and maximum frequencies
printf("This is the minimum frequency of the CPU %d\n", ldx_cpu_get_min_freq());

printf("This is the maximum frequency of the CPU %d\n", ldx_cpu_get_max_freq());

The scaling frequency is used in by the governors to determine the operation frequency.

Function Description
int ldx_cpu_get_max_scaling_freq();

Returns the maximum scaling frequency of the CPU, -1 on error.

int ldx_cpu_set_max_scaling_freq(int freq);

Sets the maximum scaling frequency of the CPU.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

int ldx_cpu_get_min_scaling_freq();

Returns the minimum scaling frequency of the CPU, -1 on error.

int ldx_cpu_set_min_scaling_freq(int freq);

Sets the minimum scaling frequency of the CPU.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

int ldx_cpu_get_scaling_freq();

Returns the current scaling frequency of the CPU, -1 on error.

int ldx_cpu_set_scaling_freq(int freq);

Sets the scaling frequency of the CPU.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

Get and set minimum and maximum scaling frequencies
int min_scaling_freq, max_scaling_freq;

min_scaling_freq = ldx_cpu_get_min_scaling_freq();
printf("This is the minimum scaling frequency of the CPU %d\n", min_scaling_freq);

max_scaling_freq = ldx_cpu_get_max_scaling_freq();
printf("This is the maximum scaling frequency of the CPU %d\n", max_scaling_freq);

/* To obtain better performance, set min_scaling_freq to the maximum frequency */
ldx_cpu_set_min_scaling_freq(max_scaling_freq);

Establish GPU frequency

The ConnectCore 6UL does not have a GPU, so the functions in this section have no effect on this platform.

Another way to reduce the power consumption of the module is to lower the GPU frequency. Digi provides a set of functions to lower the frequency by controlling the GPU prescaler.

Note that lowering the GPU clock frequency will impact graphic performance.
Function Description
int ldx_gpu_get_min_multiplier();

Returns the minimum multiplier of the GPU, -1 on error.

int ldx_gpu_set_min_multiplier(
			int multiplier);

Sets the minimum multiplier of the GPU.

This multiplier is applied when the CPU temperature reaches the passive trip point.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

int ldx_gpu_get_multiplier();

Returns the current multiplier of the GPU, -1 on error.

int ldx_gpu_set_multiplier(
			int multiplier);

Sets the current multiplier for the GPU.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

Get and set GPU multiplier
int min_multiplier = ldx_gpu_get_min_multiplier();
printf("This is the GPU min scaling: %d\n", min_multiplier);

/* To reduce power consumption, set the current scale to a lower value*/
/* This will impact GPU performance */
ldx_gpu_set_multiplier(ldx_gpu_get_multiplier() / 2);

Manage temperature

Module temperature is directly related to power consumption. Digi’s power management API allows you to read and define temperatures thresholds. The Linux kernel defines two temperature trip points:

  • passive: when the CPU temperature exceeds this temperature, the kernel takes certain cooling actions such as reducing the GPU scaling frequency.

  • critical: when the CPU temperature exceeds this temperature, the system shuts down.

Function Description
int ldx_cpu_get_current_temp();

Returns the current temperature reported by the CPU, -1 on error.

int ldx_cpu_get_passive_trip_point();

Returns the passive temperature of the CPU, -1 on error.

int ldx_cpu_set_passive_trip_point(
			int temp);

Sets the passive trip point of the CPU.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

int ldx_cpu_get_critical_trip_point();

Returns the critical temperature of the CPU, -1 on error.

int ldx_cpu_set_critical_trip_point(
			int temp);

Sets the critical trip point of the CPU.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

Manage temperature trip points
printf("This is the current CPU temperature: %d\n", ldx_cpu_get_current_temp());
printf("This is the current critical trip point: %d\n", ldx_cpu_get_critical_trip_point());
printf("This is the current passive trip point: %d\n", ldx_cpu_get_passive_trip_point());

Manage CPU cores

Another way to reduce the power consumption of the module is to disable CPU cores.

Function Description
int ldx_cpu_get_usage();

Returns CPU usage in percentage, -1 on error.

int ldx_cpu_get_number_of_cores();

Gets the number of cores available in the CPU, -1 on error.

int ldx_cpu_enable_core(int core);

Enables the core selected by its index. The index starts at 0.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

int ldx_cpu_disable_core(int core);

Disables the core selected by its index. The index starts at 0.

It returns EXIT_SUCCESS on success, EXIT_FAILURE otherwise.

You can disable all cores but one. If you attempt to disable the last remaining core, the system returns an error.
Work with the CPU
int cores = ldx_cpu_get_number_of_cores();
printf("This is the number of cores: %d\n", cores);

printf("This is the current CPU usage: %d\n", ldx_cpu_get_usage());

if (cores >= 2) {
	/* If we have two or more cores disable one */
	ldx_cpu_disable_core(0);
}

Power management example

The following examples demonstrate how to manage the CPU using the APIx:

  • apix-cpu-example: demonstrates how to obtain and set different CPU parameters.

  • apix-pm-application: demonstrates how to manage the CPU & GPU using the APIX.

Import the power management API examples in Eclipse using the Digi Embedded Yocto plugin. For more information, see Create a new DEY sample project. These examples are included in Digi Embedded Yocto. Go to GitHub to see the source code.