在线看毛片网站电影-亚洲国产欧美日韩精品一区二区三区,国产欧美乱夫不卡无乱码,国产精品欧美久久久天天影视,精品一区二区三区视频在线观看,亚洲国产精品人成乱码天天看,日韩久久久一区,91精品国产91免费

<menu id="6qfwx"><li id="6qfwx"></li></menu>
    1. <menu id="6qfwx"><dl id="6qfwx"></dl></menu>

      <label id="6qfwx"><ol id="6qfwx"></ol></label><menu id="6qfwx"></menu><object id="6qfwx"><strike id="6qfwx"><noscript id="6qfwx"></noscript></strike></object>
        1. <center id="6qfwx"><dl id="6qfwx"></dl></center>

            新聞中心

            EEPW首頁 > 嵌入式系統(tǒng) > 設計應用 > 淺談分析Arm linux 內(nèi)核移植及系統(tǒng)初始化的過程四

            淺談分析Arm linux 內(nèi)核移植及系統(tǒng)初始化的過程四

            作者: 時間:2016-11-09 來源:網(wǎng)絡 收藏
            7、淺談分析Arm linux 內(nèi)核移植系統(tǒng)初始化的過程 咨詢QQ:313807838

            MACHINE_START(SMDK2410, "SMDK2410") /* @TODO: request a new identifier and switch
            * to SMDK2410 */
            /* Maintainer: Jonas Dietsche */
            .phys_io = S3C2410_PA_UART,
            .io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
            .boot_params = S3C2410_SDRAM_PA + 0x100,
            .map_io = smdk2410_map_io,
            .init_irq = s3c24xx_init_irq,
            .init_machine = smdk_machine_init,
            .timer = &s3c24xx_timer,
            MACHINE_END

            本文引用地址:http://www.biyoush.com/article/201611/318026.htm

            由此可見在.arch.info.init段內(nèi)存放了__desc_mach_desc_SMDK2410結構體。初始化了相應的初始化函數(shù)指針。問題又來了, 這些初始化指針函數(shù)是什么時候被調(diào)用的呢?
            分析發(fā)現(xiàn),不一而同。
            如 s3c24xx_init_irq()函數(shù)是通過start_kernel()里的init_IRQ()函數(shù)調(diào)用init_arch_irq()實現(xiàn)的。 因為在MACHINE_START結構體中 .init_irq = s3c24xx_init_irq,而在setup_arch()函數(shù)中init_arch_irq = mdesc->init_irq, 所以調(diào)用init_arch_irq()就相當于調(diào)用了s3c24xx_init_irq()。
            又如smdk_machine_init()函數(shù) 的初始化。在MACHINE_START結構體中,函數(shù)指針賦值,.init_machine = smdk_machine_init。而init_machine()函數(shù)被linux/arch/arm/kernel/setup.c文件中的 customize_machine()函數(shù)調(diào)用并被arch_initcall(Fn)宏處 理,arch_initcall(customize_machine)。 被arch_initcall(Fn)宏處理過函數(shù)將linux/init/main.c
            do_initcalls()函數(shù)調(diào)用。 具體參看下邊的部分。

            void __init setup_arch(char cmdline_p)
            {
            struct tag *tags = (struct tag *)&init_tags;
            struct machine_desc *mdesc;
            char *from = default_command_line;

            setup_processor();
            mdesc = setup_machine(machine_arch_type);//machine_arch_type =SMDK2410 by edwin
            machine_name = mdesc->name;

            if (mdesc->soft_reboot)
            reboot_setup("s");

            if (mdesc->boot_params)
            tags = phys_to_virt(mdesc->boot_params);

            /*
            * If we have the old style parameters, convert them to
            * a tag list.
            */
            if (tags->hdr.tag != ATAG_CORE)
            convert_to_tag_list(tags);
            if (tags->hdr.tag != ATAG_CORE)
            tags = (struct tag *)&init_tags;

            if (mdesc->fixup)
            mdesc->fixup(mdesc, tags, &from, &meminfo);

            if (tags->hdr.tag == ATAG_CORE) {
            if (meminfo.nr_banks != 0)
            squash_mem_tags(tags);
            parse_tags(tags);
            }

            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;

            memcpy(saved_command_line, from, COMMAND_LINE_SIZE);

            8、淺談分析Arm linux 內(nèi)核移植及系統(tǒng)初始化的過程 咨詢QQ:313807838
            saved_command_line[COMMAND_LINE_SIZE-1] = /0;
            parse_cmdline(cmdline_p, from);
            paging_init(&meminfo, mdesc);
            request_standard_resources(&meminfo, mdesc);

            #ifdef CONFIG_SMP
            smp_init_cpus();
            #endif

            cpu_init();

            /*
            * Set up various architecture-specific pointers
            */
            init_arch_irq = mdesc->init_irq;
            system_timer = mdesc->timer;
            init_machine = mdesc->init_machine;

            #ifdef CONFIG_VT
            #if defined(CONFIG_VGA_CONSOLE)
            conswitchp = &vga_con;
            #elif defined(CONFIG_DUMMY_CONSOLE)
            conswitchp = &dummy_con;
            #endif
            #endif
            }
            5.3. rest_init()函數(shù)分析
            下面我們來分析下rest_init()函數(shù)。
            Start_kernel() 函數(shù)負責初始化內(nèi)核各子系統(tǒng),最后調(diào)用reset_init(),啟動一個叫做init的內(nèi)核線程,繼續(xù)初始化。在init內(nèi)核線程中,將執(zhí)行下列 init()函數(shù)的程序。Init()函數(shù)負責完成根文件系統(tǒng)的掛接、初始化設備驅(qū)動程序和啟動用戶空間的init進程等重要工作。

            static void noinline rest_init(void)
            __releases(kernel_lock)
            {
            kernel_thread(init, NULL, CLONE_FS | CLONE_SIGHAND);
            numa_default_policy();
            unlock_kernel();

            /*
            * The boot idle thread must execute schedule()
            * at least one to get things moving:
            */
            preempt_enable_no_resched();
            schedule();
            preempt_disable();

            /* Call into cpu_idle with preempt disabled */
            cpu_idle();
            }


            static int init(void * unused)
            {
            lock_kernel();
            /*
            * init can run on any cpu.
            */
            set_cpus_allowed(current, CPU_MASK_ALL);
            /*
            * Tell the world that were going to be the grim
            * reaper of innocent orphaned children.
            *
            * We dont want people to have to make incorrect
            * assumptions about where in the task array this
            * can be found.
            */
            child_reaper = current;

            smp_prepare_cpus(max_cpus);

            do_pre_smp_initcalls();

            smp_init();
            sched_init_smp();

            cpuset_init_smp();

            /*
            * Do this before initcalls, because some drivers want to access
            * firmware files.
            */
            populate_rootfs(); //掛接根文件系統(tǒng)

            do_basic_setup(); //初始化設備驅(qū)動程序

            /*
            * check if there is an early userspace init. If yes, let it do all
            * the work //啟動用戶空間的init進程

            9、淺談分析Arm linux 內(nèi)核移植及系統(tǒng)初始化的過程 咨詢QQ:313807838
            */

            if (!ramdisk_execute_command)
            ramdisk_execute_command = "/init";

            if (sys_access((const char __user *) ramdisk_execute_command, 0) != 0) {
            ramdisk_execute_command = NULL;
            prepare_namespace();
            }

            /*
            * Ok, we have completed the initial bootup, and
            * were essentially up and running. Get rid of the
            * initmem segments and start the user-mode stuff..
            */
            free_initmem();
            unlock_kernel();
            mark_rodata_ro();
            system_state = SYSTEM_RUNNING;
            numa_default_policy();

            if (sys_open((const char __user *) "/dev/console", O_RDWR, 0) < 0)
            printk(KERN_WARNING "Warning: unable to open an initial console./n");

            (void) sys_dup(0);
            (void) sys_dup(0);

            if (ramdisk_execute_command) {
            run_init_process(ramdisk_execute_command);
            printk(KERN_WARNING "Failed to execute %s/n",
            ramdisk_execute_command);
            }

            /*
            * We try each of these until one succeeds.
            *
            * The Bourne shell can be used instead of init if we are
            * trying to recover a really broken machine.
            */
            if (execute_command) {
            run_init_process(execute_command);
            printk(KERN_WARNING "Failed to execute %s. Attempting "
            "defaults.../n", execute_command);
            }
            run_init_process("/sbin/init");
            run_init_process("/etc/init");
            run_init_process("/bin/init");
            run_init_process("/bin/sh");

            panic("No init found. Try passing init= option to kernel.");
            }

            5.3.1. 掛接根文件系統(tǒng)
            Linux/init/ramfs.c
            void __init populate_rootfs(void)
            {
            char *err = unpack_to_rootfs(__initramfs_start,
            __initramfs_end - __initramfs_start, 0);
            if (err)
            panic(err);
            #ifdef CONFIG_BLK_DEV_INITRD
            if (initrd_start) {
            #ifdef CONFIG_BLK_DEV_RAM
            int fd;
            printk(KERN_INFO "checking if image is initramfs...");
            err = unpack_to_rootfs((char *)initrd_start,
            initrd_end - initrd_start, 1);
            if (!err) {
            printk(" it is/n");
            unpack_to_rootfs((char *)initrd_start,
            initrd_end - initrd_start, 0);
            free_initrd();
            return;
            }
            printk("it isnt (%s); looks like an initrd/n", err);



            評論


            技術專區(qū)

            關閉