ACPI_STATUS acpi_tb_validate_table_header ( ACPI_TABLE_HEADER *table_header) { ACPI_NAME signature; /* Verify that this is a valid address */ if (!acpi_os_readable (table_header, sizeof (ACPI_TABLE_HEADER))) { return (AE_BAD_ADDRESS); } /* Ensure that the signature is 4 ASCII characters */ MOVE_UNALIGNED32_TO_32 (&signature, &table_header->signature); if (!acpi_cm_valid_acpi_name (signature)) { REPORT_WARNING (("Invalid table signature found\n")); return (AE_BAD_SIGNATURE); } /* Validate the table length */ if (table_header->length < sizeof (ACPI_TABLE_HEADER)) { REPORT_WARNING (("Invalid table header length found\n")); return (AE_BAD_HEADER); } return (AE_OK); }
bool CMD_config( u32 n_args, char **args ) { char buf[RC_CONSOLE_MAX_LINE_WIDTH]; FILE *f; if (!Command::checkArgCount(1, n_args, args)) return false; Console::log("Loading config file \"%s\"", args[0]); f = fopen(args[0], "r"); if (!f) { REPORT_WARNING("Couldn't read config file"); return false; } while (fgets(buf, RC_CONSOLE_MAX_LINE_WIDTH, f)) { if (strlen(buf) > 0) Command::run(buf); } fclose(f); return true; }
void VertexArray::setArray( void *new_array, u32 n /* Number of structs */ ) { if (n == 0) REPORT_WARNING("Number of structs set to 0"); n_elements = n; if (holds_array) { Renderer::reloadVertexArray(this, new_array, n); } else { Renderer::loadVertexArray(this, new_array, n, usage); holds_array = true; } has_bounds = false; if (varray) free(varray); varray = malloc(n * stride); memcpy(varray, new_array, n * stride); }
void NodeList::add( Node *node ) { // if (next_free >= max_free) { // max_free = max_free + (max_free >> 2); /* Grow by 25% */ // free_list = (NodeElement *) realloc(free_list, sizeof(NodeElement) * max_free); // } NodeElement *ne; if (!node) { REPORT_WARNING("No node given"); return; } ne = new NodeElement; ne->node = node; ne->next = head; head = ne; n_nodes++; n_nodes_of_type[(u32) node->getNodeType()]++; }
bool CMD_help( u32 n_args, char **args ) { if (n_args > 0) { Command_t *cmd = Command::command_head; while (cmd) { if (strcmp(cmd->name, args[0]) == 0) { Console::log(" Help for \"%s\":", cmd->name); Console::log(cmd->desc); return true; } cmd = cmd->list_next; } REPORT_WARNING("Command not found"); } else { Console::log("Type \"/help <Command>\" for more info on a particular command"); Console::log("Type \"/list_commands\" to list all available commands"); Console::log("Use F1 to toggle console"); } return true; }
void NodeList::remove( Node *node ) { NodeElement *iter, *p = 0; if (!head) return; if (!node) { REPORT_WARNING("No node given"); return; } iter = head; for (;;) { if (iter->node == node) { if (p) { p->next = iter->next; } else { head = (NodeElement *) iter->next; } n_nodes_of_type[(u32) iter->node->getNodeType()]--; delete iter; n_nodes--; return; } if (!iter->next) { REPORT_WARNING("Node %s not found", node->getName()); return; } p = iter; iter = (NodeElement *) iter->next; } }
acpi_object_type8 acpi_ns_get_type ( acpi_namespace_node *node) { FUNCTION_TRACE ("Ns_get_type"); if (!node) { REPORT_WARNING (("Ns_get_type: Null Node ptr")); return_VALUE (ACPI_TYPE_ANY); } return_VALUE (node->type); }
bool Command::bindKey( char *keyn, char *line ) { u32 i, j; if (!line || *line == 0) { REPORT_WARNING("No string given"); return false; } for (i = 0; i < RC_KEY_LAST; i++) { if (key_name[i] && strcmp(keyn, key_name[i]) == 0) { break; } } if (i == RC_KEY_LAST) { REPORT_WARNING("Couldn't bind key - key name \"%s\"not found", keyn); return false; } for (j = 0; j < n_bindings; j++) { if (binding[j].key == i) { free(binding[j].line); binding[j].line = duplicateString(line); return true; } } binding[n_bindings].line = duplicateString(line); binding[n_bindings].key = i; n_bindings++; return true; }
static Transformable *fetchTransformable( char *nname ) { Node *node; node = SceneGraph::getNode(nname); if (!node || !node->isTransformable()) { REPORT_WARNING("Transformable \"%s\" not found", nname); return 0; } return (Transformable *) node; }
ACPI_STATUS acpi_aml_exec_fatal ( ACPI_WALK_STATE *walk_state) { ACPI_OPERAND_OBJECT *type_desc; ACPI_OPERAND_OBJECT *code_desc; ACPI_OPERAND_OBJECT *arg_desc; ACPI_STATUS status; /* Resolve operands */ status = acpi_aml_resolve_operands (AML_FATAL_OP, WALK_OPERANDS, walk_state); /* Get operands */ status |= acpi_ds_obj_stack_pop_object (&arg_desc, walk_state); status |= acpi_ds_obj_stack_pop_object (&code_desc, walk_state); status |= acpi_ds_obj_stack_pop_object (&type_desc, walk_state); if (ACPI_FAILURE (status)) { /* Invalid parameters on object stack */ goto cleanup; } /* Def_fatal := Fatal_op Fatal_type Fatal_code Fatal_arg */ /* * TBD: [Unhandled] call OSD interface to notify OS of fatal error * requiring shutdown! */ cleanup: /* Free the operands */ acpi_cm_remove_reference (arg_desc); acpi_cm_remove_reference (code_desc); acpi_cm_remove_reference (type_desc); /* If we get back from the OS call, we might as well keep going. */ REPORT_WARNING (("An AML \"fatal\" Opcode (Fatal_op) was executed\n")); return (AE_OK); }
u32 acpi_ns_opens_scope ( acpi_object_type8 type) { FUNCTION_TRACE_U32 ("Ns_opens_scope", type); if (!acpi_ut_valid_object_type (type)) { /* type code out of range */ REPORT_WARNING (("Ns_opens_scope: Invalid Object Type\n")); return_VALUE (NSP_NORMAL); } return_VALUE (((u32) acpi_gbl_ns_properties[type]) & NSP_NEWSCOPE); }
u32 acpi_ns_local ( acpi_object_type8 type) { FUNCTION_TRACE ("Ns_local"); if (!acpi_ut_valid_object_type (type)) { /* Type code out of range */ REPORT_WARNING (("Ns_local: Invalid Object Type\n")); return_VALUE (NSP_NORMAL); } return_VALUE ((u32) acpi_gbl_ns_properties[type] & NSP_LOCAL); }
Attribute_t *VertexArray::getAttribute( char *name ) { u32 i; for (i = 0; i < n_attribs; i++) { if (strcmp(attrib[i].name, name) == 0) return &attrib[i]; } REPORT_WARNING("No attribute by the name \"%s\" found", name); return 0; }
acpi_status acpi_ds_scope_stack_push ( acpi_namespace_node *node, acpi_object_type8 type, acpi_walk_state *walk_state) { acpi_generic_state *scope_info; FUNCTION_TRACE ("Ds_scope_stack_push"); if (!node) { /* Invalid scope */ REPORT_ERROR (("Ds_scope_stack_push: null scope passed\n")); return_ACPI_STATUS (AE_BAD_PARAMETER); } /* Make sure object type is valid */ if (!acpi_ex_validate_object_type (type)) { REPORT_WARNING (("Ds_scope_stack_push: type code out of range\n")); } /* Allocate a new scope object */ scope_info = acpi_ut_create_generic_state (); if (!scope_info) { return_ACPI_STATUS (AE_NO_MEMORY); } /* Init new scope object */ scope_info->common.data_type = ACPI_DESC_TYPE_STATE_WSCOPE; scope_info->scope.node = node; scope_info->common.value = (u16) type; /* Push new scope object onto stack */ acpi_ut_push_generic_state (&walk_state->scope_info, scope_info); return_ACPI_STATUS (AE_OK); }
Resource::Resource( const char *nidentifier, u32 purge_level, ResourceType rtype ) { if (!nidentifier || *nidentifier == 0) REPORT_WARNING("No resource identifier given"); broken = false; next = 0; identifier = duplicateString(nidentifier); hash = calculateStringHash(identifier); purgeLevel = purge_level; type = rtype; }
bool Command::checkArgCount( u32 expected, u32 got, char **args ) { u32 i; if (expected != got) { REPORT_WARNING("Wrong number of arguments given - got %d but expected %d.", got, expected); for (i = 0; i < got; i++) Console::log("Arg %d: \"%s\"", i, args[i]); return false; } return true; }
bool ResourceList::dereference( Resource *obj ) { if (obj->n_refs > 0) obj->n_refs--; if (obj->n_refs == 0 && obj->purgeLevel == 0) { u32 h = obj->hash % length; Resource *ref = list[h]; Resource *prev = 0; while (ref) { if (ref->isEqual(obj)) { if (prev) { prev->next = ref->next; } else { list[h] = ref->next; } n_entries--; delete obj; return true; } prev = ref; ref = ref->next; } REPORT_WARNING("The resource %s was not found in the resource list", obj->getIdentifier()); } return false; }
bool CMD_load_scene( u32 n_args, char **args ) { bool parse_success; i32 arg2; if (n_args != 2) { REPORT_WARNING(RC_WRN_CMD_ARG, 2); return false; } parse_success = parseInt(&arg2, args[2]); if (!parse_success) return false; SceneGraph::createGroup(args[0], args[1], (u32) arg2); return true; }
void Platform::setDisplay( bool fullscreen, u32 width, u32 height ) { u32 full = fullscreen ? SDL_FULLSCREEN : 0; #if defined RC_OPENGL screen = SDL_SetVideoMode(width, height, 0, SDL_OPENGL | full); #elif defined RC_OPENGL_ES_20 screen = SDL_SetVideoMode(width, height, 32, SDL_HWSURFACE | SDL_DOUBLEBUF | full); #endif if (!screen) { REPORT_WARNING("Couldn't initiate screen resolution (%d, %d) with fullscreen %s", width, height, fullscreen ? "on" : "off"); /* Could not initialize the specified resolution. Revert to old settings */ #if defined RC_OPENGL screen = SDL_SetVideoMode(displayWidth, displayHeight, 0, SDL_OPENGL); #elif defined RC_OPENGL_ES_20 screen = SDL_SetVideoMode(displayWidth, displayHeight, 32, SDL_HWSURFACE | SDL_DOUBLEBUF); #endif if (!screen) { REPORT_ERROR("Couldn't revert to old screen resolution (%d, %d)", displayWidth, displayHeight); } } else { displayWidth = width; displayHeight = height; } }
RenderTarget::RenderTarget( const char *nidentifier, u32 nwidth, u32 nheight, u32 n_targets, TextureFilter_t filter, TextureWrap_t wrap, bool include_depth_buffer, bool include_stencil_buffer ) : Resource(nidentifier, NO_PURGE, RESOURCE_RENDER_TARGET) { u32 i; width = nwidth; height = nheight; format = TEXTURE_FORMAT_RGBA8; if (n_targets > RC_MAX_RENDER_TARGET_TEXTURES) { REPORT_WARNING("Too many render targets (%d). Only %d allowed", n_targets, RC_MAX_RENDER_TARGET_TEXTURES); broken = true; return; } for (i = 0; i < n_targets; i++) { textures[i] = SceneGraph::createTexture(0, 0, format, nwidth, nheight, false, filter, TEXTURE_WRAP_CLAMP); textures[i]->setPurgeLevel(0); } n_textures = n_targets; Renderer::loadRenderTarget(this, n_targets, include_depth_buffer, include_stencil_buffer); }
ACPI_STATUS acpi_tb_verify_table_checksum ( ACPI_TABLE_HEADER *table_header) { u8 checksum; ACPI_STATUS status = AE_OK; /* Compute the checksum on the table */ checksum = acpi_tb_checksum (table_header, table_header->length); /* Return the appropriate exception */ if (checksum) { REPORT_WARNING (("Invalid checksum (%X) in table %4.4s\n", checksum, &table_header->signature)); status = AE_BAD_CHECKSUM; } return (status); }
acpi_status acpi_ev_gpe_initialize (void) { u32 i; u32 j; u32 register_index; u32 gpe_number; u16 gpe0register_count; u16 gpe1_register_count; FUNCTION_TRACE ("Ev_gpe_initialize"); /* * Set up various GPE counts * * You may ask,why are the GPE register block lengths divided by 2? * From the ACPI 2.0 Spec, section, 4.7.1.6 General-Purpose Event * Registers, we have, * * "Each register block contains two registers of equal length * GPEx_STS and GPEx_EN (where x is 0 or 1). The length of the * GPE0_STS and GPE0_EN registers is equal to half the GPE0_LEN * The length of the GPE1_STS and GPE1_EN registers is equal to * half the GPE1_LEN. If a generic register block is not supported * then its respective block pointer and block length values in the * FADT table contain zeros. The GPE0_LEN and GPE1_LEN do not need * to be the same size." */ gpe0register_count = (u16) DIV_2 (acpi_gbl_FADT->gpe0blk_len); gpe1_register_count = (u16) DIV_2 (acpi_gbl_FADT->gpe1_blk_len); acpi_gbl_gpe_register_count = gpe0register_count + gpe1_register_count; if (!acpi_gbl_gpe_register_count) { REPORT_WARNING (("Zero GPEs are defined in the FADT\n")); return_ACPI_STATUS (AE_OK); } /* * Allocate the Gpe information block */ acpi_gbl_gpe_registers = ACPI_MEM_CALLOCATE (acpi_gbl_gpe_register_count * sizeof (acpi_gpe_registers)); if (!acpi_gbl_gpe_registers) { ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Could not allocate the Gpe_registers block\n")); return_ACPI_STATUS (AE_NO_MEMORY); } /* * Allocate the Gpe dispatch handler block * There are eight distinct GP events per register. * Initialization to zeros is sufficient */ acpi_gbl_gpe_info = ACPI_MEM_CALLOCATE (MUL_8 (acpi_gbl_gpe_register_count) * sizeof (acpi_gpe_level_info)); if (!acpi_gbl_gpe_info) { ACPI_MEM_FREE (acpi_gbl_gpe_registers); ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Could not allocate the Gpe_info block\n")); return_ACPI_STATUS (AE_NO_MEMORY); } /* Set the Gpe validation table to GPE_INVALID */ MEMSET (acpi_gbl_gpe_valid, (int) ACPI_GPE_INVALID, ACPI_NUM_GPE); /* * Initialize the Gpe information and validation blocks. A goal of these * blocks is to hide the fact that there are two separate GPE register sets * In a given block, the status registers occupy the first half, and * the enable registers occupy the second half. */ /* GPE Block 0 */ register_index = 0; for (i = 0; i < gpe0register_count; i++) { acpi_gbl_gpe_registers[register_index].status_addr = (u16) (ACPI_GET_ADDRESS (acpi_gbl_FADT->Xgpe0blk.address) + i); acpi_gbl_gpe_registers[register_index].enable_addr = (u16) (ACPI_GET_ADDRESS (acpi_gbl_FADT->Xgpe0blk.address) + i + gpe0register_count); acpi_gbl_gpe_registers[register_index].gpe_base = (u8) MUL_8 (i); for (j = 0; j < 8; j++) { gpe_number = acpi_gbl_gpe_registers[register_index].gpe_base + j; acpi_gbl_gpe_valid[gpe_number] = (u8) register_index; } /* * Clear the status/enable registers. Note that status registers * are cleared by writing a '1', while enable registers are cleared * by writing a '0'. */ acpi_os_write_port (acpi_gbl_gpe_registers[register_index].enable_addr, 0x00, 8); acpi_os_write_port (acpi_gbl_gpe_registers[register_index].status_addr, 0xFF, 8); register_index++; } /* GPE Block 1 */ for (i = 0; i < gpe1_register_count; i++) { acpi_gbl_gpe_registers[register_index].status_addr = (u16) (ACPI_GET_ADDRESS (acpi_gbl_FADT->Xgpe1_blk.address) + i); acpi_gbl_gpe_registers[register_index].enable_addr = (u16) (ACPI_GET_ADDRESS (acpi_gbl_FADT->Xgpe1_blk.address) + i + gpe1_register_count); acpi_gbl_gpe_registers[register_index].gpe_base = (u8) (acpi_gbl_FADT->gpe1_base + MUL_8 (i)); for (j = 0; j < 8; j++) { gpe_number = acpi_gbl_gpe_registers[register_index].gpe_base + j; acpi_gbl_gpe_valid[gpe_number] = (u8) register_index; } /* * Clear the status/enable registers. Note that status registers * are cleared by writing a '1', while enable registers are cleared * by writing a '0'. */ acpi_os_write_port (acpi_gbl_gpe_registers[register_index].enable_addr, 0x00, 8); acpi_os_write_port (acpi_gbl_gpe_registers[register_index].status_addr, 0xFF, 8); register_index++; } ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "GPE registers: %X@%8.8X%8.8X (Blk0) %X@%8.8X%8.8X (Blk1)\n", gpe0register_count, HIDWORD(acpi_gbl_FADT->Xgpe0blk.address), LODWORD(acpi_gbl_FADT->Xgpe0blk.address), gpe1_register_count, HIDWORD(acpi_gbl_FADT->Xgpe1_blk.address), LODWORD(acpi_gbl_FADT->Xgpe1_blk.address))); return_ACPI_STATUS (AE_OK); }
void Platform::getTexture( const char *filename, bool flip_y, u8 **pixels, u32 *width, u32 *height, u32 *bytes_per_pixel ) { u32 s; SDL_Surface *img = IMG_Load(filename); if (!img) { REPORT_WARNING("Texture image \"%s\" not found", filename); *pixels = 0; return; } *width = img->w; *height = img->h; *bytes_per_pixel = img->format->BytesPerPixel; s = (*bytes_per_pixel) * (*width) * (*height); *pixels = (u8 *) malloc(s); memcpy(*pixels, img->pixels, s); /* LOWPRIO: Better implementation... when I'm feeling less lazy */ if (flip_y) { u32 x, y, i; for (y = 0; y < (*height) >> 1; y++) { for (x = 0; x < *width; x++) { for (i = 0; i < *bytes_per_pixel; i++) { u8 *p0, *p1; u8 t; p0 = &(*pixels)[(y * (*width) + x) * (*bytes_per_pixel) + i]; p1 = &(*pixels)[((*height - y - 1) * (*width) + x) * (*bytes_per_pixel) + i]; t = *p0; *p0 = *p1; *p1 = t; } } } } if (img->format->Rmask != 255 && *bytes_per_pixel != 1) { u32 x, y; for (y = 0; y < *height; y++) { for (x = 0; x < *width; x++) { u8 *p0, *p1; u8 t; p0 = &(*pixels)[(y * (*width) + x) * (*bytes_per_pixel) + 0]; p1 = &(*pixels)[(y * (*width) + x) * (*bytes_per_pixel) + 2]; t = *p0; *p0 = *p1; *p1 = t; } } } SDL_FreeSurface((SDL_Surface *) img); }
void VertexArray::setIndexArray( void *new_array, u32 type_size, u32 n ) { //#ifdef RC_IPHONE u16 *small_array = 0; //#endif if (n == 0 || !new_array || type_size == 0) { /* TODO: Remove index array */ holds_index_array = false; return; } ASSERT(type_size == 1 || type_size == 2 || type_size == 4); n_indices = n; index_usage = USAGE_STATIC; #ifdef RC_IPHONE if (type_size == 4) { #else if (type_size == 4 && n < 65535) { #endif u32 *ii = (u32 *) new_array; u32 i; small_array = (u16 *) malloc(sizeof(u16) * n); for (i = 0; i < n; i++) { small_array[i] = (u16) ii[i]; } type_size = 2; new_array = small_array; } indexArrayTypeSize = type_size; if (!holds_index_array) { Renderer::loadIndexArray(this, new_array, n, index_usage); } else { Renderer::reloadIndexArray(this, new_array, n); } if (iarray) free(iarray); iarray = malloc(n * type_size); memcpy(iarray, new_array, n * type_size); #ifdef RC_IPHONE if (small_array) free(small_array); #endif holds_index_array = true; } /*---------------------------------------------------------------------------*/ void VertexArray::setAttribute( const char *name, u32 offset, u32 length, AttributeType_t type, bool normalized ) { i32 i; if (length == 0) return; if (n_attribs >= RC_MAX_ATTRIBS) { REPORT_WARNING("Too many attributes added for vertex array resource %s", identifier); return; } if (offset >= stride) { REPORT_WARNING("The offset is greater or equal to stride (%s)", identifier); return; } for (i = 0; i < (i32) n_attribs; i++) { if (strcmp(name, attrib[i].name) == 0) { REPORT_WARNING("Attribute %s already exists", name); return; } } i = n_attribs - 1; while (i >= 0 && offset < attrib[i].offset) { attrib[i + 1].offset = attrib[i].offset; attrib[i + 1].length = attrib[i].length; attrib[i + 1].name = attrib[i].name; attrib[i + 1].type = attrib[i].type; attrib[i + 1].normalized = attrib[i].normalized; i--; } i++; attrib[i].offset = offset; attrib[i].length = length; attrib[i].name = duplicateString(name); attrib[i].type = type; attrib[i].normalized = normalized; n_attribs++; }
void VertexArray::getBoundingBox( AABox *target ) { u8 *va; u32 i; Attribute_t *a; AABox box; if (has_bounds) { *target = bounds; return; } box.minCorner = vec3f(0.0f, 0.0f, 0.0f); box.maxCorner = vec3f(0.0f, 0.0f, 0.0f); a = getAttribute("Vertex"); if (!a) { REPORT_WARNING("No \"Vertex\" attribute to extract bounding box from"); *target = box; return; } if (a->type != ATTRIB_FLOAT32) { REPORT_WARNING("The \"Vertex\" attribute must be a 32 bit float"); *target = box; return; } if (!varray) { REPORT_WARNING("No vertex array attached"); *target = box; return; } if (n_elements == 0) { REPORT_WARNING("Vertex array contains no elements"); *target = box; return; } bounds.minCorner = fMax; bounds.maxCorner = -fMax; va = (u8 *) varray; va += a->offset; for (i = 0; i < n_elements; i++) { f32 *vtx; vec3f pt; vtx = (f32 *) va; pt = vec3f(vtx[0], vtx[1], vtx[2]); bounds.include(pt); va += stride; } has_bounds = true; *target = bounds; }
void Command::run( char *str ) { char *p; char *orig = str; // static const char delim[] = " \t"; u32 i, k, n_args; // char buf[RC_CONSOLE_MAX_LINE_WIDTH]; char *cmd; char *argbuf[RC_COMMAND_MAX_ARGS]; /* Command + RC_CONSOLE_MAX_ARGS args */ bool success = false; bool in_quotes = false; Command_t *e; u32 h, len; #ifdef RC_LOG_FRENZY printf("Command: %s\n", str); #endif while (*str && (*str == ' ' || *str == '\t')) str++; if (*str == '/') { str++; } else { Console::log(orig); return; } p = str; len = strlen(str); if (len == 0) { REPORT_WARNING("No command given"); return; } Console::log(orig); k = 0; while (*p) { if (*p == ' ' || *p == '\t') { break; } p++; k++; } cmd = new char[k + 1]; strncpy(cmd, str, k); cmd[k] = 0; /* Search for command */ h = calculateStringHash(cmd) % RC_COMMAND_HASH_SIZE; e = command_hash[h]; while (e) { if (strcmp(e->name, cmd) == 0) { break; } e = e->hash_next; } if (!e) { REPORT_WARNING("Command %s not found", cmd); return; } /* Parse arguments */ str += k; i = 0; while (*str && *str != '\n' && *str != '\r' && i < RC_COMMAND_MAX_ARGS) { k = 0; in_quotes = false; while (*str && (*str == ' ' || *str == '\t')) str++; if (*str == '\"') { in_quotes = true; str++; } p = str; while (*p) { if ((*p == ' ' || *p == '\t') && !in_quotes) { break; } else if (*p == '\"' && in_quotes) { break; } else if (*p == 0) { break; } p++; k++; } argbuf[i] = new char[k + 1]; strncpy(argbuf[i], str, k); argbuf[i][k] = 0; if (in_quotes) k++; str += k; i++; } n_args = i; success = e->funcptr(n_args, argbuf); if (!success) { REPORT_WARNING("Command %s failed", cmd); Console::log("Usage: %s", e->desc); } delete cmd; for (i = 0; i < n_args; i++) delete argbuf[i]; }
static ACPI_STATUS AcpiNsDumpOneObject ( ACPI_HANDLE ObjHandle, UINT32 Level, void *Context, void **ReturnValue) { ACPI_WALK_INFO *Info = (ACPI_WALK_INFO *) Context; ACPI_NAMESPACE_NODE *ThisNode; UINT8 *Value; ACPI_OPERAND_OBJECT *ObjDesc = NULL; ACPI_OBJECT_TYPE8 ObjType; ACPI_OBJECT_TYPE8 Type; UINT32 BytesToDump; UINT32 DownstreamSiblingMask = 0; UINT32 LevelTmp; UINT32 WhichBit; PROC_NAME ("NsDumpOneObject"); ThisNode = AcpiNsConvertHandleToEntry (ObjHandle); LevelTmp = Level; Type = ThisNode->Type; WhichBit = 1; if (!(AcpiDbgLevel & Info->DebugLevel)) { return (AE_OK); } if (!ObjHandle) { ACPI_DEBUG_PRINT ((ACPI_DB_INFO, "Null object handle\n")); return (AE_OK); } /* Check if the owner matches */ if ((Info->OwnerId != ACPI_UINT32_MAX) && (Info->OwnerId != ThisNode->OwnerId)) { return (AE_OK); } /* Indent the object according to the level */ while (LevelTmp--) { /* Print appropriate characters to form tree structure */ if (LevelTmp) { if (DownstreamSiblingMask & WhichBit) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "|")); } else { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, " ")); } WhichBit <<= 1; } else { if (AcpiNsExistDownstreamSibling (ThisNode + 1)) { DownstreamSiblingMask |= (1 << (Level - 1)); ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "+")); } else { DownstreamSiblingMask &= ACPI_UINT32_MAX ^ (1 << (Level - 1)); ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "+")); } if (ThisNode->Child == NULL) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "-")); } else if (AcpiNsExistDownstreamSibling (ThisNode->Child)) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "+")); } else { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "-")); } } } /* Check the integrity of our data */ if (Type > INTERNAL_TYPE_MAX) { Type = INTERNAL_TYPE_DEF_ANY; /* prints as *ERROR* */ } if (!AcpiUtValidAcpiName (ThisNode->Name)) { REPORT_WARNING (("Invalid ACPI Name %08X\n", ThisNode->Name)); } /* * Now we can print out the pertinent information */ ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, " %4.4s %-9s ", &ThisNode->Name, AcpiUtGetTypeName (Type))); ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "%p S:%p O:%p", ThisNode, ThisNode->Child, ThisNode->Object)); if (!ThisNode->Object) { /* No attached object, we are done */ ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "\n")); return (AE_OK); } switch (Type) { case ACPI_TYPE_METHOD: /* Name is a Method and its AML offset/length are set */ ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, " M:%p-%X\n", ((ACPI_OPERAND_OBJECT *) ThisNode->Object)->Method.Pcode, ((ACPI_OPERAND_OBJECT *) ThisNode->Object)->Method.PcodeLength)); break; case ACPI_TYPE_INTEGER: ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, " N:%X\n", ((ACPI_OPERAND_OBJECT *) ThisNode->Object)->Integer.Value)); break; case ACPI_TYPE_STRING: ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, " S:%p-%X\n", ((ACPI_OPERAND_OBJECT *) ThisNode->Object)->String.Pointer, ((ACPI_OPERAND_OBJECT *) ThisNode->Object)->String.Length)); break; case ACPI_TYPE_BUFFER: ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, " B:%p-%X\n", ((ACPI_OPERAND_OBJECT *) ThisNode->Object)->Buffer.Pointer, ((ACPI_OPERAND_OBJECT *) ThisNode->Object)->Buffer.Length)); break; default: ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "\n")); break; } /* If debug turned off, done */ if (!(AcpiDbgLevel & ACPI_LV_VALUES)) { return (AE_OK); } /* If there is an attached object, display it */ Value = ThisNode->Object; /* Dump attached objects */ while (Value) { ObjType = INTERNAL_TYPE_INVALID; /* Decode the type of attached object and dump the contents */ ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, " Attached Object %p: ", Value)); if (AcpiTbSystemTablePointer (Value)) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "(Ptr to AML Code)\n")); BytesToDump = 16; } else if (VALID_DESCRIPTOR_TYPE (Value, ACPI_DESC_TYPE_NAMED)) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "(Ptr to Node)\n")); BytesToDump = sizeof (ACPI_NAMESPACE_NODE); } else if (VALID_DESCRIPTOR_TYPE (Value, ACPI_DESC_TYPE_INTERNAL)) { ObjDesc = (ACPI_OPERAND_OBJECT *) Value; ObjType = ObjDesc->Common.Type; if (ObjType > INTERNAL_TYPE_MAX) { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "(Ptr to ACPI Object type %X [UNKNOWN])\n", ObjType)); BytesToDump = 32; } else { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "(Ptr to ACPI Object type %X [%s])\n", ObjType, AcpiUtGetTypeName (ObjType))); BytesToDump = sizeof (ACPI_OPERAND_OBJECT); } } else { ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "(String or Buffer - not descriptor)\n", Value)); BytesToDump = 16; } DUMP_BUFFER (Value, BytesToDump); /* If value is NOT an internal object, we are done */ if ((AcpiTbSystemTablePointer (Value)) || (VALID_DESCRIPTOR_TYPE (Value, ACPI_DESC_TYPE_NAMED))) { goto Cleanup; } /* * Valid object, get the pointer to next level, if any */ switch (ObjType) { case ACPI_TYPE_STRING: Value = (UINT8 *) ObjDesc->String.Pointer; break; case ACPI_TYPE_BUFFER: Value = (UINT8 *) ObjDesc->Buffer.Pointer; break; case ACPI_TYPE_BUFFER_FIELD: Value = (UINT8 *) ObjDesc->BufferField.BufferObj; break; case ACPI_TYPE_PACKAGE: Value = (UINT8 *) ObjDesc->Package.Elements; break; case ACPI_TYPE_METHOD: Value = (UINT8 *) ObjDesc->Method.Pcode; break; case INTERNAL_TYPE_REGION_FIELD: Value = (UINT8 *) ObjDesc->Field.RegionObj; break; case INTERNAL_TYPE_BANK_FIELD: Value = (UINT8 *) ObjDesc->BankField.RegionObj; break; case INTERNAL_TYPE_INDEX_FIELD: Value = (UINT8 *) ObjDesc->IndexField.IndexObj; break; default: goto Cleanup; } ObjType = INTERNAL_TYPE_INVALID; /* Terminate loop after next pass */ } Cleanup: ACPI_DEBUG_PRINT_RAW ((ACPI_DB_TABLES, "\n")); return (AE_OK); }
int summary(struct area * areap) { if (TARGET_IS_8051 || TARGET_IS_6808) { /* only for 8051 and 6808 targets */ #define EQ(A,B) !as_strcmpi((A),(B)) #define MIN_STACK 16 #define REPORT_ERROR(A, H) \ {\ fprintf(of, "%s%s", (H)?"*** ERROR: ":"", (A)); \ fprintf(stderr, "%s%s", (H)?"\n?ASlink-Error-":"",(A)); \ toreturn=1; \ } #define REPORT_WARNING(A, H) \ { \ fprintf(of, "%s%s", (H)?"*** WARNING: ":"", (A)); \ fprintf(stderr, "%s%s",(H)?"\n?ASlink-Warning-":"", (A)); \ } char buff[128]; int j, toreturn=0; unsigned int Total_Last=0, k; struct area * xp; FILE * of; /*Artifacts used for printing*/ char start[15], end[15], size[15], max[15]; char format[]=" %-16.16s %-8.8s %-8.8s %-8.8s %-8.8s\n"; char line[]="---------------------"; typedef struct { unsigned long Start; unsigned long Size; unsigned long Max; char Name[NCPS]; unsigned long flag; } _Mem; unsigned int dram[0x100]; _Mem Ram8051[] = { {0, 8, 8, "REG_BANK_0", 0x0001}, {0x8, 8, 8, "REG_BANK_1", 0x0002}, {0x10, 8, 8, "REG_BANK_2", 0x0004}, {0x18, 8, 8, "REG_BANK_3", 0x0008}, {0x20, 0, 16, "BSEG_BYTES", 0x0010}, {0, 0, 128, "UNUSED", 0x0000}, {0x7f, 0, 128, "DATA", 0x0020}, {0, 0, 128, "TOTAL:", 0x0000} }; _Mem IRam8051 = {0xff, 0, 128, "INDIRECT RAM", 0x0080}; _Mem Stack8051 = {0xff, 0, 1, "STACK", 0x0000}; _Mem XRam8051 = {0xffff, 0, 65536, "EXTERNAL RAM", 0x0100}; _Mem Rom8051 = {0xffff, 0, 65536, "ROM/EPROM/FLASH", 0x0200}; _Mem Ram6808[] = { {0, 0, 0, "REG_BANK_0", 0x0001}, {0x0, 0, 0, "REG_BANK_1", 0x0002}, {0x0, 0, 0, "REG_BANK_2", 0x0004}, {0x0, 0, 0, "REG_BANK_3", 0x0008}, {0x0, 0, 0, "BSEG_BYTES", 0x0010}, {0, 0, 256, "UNUSED", 0x0000}, {0xff, 0, 256, "DATA", 0x0020}, {0, 0, 256, "TOTAL:", 0x0000} }; _Mem IRam6808 = {0xff, 0, 0, "INDIRECT RAM", 0x0080}; _Mem Stack6808 = {0xff, 0, 1, "STACK", 0x0000}; _Mem XRam6808 = {0xffff, 0, 65536, "EXTERNAL RAM", 0x0100}; _Mem Rom6808 = {0xffff, 0, 65536, "ROM/EPROM/FLASH", 0x0200}; _Mem *Ram = NULL; _Mem IRam = {0, 0, 0, "", 0}; _Mem Stack = {0, 0, 0, "", 0}; _Mem XRam = {0, 0, 0, "", 0}; _Mem Rom = {0, 0, 0, "", 0}; if (TARGET_IS_8051) { Ram = Ram8051; memcpy(&IRam, &IRam8051, sizeof (_Mem)); memcpy(&Stack, &Stack8051, sizeof (_Mem)); memcpy(&XRam, &XRam8051, sizeof (_Mem)); memcpy(&Rom, &Rom8051, sizeof (_Mem)); } else { Ram = Ram6808; memcpy(&IRam, &IRam6808, sizeof (_Mem)); memcpy(&Stack, &Stack6808, sizeof (_Mem)); memcpy(&XRam, &XRam6808, sizeof (_Mem)); memcpy(&Rom, &Rom6808, sizeof (_Mem)); } if (stacksize == 0) stacksize = MIN_STACK; if (TARGET_IS_8051) { if(rflag) /*For the DS390*/ { XRam.Max=0x1000000; /*24 bits*/ XRam.Start=0xffffff; Rom.Max=0x1000000; Rom.Start=0xffffff; } if((iram_size<=0)||(iram_size>0x100)) /*Default: 8052 like memory*/ { Ram[5].Max=0x80; Ram[6].Max=0x80; Ram[7].Max=0x80; IRam.Max=0x80; iram_size=0x100; } else if(iram_size<0x80) { Ram[5].Max=iram_size; Ram[6].Max=iram_size; Ram[7].Max=iram_size; IRam.Max=0; } else { Ram[5].Max=0x80; Ram[6].Max=0x80; Ram[7].Max=0x80; IRam.Max=iram_size-0x80; } } for(j=0; j<(int)iram_size; j++) dram[j]=0; for(; j<0x100; j++) dram[j]=0x8000; /*Memory not available*/ /* Open Memory Summary File*/ of = afile(linkp->f_idp, "mem", 1); if (of == NULL) { lkexit(1); } xp=areap; while (xp) { /**/ if (EQ(xp->a_id, "REG_BANK_0")) { Ram[0].Size=xp->a_size; } else if (EQ(xp->a_id, "REG_BANK_1")) { Ram[1].Size=xp->a_size; } else if (EQ(xp->a_id, "REG_BANK_2")) { Ram[2].Size=xp->a_size; } else if (EQ(xp->a_id, "REG_BANK_3")) { Ram[3].Size=xp->a_size; } else if (EQ(xp->a_id, "BSEG_BYTES")) { if (TARGET_IS_8051) Ram[4].Size+=xp->a_size; else Ram[4].Size=xp->a_size; } else if (EQ(xp->a_id, "SSEG")) { Stack.Size+=xp->a_size; if(xp->a_addr<Stack.Start) Stack.Start=xp->a_addr; } else if (EQ(xp->a_id, "ISEG")) { IRam.Size+=xp->a_size; if(xp->a_addr<IRam.Start) IRam.Start=xp->a_addr; } else if (TARGET_IS_8051) { if(xp->a_flag & A_XDATA) { if(xp->a_size>0) { XRam.Size+=xp->a_size; if(xp->a_addr<XRam.Start) XRam.Start=xp->a_addr; } } else if (EQ(xp->a_id, "BIT_BANK")) { Ram[4].Size+=xp->a_size; } else if(xp->a_flag & A_CODE) { if(xp->a_size>0) { Rom.Size+=xp->a_size; if(xp->a_addr<Rom.Start) Rom.Start=xp->a_addr; } } } else if(TARGET_IS_6808) { if ( EQ(xp->a_id, "DSEG") || EQ(xp->a_id, "OSEG") ) { Ram[6].Size+=xp->a_size; if(xp->a_addr<Ram[6].Start) Ram[6].Start=xp->a_addr; } else if( EQ(xp->a_id, "CSEG") || EQ(xp->a_id, "GSINIT") || EQ(xp->a_id, "GSFINAL") || EQ(xp->a_id, "HOME") ) { Rom.Size+=xp->a_size; if(xp->a_addr<Rom.Start) Rom.Start=xp->a_addr; } else if (EQ(xp->a_id, "XSEG") || EQ(xp->a_id, "XISEG")) { XRam.Size+=xp->a_size; if(xp->a_addr<XRam.Start) XRam.Start=xp->a_addr; } } /*If is not a register bank, bit, stack, or idata, then it should be data*/ else if((TARGET_IS_8051 && xp->a_flag & (A_CODE|A_BIT|A_XDATA))==0) { if(xp->a_size) { Ram[6].Size+=xp->a_size; if(xp->a_addr<Ram[6].Start) Ram[6].Start=xp->a_addr; } } xp=xp->a_ap; } for(j=0; j<7; j++) for(k=Ram[j].Start; (k<(Ram[j].Start+Ram[j].Size))&&(k<0x100); k++) dram[k]|=Ram[j].flag; /*Mark as used*/ if (TARGET_IS_8051) { for(k=IRam.Start; (k<(IRam.Start+IRam.Size))&&(k<0x100); k++) dram[k]|=IRam.flag; /*Mark as used*/ } /*Compute the amount of unused memory in direct data Ram. This is the gap between the last register bank or bit segment and the data segment.*/ for(k=Ram[6].Start-1; (dram[k]==0) && (k>0); k--); Ram[5].Start=k+1; Ram[5].Size=Ram[6].Start-Ram[5].Start; /*It may be zero (which is good!)*/ /*Compute the data Ram totals*/ for(j=0; j<7; j++) { if(Ram[7].Start>Ram[j].Start) Ram[7].Start=Ram[j].Start; Ram[7].Size+=Ram[j].Size; } Total_Last=Ram[6].Size+Ram[6].Start-1; /*Report the Ram totals*/ fprintf(of, "Direct Internal RAM:\n"); fprintf(of, format, "Name", "Start", "End", "Size", "Max"); for(j=0; j<8; j++) { if((j==0) || (j==7)) fprintf(of, format, line, line, line, line, line); if((j!=5) || (Ram[j].Size>0)) { sprintf(start, "0x%02lx", Ram[j].Start); if(Ram[j].Size==0) end[0]=0;/*Empty string*/ else sprintf(end, "0x%02lx", j==7?Total_Last:Ram[j].Size+Ram[j].Start-1); sprintf(size, "%5lu", Ram[j].Size); sprintf(max, "%5lu", Ram[j].Max); fprintf(of, format, Ram[j].Name, start, end, size, max); } } if (TARGET_IS_8051) { for(k=Ram[6].Start; (k<(Ram[6].Start+Ram[6].Size))&&(k<0x100); k++) { if(dram[k]!=Ram[6].flag) { sprintf(buff, "Internal memory overlap starting at 0x%02x.\n", k); REPORT_ERROR(buff, 1); break; } } if(Ram[4].Size>Ram[4].Max) { k=Ram[4].Size-Ram[4].Max; sprintf(buff, "Insufficient bit addressable memory. " "%d byte%s short.\n", k, (k==1)?"":"s"); REPORT_ERROR(buff, 1); } if(Ram[5].Size!=0) { sprintf(buff, "%ld bytes in data memory wasted. " "SDCC link could use: --data-loc 0x%02lx\n", Ram[5].Size, Ram[6].Start-Ram[5].Size); REPORT_WARNING(buff, 1); } if((Ram[6].Start+Ram[6].Size)>Ram[6].Max) { k=(Ram[6].Start+Ram[6].Size)-Ram[6].Max; sprintf(buff, "Insufficient space in data memory. " "%d byte%s short.\n", k, (k==1)?"":"s"); REPORT_ERROR(buff, 1); } } /*Report the position of the beginning of the stack*/ fprintf(of, "\n%stack starts at: 0x%02lx (sp set to 0x%02lx)", rflag ? "16 bit mode initial s" : "S", Stack.Start, Stack.Start-1); if (TARGET_IS_8051) { /*Check that the stack pointer is landing in a safe place:*/ if( (dram[Stack.Start] & 0x8000) == 0x8000 ) { fprintf(of, ".\n"); sprintf(buff, "Stack set to unavailable memory.\n"); REPORT_ERROR(buff, 1); } else if(dram[Stack.Start]) { fprintf(of, ".\n"); sprintf(buff, "Stack overlaps area "); REPORT_ERROR(buff, 1); for(j=0; j<7; j++) { if(dram[Stack.Start]&Ram[j].flag) { sprintf(buff, "'%s'\n", Ram[j].Name); break; } } if(dram[Stack.Start]&IRam.flag) { sprintf(buff, "'%s'\n", IRam.Name); } REPORT_ERROR(buff, 0); } else { for(j=Stack.Start, k=0; (j<(int)iram_size)&&(dram[j]==0); j++, k++); fprintf(of, " with %d bytes available\n", k); if ((int)k<stacksize) { sprintf(buff, "Only %d byte%s available for stack.\n", k, (k==1)?"":"s"); REPORT_WARNING(buff, 1); } } } fprintf(of, "\nOther memory:\n"); fprintf(of, format, "Name", "Start", "End", "Size", "Max"); fprintf(of, format, line, line, line, line, line); /*Report IRam totals:*/ if(IRam.Size==0) { start[0]=0;/*Empty string*/ end[0]=0;/*Empty string*/ } else { sprintf(start, "0x%02lx", IRam.Start); sprintf(end, "0x%02lx", IRam.Size+IRam.Start-1); } sprintf(size, "%5lu", IRam.Size); sprintf(max, "%5lu", IRam.Max); fprintf(of, format, IRam.Name, start, end, size, max); /*Report XRam totals:*/ if(XRam.Size==0) { start[0]=0;/*Empty string*/ end[0]=0;/*Empty string*/ } else { sprintf(start, "0x%04lx", XRam.Start); sprintf(end, "0x%04lx", XRam.Size+XRam.Start-1); } sprintf(size, "%5lu", XRam.Size); sprintf(max, "%5lu", xram_size<0?XRam.Max:xram_size); fprintf(of, format, XRam.Name, start, end, size, max); /*Report Rom/Flash totals:*/ if(Rom.Size==0) { start[0]=0;/*Empty string*/ end[0]=0;/*Empty string*/ } else { sprintf(start, "0x%04lx", Rom.Start); sprintf(end, "0x%04lx", Rom.Size+Rom.Start-1); } sprintf(size, "%5lu", Rom.Size); sprintf(max, "%5lu", code_size<0?Rom.Max:code_size); fprintf(of, format, Rom.Name, start, end, size, max); /*Report any excess:*/ if (TARGET_IS_8051) { if((IRam.Start+IRam.Size)>(IRam.Max+0x80)) { sprintf(buff, "Insufficient INDIRECT RAM memory.\n"); REPORT_ERROR(buff, 1); } } if( ((XRam.Start+XRam.Size)>XRam.Max) || (((int)XRam.Size>xram_size)&&(xram_size>=0)) ) { sprintf(buff, "Insufficient EXTERNAL RAM memory.\n"); REPORT_ERROR(buff, 1); } if( ((Rom.Start+Rom.Size)>Rom.Max) || (((int)Rom.Size>code_size)&&(code_size>=0)) ) { sprintf(buff, "Insufficient ROM/EPROM/FLASH memory.\n"); REPORT_ERROR(buff, 1); } fclose(of); return toreturn; } else { assert (0); return 0; } }
ACPI_STATUS acpi_ns_lookup ( ACPI_GENERIC_STATE *scope_info, NATIVE_CHAR *pathname, OBJECT_TYPE_INTERNAL type, OPERATING_MODE interpreter_mode, u32 flags, ACPI_WALK_STATE *walk_state, ACPI_NAMESPACE_NODE **return_node) { ACPI_STATUS status; ACPI_NAMESPACE_NODE *prefix_node; ACPI_NAMESPACE_NODE *current_node = NULL; ACPI_NAMESPACE_NODE *scope_to_push = NULL; ACPI_NAMESPACE_NODE *this_node = NULL; u32 num_segments; ACPI_NAME simple_name; u8 null_name_path = FALSE; OBJECT_TYPE_INTERNAL type_to_check_for; OBJECT_TYPE_INTERNAL this_search_type; DEBUG_ONLY_MEMBERS (u32 i) if (!return_node) { return (AE_BAD_PARAMETER); } acpi_gbl_ns_lookup_count++; *return_node = ENTRY_NOT_FOUND; if (!acpi_gbl_root_node) { return (AE_NO_NAMESPACE); } /* * Get the prefix scope. * A null scope means use the root scope */ if ((!scope_info) || (!scope_info->scope.node)) { prefix_node = acpi_gbl_root_node; } else { prefix_node = scope_info->scope.node; } /* * This check is explicitly split provide relax the Type_to_check_for * conditions for Bank_field_defn. Originally, both Bank_field_defn and * Def_field_defn caused Type_to_check_for to be set to ACPI_TYPE_REGION, * but the Bank_field_defn may also check for a Field definition as well * as an Operation_region. */ if (INTERNAL_TYPE_DEF_FIELD_DEFN == type) { /* Def_field_defn defines fields in a Region */ type_to_check_for = ACPI_TYPE_REGION; } else if (INTERNAL_TYPE_BANK_FIELD_DEFN == type) { /* Bank_field_defn defines data fields in a Field Object */ type_to_check_for = ACPI_TYPE_ANY; } else { type_to_check_for = type; } /* TBD: [Restructure] - Move the pathname stuff into a new procedure */ /* Examine the name pointer */ if (!pathname) { /* 8-12-98 ASL Grammar Update supports null Name_path */ null_name_path = TRUE; num_segments = 0; this_node = acpi_gbl_root_node; } else { /* * Valid name pointer (Internal name format) * * Check for prefixes. As represented in the AML stream, a * Pathname consists of an optional scope prefix followed by * a segment part. * * If present, the scope prefix is either a Root_prefix (in * which case the name is fully qualified), or zero or more * Parent_prefixes (in which case the name's scope is relative * to the current scope). * * The segment part consists of either: * - A single 4-byte name segment, or * - A Dual_name_prefix followed by two 4-byte name segments, or * - A Multi_name_prefix_op, followed by a byte indicating the * number of segments and the segments themselves. */ if (*pathname == AML_ROOT_PREFIX) { /* Pathname is fully qualified, look in root name table */ current_node = acpi_gbl_root_node; /* point to segment part */ pathname++; /* Direct reference to root, "\" */ if (!(*pathname)) { this_node = acpi_gbl_root_node; goto check_for_new_scope_and_exit; } } else { /* Pathname is relative to current scope, start there */ current_node = prefix_node; /* * Handle up-prefix (carat). More than one prefix * is supported */ while (*pathname == AML_PARENT_PREFIX) { /* Point to segment part or next Parent_prefix */ pathname++; /* Backup to the parent's scope */ this_node = acpi_ns_get_parent_object (current_node); if (!this_node) { /* Current scope has no parent scope */ REPORT_ERROR (("Too many parent prefixes (^) - reached root\n")); return (AE_NOT_FOUND); } current_node = this_node; } } /* * Examine the name prefix opcode, if any, * to determine the number of segments */ if (*pathname == AML_DUAL_NAME_PREFIX) { num_segments = 2; /* point to first segment */ pathname++; } else if (*pathname == AML_MULTI_NAME_PREFIX_OP) { num_segments = (u32)* (u8 *) ++pathname; /* point to first segment */ pathname++; } else { /* * No Dual or Multi prefix, hence there is only one * segment and Pathname is already pointing to it. */ num_segments = 1; } } /* * Search namespace for each segment of the name. * Loop through and verify/add each name segment. */ while (num_segments-- && current_node) { /* * Search for the current name segment under the current * named object. The Type is significant only at the last (topmost) * level. (We don't care about the types along the path, only * the type of the final target object.) */ this_search_type = ACPI_TYPE_ANY; if (!num_segments) { this_search_type = type; } /* Pluck one ACPI name from the front of the pathname */ MOVE_UNALIGNED32_TO_32 (&simple_name, pathname); /* Try to find the ACPI name */ status = acpi_ns_search_and_enter (simple_name, walk_state, current_node, interpreter_mode, this_search_type, flags, &this_node); if (ACPI_FAILURE (status)) { if (status == AE_NOT_FOUND) { /* Name not found in ACPI namespace */ } return (status); } /* * If 1) This is the last segment (Num_segments == 0) * 2) and looking for a specific type * (Not checking for TYPE_ANY) * 3) Which is not an alias * 4) which is not a local type (TYPE_DEF_ANY) * 5) which is not a local type (TYPE_SCOPE) * 6) which is not a local type (TYPE_INDEX_FIELD_DEFN) * 7) and type of object is known (not TYPE_ANY) * 8) and object does not match request * * Then we have a type mismatch. Just warn and ignore it. */ if ((num_segments == 0) && (type_to_check_for != ACPI_TYPE_ANY) && (type_to_check_for != INTERNAL_TYPE_ALIAS) && (type_to_check_for != INTERNAL_TYPE_DEF_ANY) && (type_to_check_for != INTERNAL_TYPE_SCOPE) && (type_to_check_for != INTERNAL_TYPE_INDEX_FIELD_DEFN) && (this_node->type != ACPI_TYPE_ANY) && (this_node->type != type_to_check_for)) { /* Complain about a type mismatch */ REPORT_WARNING ( ("Ns_lookup: %4.4s, type %X, checking for type %X\n", &simple_name, this_node->type, type_to_check_for)); } /* * If this is the last name segment and we are not looking for a * specific type, but the type of found object is known, use that type * to see if it opens a scope. */ if ((0 == num_segments) && (ACPI_TYPE_ANY == type)) { type = this_node->type; } if ((num_segments || acpi_ns_opens_scope (type)) && (this_node->child == NULL)) { /* * More segments or the type implies enclosed scope, * and the next scope has not been allocated. */ } current_node = this_node; /* point to next name segment */ pathname += ACPI_NAME_SIZE; } /* * Always check if we need to open a new scope */ check_for_new_scope_and_exit: if (!(flags & NS_DONT_OPEN_SCOPE) && (walk_state)) { /* * If entry is a type which opens a scope, * push the new scope on the scope stack. */ if (acpi_ns_opens_scope (type_to_check_for)) { /* 8-12-98 ASL Grammar Update supports null Name_path */ if (null_name_path) { /* TBD: [Investigate] - is this the correct thing to do? */ scope_to_push = NULL; } else { scope_to_push = this_node; } status = acpi_ds_scope_stack_push (scope_to_push, type, walk_state); if (ACPI_FAILURE (status)) { return (status); } } } *return_node = this_node; return (AE_OK); }