domingo, 24 de agosto de 2008

Gestión velocidad procesador en Linux (CPUFreq)

Entre ayer y hoy he estado haciendo pruebas de lo del título. Con estas pruebas he conseguido entender cómo funciona y voy a intentar compartirlo con todos vosotros ( y por qué no, tenerlo escrito para mi, que con mi edad estoy un poco falto de fósforo
Con el fin de reducir el consumo de nuestros equipos, las sistemas operativos lo que hacen es cuando no se necesita toda la potencia del procesador, reducir la velocidad a la que trabajan (y en consecuencia el consumo). En los kernel de linux actuales (2.6.x) estas funcionalides están directamente incluidas. Es más, distribuciones como knoppix o ubuntu lo llevan activado. Pero si vamos a Debian, he probado con una 4.0r4a, nos encontramos con que no está activado por defecto.
El control de velocidad de la CPU tiene dos partes: por una parte un “driver” que permite controlar la velocidad de la CPU, y por otra parte un módulo que se encarga de decidir a qué velocidad debe estar la CPU (governor).
En los kernel actuales ambas partes de programas son módulos del kernel. Los drivers de gestión de la velocidad se encuentran en un directorio parecido al siguiente: /lib/modules/2.6.18-6-486/kernel/arch/i386/kernel/cpu/cpufreq. El governor en /lib/modules/2.6.18-6-486/kernel/drivers/cpufreq
En el primer directorio vamos a encontrar varios módulos, que dependiendo de nuestra CPU se encargarán de hablar con ella para decirle a qué velocidad funcionar… por ejemplo tendremos un módulo para máquinas centrino (speedstep-centrino), para varios procesadores de AMD (los powernow-k?)… y si no hay uno específico para tu cpu puedes probar con el acpi-cpufreq. El primer paso para habilitar la gestión será cargar uno de estos módulos, por ejemplo “modprobe acpi-cpufreq”
Después tenemos que decidir qué política emplear para gestionar la velocidad en relación a la carga. Casi todas las distribuciones suelen usar el cpufreq-ondemand (a mi también es el que más me ha gustado). Mira el resto y sino ejecuta el “modprobe cpufreq-ondemand”. Así como drivers sólo puede tener uno, governors puede tener varios cargados y después activar el que queramos.
Una vez cargado el driver y el gobernor, es necesario activarlo. La forma complicada de hacerlo es ir a los ficheros del directorio: /sys/devices/system/cpu/cpu0/cpufreq (o cpu1 si tienes dos procesadores…). En este directorio vamos a tener varios ficheros sobre los que podemos escribir/leer. Quizás el más importante sea el scaling_governor, que nos dice o estable qué governor activar. Por ejemplo para activar el ondemand podríamos hacer “echo ondemand >scaling_governor”. Con esto ya tendríamos todo el sistema funcionando.
He dicho que la forma complicada es ir a los ficheros directamente, existen formas más amigables. Descarga por ejemplo el paquete cpufrequtils y ejecuta los siguientes comandos: “cpufreq-set -g ondemand” y “cpufreq-info”
Una vez hecho los pasos anteriores, tenemos el sistema funcionado… y ¿cómo lo podríamos probarlo? Lo más fácil para saber a cuanto va nuestro procesador es ejecutar el cpufreq-info (también se podría hacer un cat /proc/cpuinfo). Si no estamos haciendo nada con el ordenador seguramente el equipo estará a su mínima velocidad.
Una forma rápida de cargar la cpu del equipo es con un programa tan simple como el siguiente:
// CPUstress.c

// compile with: gcc cpustree.c -o cpustree -Wall
int main(void){

float a=1;

while(1) { a=(a+1)*34.789; a=a/32.986; }

return 0;

}
En cuanto lo ejecutes la cpu subirá al 100% (si tienes varios procesadores subirá sólo uno de ellos, pero podrás ejecutarlo varias veces :-) y el procesador se pondrá a más velocidad. Es muy útil para ver como cambian las velocidades con los diferentes governors.
Espero que esto sirva como punto de partida para entender cómo funciona esta gestión… a mi me ha servido