2 votes

comment le chargeur de démarrage passe-t-il la ligne de commande du noyau au noyau ?

Nous pouvons voir la ligne de commande du noyau comme ceci :

ckim@chan-ubuntu:~/$ cat /proc/cmdline  
BOOT_IMAGE=/boot/vmlinuz-4.15.0-122-generic root=UUID=99c66a0a-39c1-451c-9f72-ad1576aafb41 ro quiet splash

Cette ligne de commande semble être ce que Grub a transmis au noyau pour le démarrage. Comment cette ligne de commande est-elle réellement transmise au programme du noyau ? Je suppose que la ligne de commande est chargée en mémoire sous la forme d'une chaîne de caractères et qu'un registre du processeur (comme x1, si processeur arm64) est réglé sur l'adresse de cette chaîne ? Je suis intéressé par le cas arm64 en particulier.

1voto

Rachid K. Points 2570

Dans le code source du noyau init/main.c le point d'entrée du noyau est start_kernel() :

[...]
/* Untouched command line saved by arch-specific code. */
char __initdata boot_command_line[COMMAND_LINE_SIZE];
[...]
asmlinkage __visible void __init start_kernel(void)
{
    char *command_line;
    char *after_dashes;

    set_task_stack_end_magic(&init_task);
    smp_setup_processor_id();
    debug_objects_early_init();

    cgroup_init_early();

    local_irq_disable();
    early_boot_irqs_disabled = true;

    /*
     * Interrupts are still disabled. Do necessary setups, then
     * enable them.
     */
    boot_cpu_init();
    page_address_init();
    pr_notice("%s", linux_banner);
    early_security_init();
    setup_arch(&command_line);
[...]
    pr_notice("Kernel command line: %s\n", boot_command_line);
[...]

Dans les lignes précédentes, il y a un appel à setup_arch() pour obtenir la ligne de commande d'une manière qui dépend de l'architecture.

Pour ARM64, setup_arch() est défini dans arch/arm64/kernel/setup.c :

void __init setup_arch(char **cmdline_p)
{
    init_mm.start_code = (unsigned long) _text;
    init_mm.end_code   = (unsigned long) _etext;
    init_mm.end_data   = (unsigned long) _edata;
    init_mm.brk    = (unsigned long) _end;

    *cmdline_p = boot_command_line;
[...]

Concernant le grub, il est détaillé ici .

1voto

SergA Points 558

La même question m'est parfois venue à l'esprit. C'est donc le moment de plonger en profondeur.

Alors que x86 utilise protocole spécial pour le démarrage Linux dans le cas de arm64 un schéma différent est utilisé . Pour la communication avec le noyau, le chargeur d'amorçage ne met qu'une seule adresse, celle du chargement. aplatir l'arbre du dispositif ( FDT ) dans le x0 registre.

Voici un extrait de Linux et l'arborescence des périphériques, configuration de l'exécution :

Dans la plupart des cas, un DT sera la seule méthode pour communiquer des données du données du microprogramme au noyau, et est donc aussi utilisé pour passer des configuration comme la chaîne de paramètres du noyau et la localisation d'une image initrd.

La plupart de ces données sont contenues dans le nœud /chosen, et lors du démarrage de Linux, il ressemblera à quelque chose comme ceci :

chosen {
        bootargs = "console=ttyS0,115200 loglevel=8";
        initrd-start = <0xc8000000>;
        initrd-end = <0xc8200000>;
};

Voici un autre exemple de DT .

Ensuite, au cours du démarrage anticipé du noyau, les OF/FDT analyse les données passées arbre des dispositifs y remplir boot_command_line variable .

0voto

Kaz Points 18072

Les détails varient en fonction du chargeur d'amorçage et de l'utilisateur. head.S module de démarrage en langage assembleur du noyau spécifique.

Sur Arm64, ce code de démarrage se trouve dans le fichier arch/arm64/kernel/head.S .

Lorsque le code de démarrage est invoqué, il suppose que les registres x0 par le biais de x3 sont des paramètres de démarrage et les enregistrent dans le fichier boot_params réseau. Plus tard, le code C valide que seul le premier paramètre est non nul. Les trois autres doivent être nuls ; de toute évidence, ils ont été utilisés historiquement.

Ainsi, il n'y a qu'un seul paramètre, effectivement. Quel est ce paramètre ? Le site x0 pointe vers le FDT (flattened device tree). Ce blob d'arbre de périphérique contient également la ligne de commande.

Voir le code dans drivers/of/fdt.c comment la ligne de commande est récupérée du blob DT (en recherchant un noeud appelé "bootargs" ), et retenu.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X