Zynqのqemu (その7)の続きです。
メモリおよびI/O(レジスタ)の設定が終わると、いよいよ、Linux Kernelの起動です。
xilinx.cの下記の部分です。
xilinx.cの下記の部分です。
348 xilinx_binfo.ram_size = ram_size; 349 xilinx_binfo.kernel_filename = kernel_filename; 350 xilinx_binfo.kernel_cmdline = kernel_cmdline; 351 xilinx_binfo.initrd_filename = initrd_filename; 352 xilinx_binfo.dtb_filename = qemu_kerndtb; 353 xilinx_binfo.nb_cpus = smp_cpus; 354 xilinx_binfo.board_id = 0xd32; 355 xilinx_binfo.loader_start = 0; 356 printf("ram_size %x, board_id %x, loader_start %x\n", 357 (unsigned)ram_size, (unsigned)xilinx_binfo.board_id, 358 (unsigned)xilinx_binfo.loader_start); 359 arm_load_kernel(first_cpu, &xilinx_binfo); 360xilinx_binfo変数の各メンバーに値を設定して、arm_load_kernel関数を呼びます。
arm_load_kernel関数は、arm_boot.cで次のように定義されています。
メモリに各種データ(kernel, initrc)をロードし、各CPUにブートアドレスを指定し、リセット後に起動する関数を下記のように設定します。
300 for (; env; env = env->next_cpu) {
301 env->boot_info = info;
302 qemu_register_reset(do_cpu_reset, env);
303 }
do_cpu_reset関数は、同じファイルに次のように定義されています。 182 static void do_cpu_reset(void *opaque)
183 {
184 CPUState *env = opaque;
185 const struct arm_boot_info *info = env->boot_info;
186
187 cpu_reset(env);
188 if (info) {
189 if (!info->is_linux) {
190 /* Jump to the entry point. */
191 env->regs[15] = info->entry & 0xfffffffe;
192 env->thumb = info->entry & 1;
193 } else {
194 if (env == first_cpu) {
195 env->regs[15] = info->loader_start;
196 if (old_param) {
197 set_kernel_args_old(info, info->initrd_size,
198 info->loader_start);
199 } else {
200 set_kernel_args(info, info->initrd_size,
201 info->loader_start);
202 }
203 } else {
204 stl_phys_notdirty(info->smp_bootreg_addr, 0);
205 env->regs[15] = info->smp_loader_start;
206 }
207 }
208 }
209 }
set_kernel_args関数については、次回に。
検証、Verification、FPGA