FreeCalypso > hg > fc-magnetite
view src/cs/riviera/rvm/rvm_mem.c @ 478:5e39123540e6
hybrid fw: Openmoko-mimicking AT@BAND command implemented
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Thu, 14 Jun 2018 06:04:54 +0000 |
parents | 945cf7f506b2 |
children |
line wrap: on
line source
/** * * @file rvm_mem.c * * This file contains the functions related to memory management within RVM. * * @author David Lamy-Charrier (d-lamy@ti.com) * @version 0.1 * */ /* * Revision History: * * 10/26/2001 David Lamy-Charrier Create for Riviera 1.6. * * (C) Copyright 2001 by Texas Instruments Incorporated, All Rights Reserved */ #include "rvm/rvm_i.h" #include "rvm/rvm_gen.h" #include "rvm/rvm_api.h" #include "rvm/rvm_use_id_list.h" #include "rvf/rvf_env.h" extern T_RVM_GET_INFO_FUNC RVM_SWE_GET_INFO_ARRAY[]; extern T_RVM_KNOWN_SWE * rvm_swe_array; /******************************************************************************* ** Function rvm_delete_used_memory ** ** Description Internal function which deletes used local mem if an error ** was received or at the end of the start/stop process. ** *******************************************************************************/ T_RVM_RETURN rvm_delete_used_memory ( T_RVM_PROCESSING_SWE * appli) { T_RVF_BUFFER_Q buffer_to_free_q = {0, 0, 0}; T_RVM_PROCESSING_SWE * cur_elem = appli; while (cur_elem != NULL) { rvf_enqueue (&buffer_to_free_q, cur_elem); cur_elem = cur_elem->next_swe; } while (buffer_to_free_q.p_first) { rvf_free_buf (rvf_dequeue (&buffer_to_free_q)); } return RVM_OK; } /******************************************************************************* ** Function rvm_delete_created_mb ** ** Description Internal function which deletes all created MB if an error ** was received, or in case application has to be stopped. ** *******************************************************************************/ T_RVM_RETURN rvm_delete_created_mb (T_RVM_PROCESSING_SWE * appli) { UINT8 mb_index; T_RVM_PROCESSING_SWE * cur_elem = appli; volatile T_RV_RET ret_value = RV_OK; UINT8 mb_to_delete; while (cur_elem != NULL ) { UINT8 swe_index = cur_elem->swe_id; /* If more than one appli is using this SWE, cannot delete MB Process to the next SWE. */ if (rvm_swe_array[swe_index].nb_using_appli > 1) { cur_elem = cur_elem->next_swe; /* process the next SWE */ continue; } /* If the state is running, it means that this SWE has not to be stopped. */ if (rvm_swe_array[swe_index].swe_state == SWE_RUNNING) { cur_elem = cur_elem->next_swe; /* process the next SWE */ continue; } /* We're here: - either because swe_state == SWE_NOT_STARTED => error in starting prcess - either because swe_state == SWE_STOPPING => regular stopping process */ if (cur_elem->nb_created_mb == 0) { cur_elem = cur_elem->next_swe; /* process the next SWE */ continue; } mb_to_delete = cur_elem->nb_created_mb; for( mb_index = 0; mb_index < mb_to_delete; mb_index++) { ret_value = rvf_delete_mb(cur_elem->swe_mem_bank[mb_index].mb_name); if (ret_value != RV_OK) { rvf_send_trace("RVM: Error in deletion of memory bank: ", 39, NULL_PARAM, RV_TRACE_LEVEL_WARNING, RVM_USE_ID ); rvf_send_trace(cur_elem->swe_mem_bank[mb_index].mb_name, RVF_MAX_MB_LEN, NULL_PARAM, RV_TRACE_LEVEL_WARNING, RVM_USE_ID ); } else { (cur_elem->nb_created_mb)--; } ret_value = RVM_OK; } cur_elem = cur_elem->next_swe; /* process the next SWE */ } return ret_value; } /******************************************************************************* ** ** Function rvm_check_memory_requirement ** ** Description This function checks if there is enough memory ** to start a SWE(and all the linked SWEs) ** ** Parameters: T_RVM_PROCESSING_SWE * appli: list of required SWEs with their parameters. ** ** Returns T_RVM_RETURN: RVM_OK if there is enough memory, else RVM_MEMORY_ERR. ** *******************************************************************************/ T_RVM_RETURN rvm_verify_memory_requirement( T_RVM_PROCESSING_SWE * appli, T_RVM_GROUP_DIRECTIVE* gd, UINT8 cnt) { T_RVM_PROCESSING_SWE * cur_swe = appli; UINT32 required_mem = 0; UINT32 total_mem = 0; UINT32 used_mem = 0; UINT8 mb_index; UINT8 i=0; UINT16 host_task_mem=0; /* get available memory from the rvf */ if ( rvf_get_available_mem( &total_mem, &used_mem) != RVF_OK ) { return RVM_MEMORY_ERR; } /* count required memory */ while (cur_swe !=NULL ) /* for each SWE */ { UINT8 swe_index = cur_swe->swe_id; /* ** If SWE is already running => MB already created => do nothing */ if (rvm_swe_array[swe_index].swe_state != SWE_RUNNING ) { for( mb_index = 0; mb_index < cur_swe->nb_requested_mb; mb_index++) /* for each mb */ { required_mem += cur_swe->swe_mem_bank[mb_index].mb_initial_param.size; } /* add the necessary stack sizes */ /* TO DO: add the stack size for host groups not yet started */ if( (cur_swe->swe_type == RVM_SWE_TYPE_3) || (cur_swe->swe_type == RVM_SWE_TYPE_4) ) /* || ((cur_swe->swe_type == RVM_SWE_TYPE_2) && (rvm_swe_array[swe_index].group_index == RVM_OWN_GROUP) )) */ { required_mem += rvm_swe_array[swe_index].swe_stack_size; required_mem += SYSTEM_TASK_MEM; /* only for type 3 & 4. A-M-E-N-D-E-D! */ } } cur_swe = cur_swe->next_swe; } /* type 2 group host system and stack mem. is catered for here */ for(i=0; i<cnt; i++) host_task_mem+=gd[i].stack_size; /* A-M-E-N-D-E-D! */ host_task_mem+=(cnt*SYSTEM_TASK_MEM); /* compare available memory and required memory (eventually, use a percentage to improve performances) */ if ((required_mem+host_task_mem) + used_mem > total_mem ) { /* A-M-E-N-D-E-D! */ RVM_TRACE_WARNING_PARAM("RVM: Memory required (incl. used): ", (UINT32)(required_mem+host_task_mem+ used_mem) ); RVM_TRACE_WARNING_PARAM("RVM: Total Memory available : ", (UINT32)total_mem); return RVM_MEMORY_ERR; } else{ return RVM_OK; } } /******************************************************************************* ** ** Function rvm_allocate_mem ** ** Description This function creates all the required memory banks or ** increases their size if needed, to start a SWE. ** ** Parameters: T_RVM_PROCESSING_SWE * appli: list of required SWEs with their parameters. ** ** Returns T_RVM_RETURN: RVM_OK if all allocations are successful, ** else RVM_MEMORY_ERR and it releases all the allocated memory. ** *******************************************************************************/ T_RVM_RETURN rvm_allocate_mb( T_RVM_PROCESSING_SWE * appli) { T_RVM_PROCESSING_SWE * cur_swe = appli; UINT8 mb_index; volatile T_RVM_RETURN rvm_ret_value = RVM_OK; /* for each SWE in the list */ while ((cur_swe != NULL ) && (rvm_ret_value == RVM_OK)) { UINT8 swe_index = cur_swe->swe_id; if (rvm_swe_array[swe_index].swe_state == SWE_NOT_STARTED) /* If the state is not SWE_RUNNING, then the MBs have to be created */ { for( mb_index = 0; mb_index < cur_swe->nb_requested_mb; mb_index++) /* for each mb */ { T_RVF_MB_PARAM mb_param; /* add the initial size */ mb_param.size = cur_swe->swe_mem_bank[mb_index].mb_initial_param.size; mb_param.watermark = cur_swe->swe_mem_bank[mb_index].mb_initial_param.watermark; /* create the mb */ if ( mb_param.size != 0) { /* create the mb */ if ( rvf_create_mb( cur_swe->swe_mem_bank[mb_index].mb_name, mb_param, &(cur_swe->bk_id_table[mb_index]) ) != RVF_OK) { /* if an error occurs */ rvm_ret_value = RVM_MEMORY_ERR; break; } else { cur_swe->nb_created_mb++; } } } } cur_swe = cur_swe->next_swe; /* process the next SWE */ } if (rvm_ret_value != RVM_OK) /* Something went wrong, should release all used memory */ { rvf_send_trace("RVM: Problem in memory bank creation !!!", 40, NULL_PARAM, RV_TRACE_LEVEL_WARNING, RVM_USE_ID ); if (rvm_delete_created_mb (appli) != RVM_OK) { rvf_send_trace("RVM: MB deleting error!!!", 25, NULL_PARAM, RV_TRACE_LEVEL_WARNING, RVM_USE_ID ); } } return rvm_ret_value; } /******************************************************************************* ** ** Function rvm_allocate_stack_buffer ** ** Description This function allocates a buffer for the stack of a new ** task created by RVM. ** ** Parameters: UINT32 stack_size: size of stack. ** T_RVF_BUFFER** stack_ptr: pointer to the allocated buffer. ** ** Returns T_RVM_RETURN: RVM_OK if all allocation is successful, ** else RVM_MEMORY_ERR. ** *******************************************************************************/ T_RVM_RETURN rvm_allocate_stack_buffer( UINT32 stack_size, T_RVF_BUFFER** stack_ptr ) { T_RVF_MB_PARAM mb_params; /* increase the size of the stack MB before allocating the new buffer */ if( rvf_get_mb_param( RVM_STACK_MB, &mb_params) != RV_OK) { return RVM_MEMORY_ERR; } mb_params.size += stack_size; mb_params.watermark += stack_size; if( rvf_set_mb_param( RVM_STACK_MB, &mb_params) != RV_OK) { return RVM_MEMORY_ERR; } if( rvf_get_buf( rvm_stack_mem_bank, stack_size, stack_ptr) == RVF_RED) { return RVM_MEMORY_ERR; } return RVM_OK; }