- /* Fake bootloader */
- {
-#if 1
- uint32_t offset = get_le32(phys_ram_base + kernel_addr);
-#else
- uint32_t offset = 12;
-#endif
- env->nip = kernel_addr + offset;
- printf("Start address: 0x%08x\n", env->nip);
- }
- /* Set up msr according to PREP specification */
- msr_ee = 0;
- msr_fp = 1;
- msr_pr = 0; /* Start in supervisor mode */
- msr_me = 1;
- msr_fe0 = msr_fe1 = 0;
- msr_ip = 0;
- msr_ir = msr_dr = 1;
-// msr_sf = 0;
- msr_le = msr_ile = 0;
- env->gpr[1] = stack_addr; /* Let's have a stack */
- env->gpr[2] = 0;
- env->gpr[8] = kernel_addr;
- /* There is a bug in 2.4 kernels:
- * if a decrementer exception is pending when it enables msr_ee,
- * it's not ready to handle it...
- */
- env->decr = 0xFFFFFFFF;
- p = phys_ram_base + kernel_addr;
-#if !defined (USE_OPEN_FIRMWARE)
- /* Let's register the whole memory available only in supervisor mode */
- setup_BAT(env, 0, 0x00000000, 0x00000000, mem_size, 1, 0, 2);
- /* Avoid open firmware init call (to get a console)
- * This will make the kernel think we are a PREP machine...
- */
- put_long(p, 0xdeadc0de);
- /* Build a real stack room */
- p = phys_ram_base + stack_addr;
- put_long(p, stack_addr);
- p -= 32;
- env->gpr[1] -= 32;
- /* Pretend there are no residual data */
- env->gpr[3] = 0;
- if (initrd_file != NULL) {
- int size;
- env->gpr[4] = (kernel_addr + kernel_size + 4095) & ~4095;
- size = load_initrd(initrd_file,
- phys_ram_base + env->gpr[4]);
- if (size < 0) {
- /* No initrd */
- env->gpr[4] = env->gpr[5] = 0;
- } else {
- env->gpr[5] = size;
- boot_device = 'e';
- }
- printf("Initrd loaded at 0x%08x (%d) (0x%08x 0x%08x)\n",
- env->gpr[4], env->gpr[5], kernel_addr, kernel_size);
- } else {
- env->gpr[4] = env->gpr[5] = 0;
- }
- /* We have to put bootinfos after the BSS
- * The BSS starts after the kernel end.
- */
-#if 0
- p = phys_ram_base + kernel_addr +
- kernel_size + (1 << 20) - 1) & ~((1 << 20) - 1);
-#else
- p = phys_ram_base + kernel_addr + 0x400000;
-#endif
- if (loglevel > 0) {
- fprintf(logfile, "bootinfos: %p 0x%08x\n",
- p, (int)(p - phys_ram_base));
- } else {
- printf("bootinfos: %p 0x%08x\n",
- p, (int)(p - phys_ram_base));
- }
- /* Command line: let's put it after bootinfos */
-#if 0
- sprintf(p + 0x1000, "console=ttyS0,9600 root=%02x%02x mem=%dM",
- boot_devs[boot_device - 'a'].major,
- boot_devs[boot_device - 'a'].minor,
- mem_size >> 20);
-#else
- sprintf(p + 0x1000, "console=ttyS0,9600 console=tty0 root=%s mem=%dM",
- boot_devs[boot_device - 'a'].name,
- mem_size >> 20);
-#endif
- env->gpr[6] = p + 0x1000 - phys_ram_base;
- env->gpr[7] = env->gpr[6] + strlen(p + 0x1000);
- if (loglevel > 0) {
- fprintf(logfile, "cmdline: %p 0x%08x [%s]\n",
- p + 0x1000, env->gpr[6], p + 0x1000);
- } else {
- printf("cmdline: %p 0x%08x [%s]\n",
- p + 0x1000, env->gpr[6], p + 0x1000);
- }
- /* BI_FIRST */
- p = set_bootinfo_tag(p, 0x1010, 0, 0);
- /* BI_CMD_LINE */
- p = set_bootinfo_tag(p, 0x1012, env->gpr[7] - env->gpr[6],
- env->gpr[6] + phys_ram_base);
- /* BI_MEM_SIZE */
- tmp = (void *)tmpi;
- tmp[0] = (mem_size >> 24) & 0xFF;
- tmp[1] = (mem_size >> 16) & 0xFF;
- tmp[2] = (mem_size >> 8) & 0xFF;
- tmp[3] = mem_size & 0xFF;
- p = set_bootinfo_tag(p, 0x1017, 4, tmpi);
- /* BI_INITRD */
- tmp[0] = (env->gpr[4] >> 24) & 0xFF;
- tmp[1] = (env->gpr[4] >> 16) & 0xFF;
- tmp[2] = (env->gpr[4] >> 8) & 0xFF;
- tmp[3] = env->gpr[4] & 0xFF;
- tmp[4] = (env->gpr[5] >> 24) & 0xFF;
- tmp[5] = (env->gpr[5] >> 16) & 0xFF;
- tmp[6] = (env->gpr[5] >> 8) & 0xFF;
- tmp[7] = env->gpr[5] & 0xFF;
- p = set_bootinfo_tag(p, 0x1014, 8, tmpi);
- env->gpr[4] = env->gpr[5] = 0;
- /* BI_LAST */
- p = set_bootinfo_tag(p, 0x1011, 0, 0);
-#else
- /* Set up MMU:
- * kernel is loaded at kernel_addr and wants to be seen at 0x01000000
- */
- setup_BAT(env, 0, 0x01000000, kernel_addr, 0x00400000, 1, 0, 2);
- {
-#if 0
- uint32_t offset = get_le32(phys_ram_base + kernel_addr);
-#else
- uint32_t offset = 12;
-#endif
- env->nip = 0x01000000 | (kernel_addr + offset);
- printf("Start address: 0x%08x\n", env->nip);
- }
- env->gpr[1] = env->nip + (1 << 22);
- p = phys_ram_base + stack_addr;
- put_long(p - 32, stack_addr);
- env->gpr[1] -= 32;
- printf("Kernel starts at 0x%08x stack 0x%08x\n", env->nip, env->gpr[1]);
- /* We want all lower address not to be translated */
- setup_BAT(env, 1, 0x00000000, 0x00000000, 0x010000000, 1, 1, 2);
- /* We also need a BAT to access OF */
- setup_BAT(env, 2, 0xFFFE0000, mem_size - 131072, 131072, 1, 0, 1);
- /* Setup OF entry point */
- {
- char *p;
- p = (char *)phys_ram_base + mem_size - 131072;
- /* Special opcode to call OF */
- *p++ = 0x18; *p++ = 0x00; *p++ = 0x00; *p++ = 0x02;
- /* blr */
- *p++ = 0x4E; *p++ = 0x80; *p++ = 0x00; *p++ = 0x20;
- }
- env->gpr[5] = 0xFFFE0000;
- /* Register translations */
- {
- OF_transl_t translations[3] = {
- { 0x01000000, 0x00400000, kernel_addr, 0x00000002, },
- { 0x00000000, 0x01000000, 0x00000000, 0x00000002, },
- { 0xFFFE0000, 0x00020000, mem_size - (128 * 1024),
- 0x00000001, },
- };
- OF_register_translations(3, translations);
- }
- /* Quite artificial, for now */
- OF_register_bus("isa", "isa");
- OF_register_serial("isa", "serial", 4, 0x3f8);
- OF_register_stdio("serial", "serial");
- /* Set up RTAS service */
- RTAS_init();
- /* Command line: let's put it just over the stack */
-#if 0
-#if 0
- p = phys_ram_base + kernel_addr +
- kernel_size + (1 << 20) - 1) & ~((1 << 20) - 1);
-#else
- p = phys_ram_base + kernel_addr + 0x400000;
-#endif
-#if 1
- sprintf(p, "console=ttyS0,9600 root=%02x%02x mem=%dM",
- boot_devs[boot_device - 'a'].major,
- boot_devs[boot_device - 'a'].minor,
- mem_size >> 20);
-#else
- sprintf(p, "console=ttyS0,9600 root=%s mem=%dM ne2000=0x300,9",
- boot_devs[boot_device - 'a'].name,
- mem_size >> 20);
-#endif
- OF_register_bootargs(p);
-#endif
-#endif