Quelqu’un peut-il expliquer le registre de contrôle de la puissance dans exynos ARM?

Dans le kernel Linux, plus précisément dans /arch/arm/mach-exynos/cpuidle.c sous 3.9-rc6, les lignes se lisent

static unsigned int g_pwr_ctrl, g_diag_reg; static void save_cpu_arch_register(void) { /*read power control register*/ asm("mrc p15, 0, %0, c15, c0, 0" : "=r"(g_pwr_ctrl) : : "cc"); /*read diagnostic register*/ asm("mrc p15, 0, %0, c15, c0, 1" : "=r"(g_diag_reg) : : "cc"); return; } 

Après avoir étudié le problème, il semble s’agir d’un assemblage en ligne gcc . Considérant que c’est un élément essentiel, l’ asm lit ceci, c’est soit

  1. Plus rapide et donc plus efficace
  2. Non disponible en C

J’ai vérifié le manuel ARM pour MCR pendant que j’apprenais l’assemblage, mais je pouvais dire que MCR était un coprocesseur en raison de sa longueur de trois lettres. Le inline asm semble accéder au registre de contrôle de l’ alimentation et sauvegarder le résultat (du registre) dans un entier non signé de la première ligne (à appeler à un moment donné, je suppose).

En ce qui concerne le registre de contrôle de puissance, le manuel du arm répertorie,

  • la latence de l’horloge pour votre implémentation du processeur Cortex-A9
  • synchronisation d’horloge dynamic.

J’ai du mal à comprendre pourquoi c’est nécessaire, on peut y accéder à la volée, dans une fonction.

Enfin, le manuel ARM répertorie la conception du registre large 32 bits. L’horloge de base semble être réglée là-bas, lisons-nous cela tout en démarrant à partir d’un processus de contexte inactif?

J’ai également trouvé une question similaire – cela peut aussi vous aider.

Votre question manque de concentration, envisagez de la mettre à jour. Je suppose que vous essayez de comprendre le mécanisme de suspension / reprise exynos dans le kernel Linux.

Pourquoi assembleur en ligne

… cela semble être un assemblage en ligne gcc . Considérant que c’est un élément essentiel, l’asm lit ceci, c’est soit
a) plus rapide et donc plus efficace;
b) non disponible en C

Nous choisissons l’option b , il n’existe aucun moyen d’exprimer mcr / mrc en C.

Liste de clobeurs en ligne

Deuxièmement, … : : "cc");

Ceci est une liste de désinscription gcc . Il dit que les codes de condition seront modifiés par l’instruction. C’est peut-être juste pour s’assurer que gcc décide de ne pas ignorer cette instruction. Vous pouvez en lire plus dans le manuel de gcc .

Qu’est-ce que cela fait

J’ai du mal à comprendre pourquoi c’est nécessaire, on peut y accéder à la volée, dans une fonction.

La partie que vous devez regarder est exynos4_enter_core0_aftr() . Ceci utilise à la fois save_cpu_arch_register() et restore_cpu_arch_register() . Il existe donc un double ensemble de fonctions et nous notons que les valeurs sont stockées dans des globals . L’autre chose à noter est le cpu_suspend(0, idle_finisher); . Cette fonction indique à Linux que le cpu est suspendu puis appelle cpu_do_idle(); qui est généralement une instruction ARM WFI ( attendre une interruption ). Cela fait geler le processeur à cette instruction jusqu’à ce qu’une interruption activée se déclenche. Le problème avec la suspension d’une horloge du processeur à pleine vitesse est que cela peut gaspiller du courant / de l’énergie. En règle générale, les horloges de la SDRAM et de la plate-forme peuvent être automatiquement mises à l’état basse consommation dans ce mode.

Vous devrez consulter les fiches techniques sur votre CPU / SOC pour plus d’informations. Cependant, revenons à la question. Il est fort probable que ce mode à faible consommation détruit / modifie ces registres de coprocesseur. Par conséquent, save_cpu_arch_register() et restore_cpu_arch_register() sont nécessaires pour garantir qu’ils restnt tels qu’avant l’appel. Le code pourrait probablement utiliser des locales dans exynos4_enter_core0_aftr() . Ils doivent être sauvegardés et restaurés ou le processeur peut reprendre avec une alimentation / une tension / des horloges étranges. Il se peut également que cpu_do_idle() soit cpu_do_idle() par votre machine et qu’il modifie ces registres.

En bref, cette fonction permet de sauvegarder un état qui sera détruit lorsque la CPU se mettra en veille ou attendra le mode d’ interruption .