static os_emul_data * emul_netbsd_create(device *root, bfd *image, const char *name) { unsigned_word top_of_stack; unsigned stack_size; int elf_binary; os_emul_data *bsd_data; device *vm; char *filename; /* check that this emulation is really for us */ if (name != NULL && strcmp(name, "netbsd") != 0) return NULL; if (image == NULL) return NULL; /* merge any emulation specific entries into the device tree */ /* establish a few defaults */ if (image->xvec->flavour == bfd_target_elf_flavour) { elf_binary = 1; top_of_stack = 0xe0000000; stack_size = 0x00100000; } else { elf_binary = 0; top_of_stack = 0x20000000; stack_size = 0x00100000; } /* options */ emul_add_tree_options(root, image, "netbsd", (WITH_ENVIRONMENT == USER_ENVIRONMENT ? "user" : "virtual"), 0 /*oea-interrupt-prefix*/); /* virtual memory - handles growth of stack/heap */ vm = tree_parse(root, "/openprom/vm"); tree_parse(vm, "./stack-base 0x%lx", (unsigned long)(top_of_stack - stack_size)); tree_parse(vm, "./nr-bytes 0x%x", stack_size); filename = tree_quote_property (bfd_get_filename(image)); tree_parse(root, "/openprom/vm/map-binary/file-name %s", filename); free (filename); /* finish the init */ tree_parse(root, "/openprom/init/register/pc 0x%lx", (unsigned long)bfd_get_start_address(image)); tree_parse(root, "/openprom/init/register/sp 0x%lx", (unsigned long)top_of_stack); tree_parse(root, "/openprom/init/register/msr 0x%x", ((tree_find_boolean_property(root, "/options/little-endian?") ? msr_little_endian_mode : 0) | (tree_find_boolean_property(root, "/openprom/options/floating-point?") ? (msr_floating_point_available | msr_floating_point_exception_mode_0 | msr_floating_point_exception_mode_1) : 0))); tree_parse(root, "/openprom/init/stack/stack-type %s", (elf_binary ? "ppc-elf" : "ppc-xcoff")); /* finally our emulation data */ bsd_data = ZALLOC(os_emul_data); bsd_data->vm = vm; bsd_data->syscalls = &emul_netbsd_syscalls; return bsd_data; }
static os_emul_data * emul_bugapi_create(device *root, bfd *image, const char *name) { device *node; os_emul_data *bugapi; char *filename; /* check it really is for us */ if (name != NULL && strcmp(name, "bugapi") != 0 && strcmp(name, "bug") != 0) return NULL; if (image != NULL && name == NULL && bfd_get_start_address(image) >= BUGAPI_END_ADDRESS) return NULL; bugapi = ZALLOC(os_emul_data); /* options */ emul_add_tree_options(root, image, "bug", "oea", 1 /*oea-interrupt-prefix*/); /* add some real hardware, include eeprom memory for the eeprom trap addresses */ emul_add_tree_hardware(root); node = tree_parse(root, "/openprom/memory@0xfff00000"); tree_parse(node, "./psim,description \"eeprom trap addresses"); tree_parse(node, "./reg 0xfff00000 0x3000"); bugapi->root = root; bugapi->memory_size = tree_find_integer_property(root, "/openprom/options/oea-memory-size"); bugapi->interrupt_prefix = tree_find_integer_property(root, "/openprom/options/oea-interrupt-prefix"); bugapi->interrupt_vector_address = (bugapi->interrupt_prefix ? MASK(0, 43) : 0); bugapi->system_call_address = (bugapi->interrupt_vector_address + 0x00c00); bugapi->stall_cpu_loop_address = (bugapi->system_call_address + 0x000f0); bugapi->top_of_stack = bugapi->memory_size - 0x1000; bugapi->little_endian = tree_find_boolean_property(root, "/options/little-endian?"); bugapi->floating_point_available = tree_find_boolean_property(root, "/openprom/options/floating-point?"); bugapi->input = NULL; bugapi->output = NULL; /* initialization */ if (image != NULL) tree_parse(root, "/openprom/init/register/0.pc 0x%lx", (unsigned long)bfd_get_start_address(image)); tree_parse(root, "/openprom/init/register/pc 0x%lx", (unsigned long)bugapi->stall_cpu_loop_address); tree_parse(root, "/openprom/init/register/sp 0x%lx", (unsigned long)(bugapi->top_of_stack - 16)); tree_parse(root, "/openprom/init/register/msr 0x%x", (msr_recoverable_interrupt | (bugapi->little_endian ? (msr_little_endian_mode | msr_interrupt_little_endian_mode) : 0) | (bugapi->floating_point_available ? msr_floating_point_available : 0) | (bugapi->interrupt_prefix ? msr_interrupt_prefix : 0) )); /* patch the system call instruction to call this emulation and then do an rfi */ node = tree_parse(root, "/openprom/init/data@0x%lx", (unsigned long)bugapi->system_call_address); tree_parse(node, "./psim,description \"system-call trap instruction"); tree_parse(node, "./real-address 0x%lx", (unsigned long)bugapi->system_call_address); tree_parse(node, "./data 0x%x", emul_call_instruction); node = tree_parse(root, "/openprom/init/data@0x%lx", (unsigned long)bugapi->system_call_address + 4); tree_parse(node, "./psim,description \"return from interrupt instruction"); tree_parse(node, "./real-address 0x%lx", (unsigned long)bugapi->system_call_address + 4); tree_parse(node, "./data 0x%x", emul_rfi_instruction); /* patch the end of the system call instruction so that it contains a loop to self instruction and point all the cpu's at this */ node = tree_parse(root, "/openprom/init/data@0x%lx", (unsigned long)bugapi->stall_cpu_loop_address); tree_parse(node, "./psim,description \"cpu-loop instruction"); tree_parse(node, "./real-address 0x%lx", (unsigned long)bugapi->stall_cpu_loop_address); tree_parse(node, "./data 0x%lx", (unsigned long)emul_loop_instruction); if (image != NULL) tree_parse(root, "/openprom/init/stack/stack-type %s", (image->xvec->flavour == bfd_target_elf_flavour ? "ppc-elf" : "ppc-xcoff")); if (image != NULL) { filename = tree_quote_property (bfd_get_filename(image)); tree_parse(root, "/openprom/init/load-binary/file-name %s", filename); free (filename); } return bugapi; }