test public
Dependencies: HttpServer_snapshot_mbed-os
r_ospl.c
00001 /******************************************************************************* 00002 * DISCLAIMER 00003 * This software is supplied by Renesas Electronics Corporation and is only 00004 * intended for use with Renesas products. No other uses are authorized. This 00005 * software is owned by Renesas Electronics Corporation and is protected under 00006 * all applicable laws, including copyright laws. 00007 * THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING 00008 * THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT 00009 * LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE 00010 * AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED. 00011 * TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS 00012 * ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE 00013 * FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR 00014 * ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE 00015 * BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. 00016 * Renesas reserves the right, without notice, to make changes to this software 00017 * and to discontinue the availability of this software. By using this software, 00018 * you agree to the additional terms and conditions found by accessing the 00019 * following link: 00020 * http://www.renesas.com/disclaimer 00021 * Copyright (C) 2012 - 2015 Renesas Electronics Corporation. All rights reserved. 00022 *******************************************************************************/ 00023 /** 00024 * @file r_ospl.c 00025 * @brief OS Porting Layer. Functions not depended on any environment. 00026 * 00027 * $Module: OSPL $ $PublicVersion: 0.90 $ (=R_OSPL_VERSION) 00028 * $Rev: 35 $ 00029 * $Date:: 2014-04-15 21:38:18 +0900#$ 00030 */ 00031 00032 00033 /****************************************************************************** 00034 Includes <System Includes> , "Project Includes" 00035 ******************************************************************************/ 00036 #include "r_ospl.h" 00037 #include "iodefine.h" 00038 #if defined(TARGET_RZ_A1XX) 00039 #include "iobitmasks/cpg_iobitmask.h" 00040 #endif 00041 #include "r_ospl_private.h" 00042 #include "r_ospl_os_less_private.h" 00043 #include "mbed_critical.h" 00044 #if R_OSPL_IS_PREEMPTION 00045 #include "r_ospl_RTX_private.h" 00046 #endif 00047 #include "locking.h" 00048 #ifdef __ICCARM__ 00049 #include <intrinsics.h> 00050 #endif 00051 #ifdef __GNUC__ 00052 #if ! IS_MBED_USED 00053 #include "irq.h" 00054 #endif 00055 #endif 00056 #if R_OSPL_DEBUG_TOOL 00057 #include <stdio.h> 00058 #endif 00059 #ifndef R_OSPL_NDEBUG 00060 #include <string.h> 00061 #endif 00062 00063 00064 /****************************************************************************** 00065 Typedef definitions 00066 ******************************************************************************/ 00067 00068 /****************************************************************************** 00069 Macro definitions 00070 ******************************************************************************/ 00071 00072 /****************************************************************************** 00073 Imported global variables and functions (from other files) 00074 ******************************************************************************/ 00075 00076 /****************************************************************************** 00077 Exported global variables and functions (to be accessed by other files) 00078 ******************************************************************************/ 00079 00080 /****************************************************************************** 00081 Private global variables and functions 00082 ******************************************************************************/ 00083 00084 static void R_OSPL_TABLE_Search_Sub( const r_ospl_table_t *self, 00085 const void *Key, r_ospl_table_searched_t *out_Searched ); 00086 00087 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 00088 static r_ospl_error_t *R_OSPL_GetCurrentThreadError_Sub( r_ospl_if_not_t TypeOfIfNot ); 00089 #endif 00090 00091 00092 /** 00093 * @def R_OSPL_DEFAULT_DEBUG_THREAD_COUNT 00094 * @brief For until calling "R_OSPL_SET_DEBUG_WORK" 00095 * @par Parameters 00096 * None 00097 * @return None. 00098 */ 00099 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 00100 #define R_OSPL_DEFAULT_DEBUG_THREAD_COUNT 2 00101 #endif 00102 00103 00104 /** For until calling "R_OSPL_SET_DEBUG_WORK" */ 00105 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 00106 static r_ospl_table_block_t gs_thread_index_table_body[ R_OSPL_DEFAULT_DEBUG_THREAD_COUNT ]; 00107 #endif 00108 00109 00110 /** For until calling "R_OSPL_SET_DEBUG_WORK" */ 00111 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 00112 static r_ospl_error_t gs_error; 00113 #endif 00114 00115 00116 /** as <r_ospl_global_error_t> */ 00117 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 00118 00119 /* ->MISRA 8.7 : If not defined R_OSPL_ERROR_BREAK, this is referenced by only 1 function. */ /* ->SEC M2.2.1 */ 00120 static r_ospl_global_error_t gs_global_error = 00121 /* <-MISRA 8.7 */ /* <-SEC M2.2.1 */ 00122 { 00123 { /* .ThreadIndexTable */ 00124 gs_thread_index_table_body, /* .Area */ 00125 0, /* .Count */ 00126 R_OSPL_DEFAULT_DEBUG_THREAD_COUNT, /* .MaxCount */ 00127 NULL, /* .KeyCache */ 00128 0, /* .IndexCache */ 00129 0, /* .FirstFreeIndex */ 00130 #if R_OSPL_IS_PREEMPTION 00131 true /* .Is_T_Lock */ 00132 #endif 00133 }, 00134 &gs_error, /* .ErrorArray */ 00135 00136 #if R_OSPL_ERROR_BREAK 00137 0, /* .RaisedGlobalErrorID */ /* Necessary T-Lock */ 00138 0 /* .BreakGlobalErrorID */ 00139 #endif 00140 }; 00141 #endif 00142 00143 00144 /*********************************************************************** 00145 * Implement: R_OSPL_GetVersion 00146 ************************************************************************/ 00147 int32_t R_OSPL_GetVersion(void) 00148 { 00149 return R_OSPL_VERSION; 00150 } 00151 00152 00153 /*********************************************************************** 00154 * Implement: R_OSPL_IsPreemption 00155 ************************************************************************/ 00156 bool_t R_OSPL_IsPreemption(void) 00157 { 00158 return R_OSPL_IS_PREEMPTION; 00159 } 00160 00161 00162 /*********************************************************************** 00163 * Implement: R_OSPL_FLAG32_InitConst 00164 ************************************************************************/ 00165 void R_OSPL_FLAG32_InitConst( volatile r_ospl_flag32_t *const self ) 00166 { 00167 IF_DQ( self == NULL ) { 00168 goto fin; 00169 } 00170 00171 self->Flags = 0; 00172 00173 fin: 00174 return; 00175 } 00176 00177 00178 /*********************************************************************** 00179 * Implement: R_OSPL_FLAG32_Set 00180 ************************************************************************/ 00181 void R_OSPL_FLAG32_Set( volatile r_ospl_flag32_t *const self, bit_flags32_t const SetFlags ) 00182 { 00183 IF_DQ( self == NULL ) { 00184 goto fin; 00185 } 00186 00187 self->Flags |= SetFlags; 00188 00189 fin: 00190 return; 00191 } 00192 00193 00194 /*********************************************************************** 00195 * Implement: R_OSPL_FLAG32_Clear 00196 ************************************************************************/ 00197 void R_OSPL_FLAG32_Clear( volatile r_ospl_flag32_t *const self, bit_flags32_t const ClearFlags1 ) 00198 { 00199 IF_DQ( self == NULL ) { 00200 goto fin; 00201 } 00202 00203 self->Flags &= ~ClearFlags1; 00204 00205 fin: 00206 return; 00207 } 00208 00209 00210 /*********************************************************************** 00211 * Implement: R_OSPL_FLAG32_Get 00212 ************************************************************************/ 00213 bit_flags32_t R_OSPL_FLAG32_Get( volatile const r_ospl_flag32_t *const self ) 00214 { 00215 bit_flags32_t return_value; 00216 00217 IF_DQ( self == NULL ) { 00218 return_value = 0; 00219 goto fin; 00220 } 00221 00222 return_value = self->Flags; 00223 00224 fin: 00225 return return_value; 00226 } 00227 00228 00229 /*********************************************************************** 00230 * Implement: R_OSPL_FLAG32_GetAndClear 00231 ************************************************************************/ 00232 bit_flags32_t R_OSPL_FLAG32_GetAndClear( volatile r_ospl_flag32_t *const self ) 00233 { 00234 bit_flags32_t return_value; 00235 00236 IF_DQ( self == NULL ) { 00237 return_value = 0; 00238 goto fin; 00239 } 00240 00241 return_value = self->Flags; 00242 self->Flags = 0; 00243 00244 fin: 00245 return return_value; 00246 } 00247 00248 00249 /*********************************************************************** 00250 * Implement: R_OSPL_ASYNC_CopyExceptAThread 00251 ************************************************************************/ 00252 void R_OSPL_ASYNC_CopyExceptAThread( const r_ospl_async_t *const Source, 00253 r_ospl_async_t *const Destination ) 00254 { 00255 IF_DQ( Destination == NULL ) { 00256 goto fin; 00257 } 00258 IF_DQ( Source == NULL ) { 00259 goto fin; 00260 } 00261 00262 *Destination = *Source; 00263 Destination->A_Thread = NULL; 00264 00265 fin: 00266 return; 00267 } 00268 00269 00270 /*********************************************************************** 00271 * Implement: R_OSPL_EnableAllInterrupt 00272 ************************************************************************/ 00273 void R_OSPL_EnableAllInterrupt(void) 00274 { 00275 core_util_critical_section_exit(); 00276 } 00277 00278 00279 /*********************************************************************** 00280 * Implement: R_OSPL_DisableAllInterrupt 00281 ************************************************************************/ 00282 void R_OSPL_DisableAllInterrupt(void) 00283 { 00284 core_util_critical_section_enter(); 00285 } 00286 00287 00288 /*********************************************************************** 00289 * Implement: R_BSP_InterruptsEnable 00290 ************************************************************************/ 00291 void R_BSP_InterruptsEnable(void) 00292 { 00293 core_util_critical_section_exit(); 00294 } 00295 00296 00297 /*********************************************************************** 00298 * Implement: R_BSP_InterruptsDisable 00299 ************************************************************************/ 00300 void R_BSP_InterruptsDisable(void) 00301 { 00302 core_util_critical_section_enter(); 00303 } 00304 00305 00306 /*********************************************************************** 00307 * Implement: R_OSPL_LockChannel 00308 ************************************************************************/ 00309 errnum_t R_OSPL_LockChannel( int_fast32_t ChannelNum, int_fast32_t *out_ChannelNum, 00310 mcu_lock_t HardwareIndexMin, mcu_lock_t HardwareIndexMax ) 00311 { 00312 errnum_t e; 00313 bool_t is_success; 00314 mcu_lock_t hardware_index; 00315 00316 ASSERT_D( HardwareIndexMin <= HardwareIndexMax, e=E_OTHERS; goto fin ); 00317 00318 if ( ChannelNum == R_OSPL_UNLOCKED_CHANNEL ) { 00319 ASSERT_D( out_ChannelNum != NULL, e=E_OTHERS; goto fin ); 00320 00321 #if BSP_CFG_USER_LOCKING_ENABLED 00322 for ( hardware_index = HardwareIndexMin; hardware_index <= HardwareIndexMax; 00323 hardware_index += 1 ) { 00324 is_success = R_BSP_HardwareLock( hardware_index ); 00325 if ( is_success ) { 00326 break; 00327 } 00328 } 00329 IF ( hardware_index > HardwareIndexMax ) { 00330 e=E_FEW_ARRAY; 00331 goto fin; 00332 } 00333 #else 00334 e= R_OSPL_LockUnlockedChannel( out_ChannelNum, 00335 HardwareIndexMin, HardwareIndexMax ); 00336 IF(e) { 00337 goto fin; 00338 } 00339 out_ChannelNum = NULL; 00340 #endif 00341 } else { 00342 hardware_index = (mcu_lock_t)( HardwareIndexMin + ChannelNum ); 00343 00344 IF_D ( hardware_index < HardwareIndexMin || hardware_index > HardwareIndexMax ) { 00345 e=E_FEW_ARRAY; 00346 goto fin; 00347 } 00348 00349 is_success = R_BSP_HardwareLock( hardware_index ); 00350 IF ( ! is_success ) { 00351 e=E_ACCESS_DENIED; 00352 goto fin; 00353 } 00354 } 00355 00356 if ( out_ChannelNum != NULL ) { 00357 *out_ChannelNum = hardware_index - HardwareIndexMin; 00358 } 00359 00360 e=0; 00361 fin: 00362 return e; 00363 } 00364 00365 00366 /*********************************************************************** 00367 * Implement: R_OSPL_UnlockChannel 00368 ************************************************************************/ 00369 errnum_t R_OSPL_UnlockChannel( int_fast32_t ChannelNum, errnum_t e, 00370 mcu_lock_t HardwareIndexMin, mcu_lock_t HardwareIndexMax ) 00371 { 00372 bool_t is_success; 00373 mcu_lock_t hardware_index; 00374 00375 ASSERT_D( HardwareIndexMin <= HardwareIndexMax, e= R_OSPL_MergeErrNum( e, E_OTHERS ) ); 00376 00377 hardware_index = (mcu_lock_t)( HardwareIndexMin + ChannelNum ); 00378 00379 if ( hardware_index >= HardwareIndexMin && hardware_index <= HardwareIndexMax ) { 00380 is_success = R_BSP_HardwareUnlock( hardware_index ); 00381 IF ( ! is_success ) { 00382 e= R_OSPL_MergeErrNum( e, E_ACCESS_DENIED ); 00383 } 00384 } 00385 00386 return e; 00387 } 00388 00389 00390 /*********************************************************************** 00391 * Implement: R_OSPL_C_LOCK_InitConst 00392 ************************************************************************/ 00393 void R_OSPL_C_LOCK_InitConst( r_ospl_c_lock_t *const self ) 00394 { 00395 IF_DQ( self == NULL ) { 00396 goto fin; 00397 } 00398 00399 self->IsLocked = false; 00400 00401 fin: 00402 return; 00403 } 00404 00405 00406 /*********************************************************************** 00407 * Implement: R_OSPL_C_LOCK_Lock 00408 ************************************************************************/ 00409 errnum_t R_OSPL_C_LOCK_Lock( r_ospl_c_lock_t *const self ) 00410 { 00411 errnum_t e; 00412 00413 IF_DQ( self == NULL ) { 00414 e=E_OTHERS; 00415 goto fin; 00416 } 00417 00418 IF ( R_OSPL_THREAD_GetCurrentId() == NULL ) { /* Interrupt */ 00419 e = E_NOT_THREAD; 00420 R_OSPL_RaiseUnrecoverable( e ); 00421 goto fin; 00422 } 00423 00424 IF ( IS( self->IsLocked ) ) { 00425 e=E_ACCESS_DENIED; 00426 goto fin; 00427 } 00428 00429 self->IsLocked = true; 00430 00431 e=0; 00432 fin: 00433 return e; 00434 } 00435 00436 00437 /*********************************************************************** 00438 * Implement: R_OSPL_C_LOCK_Unlock 00439 ************************************************************************/ 00440 errnum_t R_OSPL_C_LOCK_Unlock( r_ospl_c_lock_t *const self ) 00441 { 00442 errnum_t e; 00443 00444 if ( self != NULL ) { 00445 00446 IF ( R_OSPL_THREAD_GetCurrentId() == NULL ) { /* Interrupt */ 00447 e = E_NOT_THREAD; 00448 R_OSPL_RaiseUnrecoverable( e ); 00449 goto fin; 00450 } 00451 00452 IF ( ! self->IsLocked ) { 00453 /* Check not unlock the object that was initialized by other thread */ 00454 e = E_ACCESS_DENIED; 00455 goto fin; 00456 } 00457 00458 self->IsLocked = false; 00459 } 00460 00461 e=0; 00462 fin: 00463 return e; 00464 } 00465 00466 00467 /*********************************************************************** 00468 * Implement: R_OSPL_I_LOCK_LockStub 00469 ************************************************************************/ 00470 bool_t R_OSPL_I_LOCK_LockStub( void *const self_ ) 00471 { 00472 R_IT_WILL_BE_NOT_CONST( self_ ); 00473 R_UNREFERENCED_VARIABLE( self_ ); 00474 return false; 00475 } 00476 00477 00478 /*********************************************************************** 00479 * Implement: R_OSPL_I_LOCK_UnlockStub 00480 ************************************************************************/ 00481 void R_OSPL_I_LOCK_UnlockStub( void *const self_ ) 00482 { 00483 R_IT_WILL_BE_NOT_CONST( self_ ); 00484 R_UNREFERENCED_VARIABLE( self_ ); 00485 } 00486 00487 00488 /*********************************************************************** 00489 * Implement: R_OSPL_I_LOCK_RequestFinalizeStub 00490 ************************************************************************/ 00491 void R_OSPL_I_LOCK_RequestFinalizeStub( void *const self_ ) 00492 { 00493 R_IT_WILL_BE_NOT_CONST( self_ ); 00494 R_UNREFERENCED_VARIABLE( self_ ); 00495 } 00496 00497 00498 /*********************************************************************** 00499 * Implement: R_OSPL_MEMORY_Barrier 00500 ************************************************************************/ 00501 void R_OSPL_MEMORY_Barrier(void) 00502 { 00503 /* ->QAC 1006 : asm */ 00504 __asm("DSB"); 00505 /* <-QAC 1006 */ 00506 } 00507 00508 00509 /*********************************************************************** 00510 * Implement: R_OSPL_InstructionSyncBarrier 00511 ************************************************************************/ 00512 void R_OSPL_InstructionSyncBarrier(void) 00513 { 00514 /* ->QAC 1006 : asm */ 00515 __asm("ISB"); 00516 /* <-QAC 1006 */ 00517 } 00518 00519 00520 /*********************************************************************** 00521 * Implement: R_OSPL_CALLER_Initialize 00522 ************************************************************************/ 00523 void R_OSPL_CALLER_Initialize( r_ospl_caller_t *const self, r_ospl_async_t *const Async, 00524 volatile void *const PointerToState, int_t const StateValueOfOnInterrupting, 00525 void *const I_Lock, const r_ospl_i_lock_vtable_t *const I_LockVTable ) 00526 { 00527 ASSERT_D( Async != NULL, R_NOOP() ); 00528 ASSERT_D( PointerToState != NULL, R_NOOP() ); 00529 IF_DQ( self == NULL ) {} 00530 else { 00531 self->Async = Async; 00532 self->PointerToState = (volatile int_fast32_t *) PointerToState; 00533 self->StateValueOfOnInterrupting = StateValueOfOnInterrupting; 00534 self->I_Lock = I_Lock; 00535 self->I_LockVTable = I_LockVTable; 00536 } 00537 00538 #ifndef R_OSPL_NDEBUG 00539 /* Set sentinel */ 00540 ASSERT_D( IS_ALL_BITS_NOT_SET( Async->Flags, R_F_OSPL_ASYNC_FLAGS_SENTINEL_MASK ), 00541 R_NOOP() ); 00542 ASSERT_D( IS_ALL_BITS_NOT_SET( R_F_OSPL_ASYNC_FLAGS_SENTINEL_VALUE, 00543 ~R_F_OSPL_ASYNC_FLAGS_SENTINEL_MASK ), R_NOOP() ); 00544 00545 Async->Flags |= R_F_OSPL_ASYNC_FLAGS_SENTINEL_VALUE; 00546 #endif 00547 } 00548 00549 00550 #if defined(TARGET_RZ_A1XX) 00551 /*********************************************************************** 00552 * Implement: R_OSPL_FTIMER_InitializeIfNot 00553 ************************************************************************/ 00554 errnum_t R_OSPL_FTIMER_InitializeIfNot( r_ospl_ftimer_spec_t *const out_Specification ) 00555 { 00556 /* ->SEC M1.11.1 : Can not const "is_initialized" because timing */ 00557 bool_t is_initialized; 00558 /* <-SEC M1.11.1 */ 00559 #if R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_MTU2_1_2 00560 enum { bits_CST1_CST2 = 0x06 }; 00561 #endif 00562 00563 /* ->QAC 0306 */ 00564 #if R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_OSTM0 00565 struct st_ostm *const reg_OSTM = &OSTM0; 00566 #elif R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_OSTM1 00567 struct st_ostm *const reg_OSTM = &OSTM1; 00568 #endif 00569 /* <-QAC 0306 */ 00570 00571 /* ->QAC 0306 */ 00572 #if R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_OSTM0 00573 R_OSPL_SET_TO_8_BIT_REGISTER( &CPG.STBCR5, CPG_STBCR5_MSTP51, 00574 CPG_STBCR5_MSTP51_SHIFT, 0 ); 00575 00576 #elif R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_OSTM1 00577 R_OSPL_SET_TO_8_BIT_REGISTER( &CPG.STBCR5, CPG_STBCR5_MSTP50, 00578 CPG_STBCR5_MSTP50_SHIFT, 0 ); 00579 00580 #elif R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_MTU2_1_2 00581 R_OSPL_SET_TO_8_BIT_REGISTER( &CPG.STBCR3, CPG_STBCR3_MSTP33, 00582 CPG_STBCR3_MSTP33_SHIFT, 0 ); 00583 #endif 00584 00585 #if R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_MTU2_1_2 00586 is_initialized = IS_ALL_BITS_NOT_SET( MTU2.TSTR, bits_CST1_CST2 ); 00587 #else 00588 is_initialized = ( (int_fast32_t) reg_OSTM->OSTMnTE == 0 ); 00589 #endif 00590 /* <-QAC 0306 */ 00591 00592 if ( IS( is_initialized ) ) { /* Integer Promotions */ 00593 #if R_OSPL_FTIMER_IS != R_OSPL_FTIMER_IS_MTU2_1_2 00594 enum { free_running_no_interrupt = 2 }; 00595 #endif 00596 00597 R_OSPL_DisableAllInterrupt(); 00598 00599 #if R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_MTU2_1_2 00600 { 00601 enum { external_clock_TCLKD = 0x07u }; 00602 00603 /* ->QAC 0306 */ 00604 00605 /* Channel 1 */ 00606 MTU2.TCR_1 = (uint8_t) external_clock_TCLKD; /* overflow of the timer2 */ 00607 MTU2.TMDR_1 = 0; 00608 MTU2.TIOR_1 = 0; 00609 MTU2.TIER_1 = 0; 00610 MTU2.TSR_1 = 0; 00611 MTU2.TCNT_1 = 0; 00612 00613 /* Channel 2 */ 00614 MTU2.TCR_2 = 0; /* 33MHz */ 00615 MTU2.TMDR_2 = 0; 00616 MTU2.TIOR_2 = 0; 00617 MTU2.TIER_2 = 0; 00618 MTU2.TSR_2 = 0; 00619 MTU2.TCNT_2 = 0; 00620 00621 /* Timer start */ 00622 /* MTU2.TSTR |= bits_CST1_CST2; */ 00623 { 00624 uint8_t const value = MTU2.TSTR; 00625 MTU2.TSTR = (uint8_t)( (uint_fast32_t) value | bits_CST1_CST2 ); 00626 } /* QAC 2100 */ 00627 00628 /* <-QAC 0306 */ 00629 } 00630 #else 00631 if ( (int_fast32_t) reg_OSTM->OSTMnTE == 0 ) { /* Integer Promotions */ 00632 reg_OSTM->OSTMnCTL = free_running_no_interrupt; 00633 reg_OSTM->OSTMnTS = 1; 00634 } 00635 #endif 00636 00637 R_OSPL_EnableAllInterrupt(); 00638 } 00639 00640 R_OSPL_FTIMER_GetSpecification( out_Specification ); 00641 00642 return 0; 00643 } 00644 00645 00646 /*********************************************************************** 00647 * Implement: R_OSPL_FTIMER_GetSpecification 00648 ************************************************************************/ 00649 void R_OSPL_FTIMER_GetSpecification( r_ospl_ftimer_spec_t *const out_Specification ) 00650 { 00651 if ( out_Specification != NULL ) { 00652 enum { msec_numerator = 1 }; /* SEC M1.10.1, QAC-3132 */ 00653 enum { msec_denominator = 33333 }; /* SEC M1.10.1, QAC-3132 */ 00654 static const uint32_t max_count = 0xFFFFFFFFu; /* SEC M1.10.1, QAC-3132 */ 00655 static const uint32_t extension_of_count = (1000 * msec_denominator) / msec_numerator; 00656 /* SEC M1.10.1, QAC-3132 */ 00657 00658 out_Specification->msec_Numerator = msec_numerator; 00659 out_Specification->msec_Denominator = msec_denominator; 00660 out_Specification->MaxCount = max_count; 00661 out_Specification->ExtensionOfCount = extension_of_count; 00662 } 00663 } 00664 00665 00666 /*********************************************************************** 00667 * Implement: R_OSPL_FTIMER_Get 00668 ************************************************************************/ 00669 uint32_t R_OSPL_FTIMER_Get(void) 00670 { 00671 #if R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_MTU2_1_2 00672 enum { num_16bit = 16 }; /* SEC M1.10.1, QAC-3132 */ 00673 /* ->QAC 0306 */ 00674 00675 uint32_t now_high = (uint32_t)(MTU2.TCNT_1); 00676 uint32_t not_low = (uint32_t)(MTU2.TCNT_2); 00677 00678 while( now_high != (uint32_t)(MTU2.TCNT_1) ) { 00679 /* If higher byte was changed while reading lower byte, re-read. */ 00680 now_high = (uint32_t)(MTU2.TCNT_1); 00681 not_low = (uint32_t)(MTU2.TCNT_2); 00682 } 00683 00684 return ( now_high << num_16bit ) | not_low; 00685 00686 /* <-QAC 0306 */ 00687 #else 00688 00689 /* ->QAC 0306 */ 00690 #if R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_OSTM0 00691 struct st_ostm *const reg_OSTM = &OSTM0; 00692 #elif R_OSPL_FTIMER_IS == R_OSPL_FTIMER_IS_OSTM1 00693 struct st_ostm *const reg_OSTM = &OSTM1; 00694 #endif 00695 /* <-QAC 0306 */ 00696 00697 ASSERT_R( reg_OSTM->OSTMnCMP == 0x0000000u, R_NOOP() ); 00698 /* If "OSTMnCMP != 0", OSTMnCNT is set from 0 to OSTMnCMP-1 */ 00699 00700 return reg_OSTM->OSTMnCNT; 00701 00702 #endif 00703 } 00704 #endif /* TARGET_RZ_A1XX */ 00705 00706 /*********************************************************************** 00707 * Implement: R_OSPL_FTIMER_IsPast 00708 ************************************************************************/ 00709 errnum_t R_OSPL_FTIMER_IsPast( const r_ospl_ftimer_spec_t *const ts, 00710 uint32_t const Now, uint32_t const TargetTime, bool_t *const out_IsPast ) 00711 { 00712 uint32_t const target_minus_now = TargetTime - Now; 00713 static const uint32_t minus_flag = 0x80000000u; 00714 errnum_t e; 00715 bool_t const is_past = IS_BIT_SET( target_minus_now, minus_flag ); 00716 00717 IF_DQ( ts == NULL ) { 00718 e=E_OTHERS; 00719 goto fin; 00720 } 00721 IF_DQ( out_IsPast == NULL ) { 00722 e=E_OTHERS; 00723 goto fin; 00724 } 00725 00726 if ( IS( is_past ) ) { 00727 uint32_t const now_minus_target = Now - TargetTime; 00728 00729 IF ( now_minus_target > ts->ExtensionOfCount ) { 00730 e=E_TIME_OUT; 00731 goto fin; 00732 } 00733 } 00734 00735 *out_IsPast = is_past; 00736 00737 e=0; 00738 fin: 00739 return e; 00740 } 00741 00742 00743 /*********************************************************************** 00744 * Implement: R_OSPL_TABLE_InitConst 00745 ************************************************************************/ 00746 void R_OSPL_TABLE_InitConst( r_ospl_table_t *const self, 00747 void *const Area, size_t const AreaByteSize, bool_t const Is_T_Lock ) 00748 { 00749 #if ! defined( R_OSPL_NDEBUG ) || R_OSPL_IS_PREEMPTION 00750 errnum_t e; 00751 #endif 00752 #if R_OSPL_IS_PREEMPTION 00753 bool_t is_lock = false; 00754 #endif 00755 00756 IF_DQ( self == NULL ) { 00757 #ifndef R_OSPL_NDEBUG 00758 e=E_OTHERS; 00759 #endif 00760 goto fin; 00761 } 00762 00763 #if R_OSPL_IS_PREEMPTION 00764 if ( IS( Is_T_Lock ) ) { 00765 if ( R_OSPL_THREAD_GetCurrentId() != NULL ) { /* If not interrrupt context */ 00766 e= R_OSPL_Start_T_Lock(); 00767 if(e!=0) { 00768 goto fin; 00769 } 00770 is_lock = true; /* T-Lock to "self" */ 00771 } 00772 } 00773 #endif 00774 00775 self->Area = Area; 00776 self->Count = 0; 00777 self->MaxCount = (int_fast32_t)( AreaByteSize / sizeof( r_ospl_table_block_t ) ); 00778 self->KeyCache = NULL; 00779 self->FirstFreeIndex = 0; 00780 #if R_OSPL_IS_PREEMPTION 00781 self->Is_T_Lock = Is_T_Lock; 00782 #else 00783 R_UNREFERENCED_VARIABLE( Is_T_Lock ); 00784 #endif 00785 00786 /* Set "self->Area[].NextFreeIndex" */ 00787 { 00788 r_ospl_table_block_t *const block_array = (r_ospl_table_block_t *) Area; 00789 int_fast32_t index; 00790 int_fast32_t const max_index = self->MaxCount - 1; 00791 00792 IF_DQ( block_array == NULL ) { 00793 #ifndef R_OSPL_NDEBUG 00794 e=E_OTHERS; 00795 #endif 00796 goto fin; 00797 } 00798 00799 for ( index = 0; index < max_index; index += 1 ) { 00800 block_array[ index ].NextFreeIndex = (int16_t)( index + 1 ); 00801 } 00802 block_array[ max_index ].NextFreeIndex = (int16_t) R_OSPL_TABLE_BLOCK_NO_NEXT; 00803 } 00804 00805 #ifndef R_OSPL_NDEBUG 00806 e=0; 00807 #endif 00808 fin: 00809 R_NOOP();/* for following all #if is false */ 00810 00811 #if R_OSPL_IS_PREEMPTION 00812 if ( IS( is_lock ) ) { 00813 R_OSPL_End_T_Lock(); 00814 } 00815 #endif 00816 #ifndef R_OSPL_NDEBUG 00817 if ( e != 0 ) { 00818 R_DebugBreak( NULL, e ); 00819 } 00820 #endif 00821 } 00822 00823 00824 /*********************************************************************** 00825 * Implement: R_OSPL_TABLE_GetIndex 00826 ************************************************************************/ 00827 errnum_t R_OSPL_TABLE_GetIndex( r_ospl_table_t *const self, const void *const Key, 00828 int_fast32_t *const out_Index, r_ospl_if_not_t const TypeOfIfNot ) 00829 { 00830 errnum_t e; 00831 #if R_OSPL_IS_PREEMPTION 00832 bool_t is_lock = false; 00833 #endif 00834 00835 IF_DQ( self == NULL ) { 00836 e=E_OTHERS; 00837 goto fin; 00838 } 00839 IF_DQ( out_Index == NULL ) { 00840 e=E_OTHERS; 00841 goto fin; 00842 } 00843 00844 #if R_OSPL_IS_PREEMPTION 00845 if ( IS( self->Is_T_Lock ) ) { 00846 if ( R_OSPL_THREAD_GetCurrentId() != NULL ) { /* If not interrrupt context */ 00847 e= R_OSPL_Start_T_Lock(); 00848 if(e!=0) { 00849 goto fin; 00850 } 00851 is_lock = true; /* T-Lock to "self" */ 00852 } 00853 } 00854 #endif 00855 00856 00857 if ( (Key == self->KeyCache) && (self->Count >= 1) ) { 00858 *out_Index = self->IndexCache; 00859 } else { 00860 r_ospl_table_searched_t searched; 00861 r_ospl_table_block_t *const block_array = self->Area; 00862 int_fast32_t found_index; 00863 00864 R_OSPL_TABLE_Search_Sub( self, Key, &searched ); 00865 00866 if ( ! searched.IsFound ) { 00867 int_fast32_t so_index; /* sorted_key_index */ 00868 int_fast32_t first_index; /* FirstFreeIndex */ 00869 00870 if ( TypeOfIfNot == R_OSPL_ALLOCATE_IF_NOT ) { 00871 if ( self->Count == self->MaxCount ) { 00872 e = E_FEW_ARRAY; 00873 goto fin; 00874 } 00875 00876 /* Insert and Set "block_array[ searched.SortedKeyIndex ].Key" */ 00877 for ( so_index = self->Count - 1; 00878 so_index >= searched.SortedKeyIndex; 00879 so_index -= 1 ) { 00880 block_array[ so_index + 1 ].Key = block_array[ so_index ].Key; 00881 block_array[ so_index + 1 ].Index = block_array[ so_index ].Index; 00882 } 00883 block_array[ searched.SortedKeyIndex ].Key = Key; 00884 self->Count += 1; 00885 00886 /* Set "block_array[ searched.SortedKeyIndex ].Index" */ 00887 first_index = self->FirstFreeIndex; 00888 block_array[ searched.SortedKeyIndex ].Index = (int16_t) first_index; 00889 self->FirstFreeIndex = block_array[ first_index ].NextFreeIndex; 00890 block_array[ first_index ].NextFreeIndex = R_OSPL_TABLE_BLOCK_USED; 00891 00892 } else if ( TypeOfIfNot == R_OSPL_ERROR_IF_NOT ) { 00893 e = E_NOT_FOUND_SYMBOL; 00894 goto fin; 00895 } else { /* TypeOfIfNot == R_OSPL_DO_NOTHING_IF_NOT */ 00896 e = 0; 00897 goto fin; 00898 } 00899 /* Don't use "IF", Because this function called from "IF". */ 00900 } 00901 00902 self->KeyCache = Key; 00903 found_index = block_array[ searched.SortedKeyIndex ].Index; 00904 self->IndexCache = found_index; 00905 *out_Index = found_index; 00906 } 00907 00908 e=0; 00909 fin: 00910 #if R_OSPL_IS_PREEMPTION 00911 if ( IS( is_lock ) ) { 00912 R_OSPL_End_T_Lock(); 00913 } 00914 #endif 00915 return e; 00916 } 00917 00918 00919 /*********************************************************************** 00920 * Implement: R_OSPL_TABLE_Free 00921 ************************************************************************/ 00922 void R_OSPL_TABLE_Free( r_ospl_table_t *const self, const void *const Key ) 00923 { 00924 #if ! defined( R_OSPL_NDEBUG ) || R_OSPL_IS_PREEMPTION 00925 errnum_t e; 00926 #endif 00927 #if R_OSPL_IS_PREEMPTION 00928 bool_t is_lock = false; 00929 #endif 00930 r_ospl_table_searched_t searched; 00931 00932 IF_DQ( self == NULL ) { 00933 #ifndef R_OSPL_NDEBUG 00934 e=0; 00935 #endif 00936 goto fin; 00937 } 00938 00939 #if R_OSPL_IS_PREEMPTION 00940 if ( R_OSPL_THREAD_GetCurrentId() != NULL ) { /* If not interrrupt context */ 00941 e= R_OSPL_Start_T_Lock(); 00942 if(e!=0) { 00943 goto fin; 00944 } 00945 is_lock = true; /* T-Lock to "gs_global_error" */ 00946 } 00947 #endif 00948 00949 R_OSPL_TABLE_Search_Sub( self, Key, &searched ); 00950 00951 if ( IS( searched.IsFound ) ) { 00952 r_ospl_table_block_t *const block_array = self->Area; 00953 int_fast32_t so_index; /* sorted_key_index */ 00954 int_fast32_t first_index; /* FirstFreeIndex */ 00955 int_fast32_t const count_ = self->Count; /* _ is for MISRA 5.6 */ 00956 00957 /* Set "FirstFreeIndex", ".NextFreeIndex" */ 00958 first_index = self->FirstFreeIndex; 00959 self->FirstFreeIndex = block_array[ searched.SortedKeyIndex ].Index; 00960 block_array[ self->FirstFreeIndex ].NextFreeIndex = (int16_t) first_index; 00961 00962 /* Remove one "r_ospl_table_block_t" */ 00963 /* Set "self->KeyCache" */ 00964 if ( searched.SortedKeyIndex < count_ ) { 00965 for ( so_index = searched.SortedKeyIndex; so_index < count_ ; so_index += 1 ) { 00966 block_array[ so_index ].Key = block_array[ so_index + 1 ].Key; 00967 block_array[ so_index ].Index = block_array[ so_index + 1 ].Index; 00968 } 00969 self->KeyCache = block_array[ searched.SortedKeyIndex ].Key; 00970 self->IndexCache = block_array[ searched.SortedKeyIndex ].Index; 00971 } else if ( searched.SortedKeyIndex > 0 ) { /* searched.SortedKeyIndex >= 1 */ 00972 self->KeyCache = block_array[ searched.SortedKeyIndex - 1 ].Key; 00973 self->IndexCache = block_array[ searched.SortedKeyIndex - 1 ].Index; 00974 } else { 00975 self->KeyCache = NULL; 00976 } 00977 self->Count -= 1; 00978 } 00979 00980 #if ! defined( R_OSPL_NDEBUG ) 00981 e=0; 00982 #endif 00983 fin: 00984 R_NOOP();/* for following all #if is false */ 00985 00986 #if R_OSPL_IS_PREEMPTION 00987 if ( IS( is_lock ) ) { 00988 R_OSPL_End_T_Lock(); 00989 } 00990 #endif 00991 #ifndef R_OSPL_NDEBUG 00992 if ( e != 0 ) { 00993 R_DebugBreak( NULL, e ); 00994 } 00995 #endif 00996 } 00997 00998 00999 /*********************************************************************** 01000 * Implement: R_OSPL_TABLE_Search_Sub 01001 ************************************************************************/ 01002 static void R_OSPL_TABLE_Search_Sub( const r_ospl_table_t *const self, 01003 const void *const Key, r_ospl_table_searched_t *const out_Searched ) 01004 { 01005 int_fast32_t left; 01006 int_fast32_t right; 01007 int_fast32_t middle; 01008 /* ->QAC 0306 : Sort by pointer value */ 01009 uintptr_t const target_key = (uintptr_t) Key; 01010 /* <-QAC 0306 */ 01011 uintptr_t middle_key; 01012 enum { num_2 = 2 }; /* SEC M1.10.1, QAC-3132 */ 01013 r_ospl_table_block_t *array; 01014 01015 IF_DQ( self == NULL ) { 01016 goto fin; 01017 } 01018 IF_DQ( out_Searched == NULL ) { 01019 goto fin; 01020 } 01021 01022 array = self->Area; 01023 01024 01025 if ( self->Count == 0 ) { 01026 out_Searched->SortedKeyIndex = 0; 01027 out_Searched->IsFound = false; 01028 } else { 01029 left = 0; 01030 right = self->Count - 1; 01031 01032 while ( (right - left) >= num_2 ) { 01033 middle = (int_fast32_t)( (uint_fast32_t)( right + left ) / num_2 ); 01034 /* ->QAC 0306 : Sort by pointer value */ 01035 middle_key = (uintptr_t) array[ middle ].Key; 01036 /* <-QAC 0306 */ 01037 01038 if ( target_key == middle_key ) { 01039 out_Searched->SortedKeyIndex = middle; 01040 out_Searched->IsFound = true; 01041 goto fin; 01042 } else if ( target_key < middle_key ) { 01043 right = (int_fast32_t)( middle - 1 ); 01044 } else { 01045 left = (int_fast32_t)( middle + 1 ); 01046 } 01047 } 01048 01049 /* ->QAC 0306 : Sort by pointer value */ 01050 if ( target_key == (uintptr_t) array[ left ].Key ) { 01051 out_Searched->SortedKeyIndex = left; 01052 out_Searched->IsFound = true; 01053 } else if ( target_key == (uintptr_t) array[ right ].Key ) { 01054 out_Searched->SortedKeyIndex = right; 01055 out_Searched->IsFound = true; 01056 } else if ( target_key < (uintptr_t) array[ left ].Key ) { 01057 out_Searched->SortedKeyIndex = left; 01058 out_Searched->IsFound = false; 01059 } else if ( target_key > (uintptr_t) array[ right ].Key ) { 01060 out_Searched->SortedKeyIndex = right + 1; 01061 out_Searched->IsFound = false; 01062 } else { 01063 out_Searched->SortedKeyIndex = right; 01064 out_Searched->IsFound = false; 01065 } 01066 /* <-QAC 0306 */ 01067 } 01068 01069 fin: 01070 return; 01071 } 01072 01073 01074 /*********************************************************************** 01075 * Implement: R_OSPL_TABLE_Print 01076 ************************************************************************/ 01077 #if R_OSPL_DEBUG_TOOL 01078 void R_OSPL_TABLE_Print( r_ospl_table_t *const self ) 01079 { 01080 int_fast32_t so_index; /* sorted_key_index */ 01081 int_fast32_t index; 01082 r_ospl_table_block_t *const array = self->Area; 01083 01084 printf( "R_OSPL_TABLE_Print: r_ospl_table_t 0x%08X\n", (uintptr_t) self ); 01085 printf( " .Count = %d\n", self->Count ); 01086 for ( so_index = 0; so_index < self->Count; so_index += 1 ) { 01087 printf( " .Area[%d].Key, Index = 0x%08X, %d\n", 01088 so_index, (uintptr_t) array[ so_index ].Key, array[ so_index ].Index ); 01089 } 01090 printf( " .FirstFreeIndex = %d\n", self->FirstFreeIndex ); 01091 for ( index = 0; index < self->MaxCount; index += 1 ) { 01092 printf( " .Area[%d].NextFreeIndex = %d\n", index, array[ index ].NextFreeIndex ); 01093 } 01094 printf( " %d = R_OSPL_TABLE_BLOCK_NO_NEXT\n", R_OSPL_TABLE_BLOCK_NO_NEXT ); 01095 printf( " %d = R_OSPL_TABLE_BLOCK_USED\n", R_OSPL_TABLE_BLOCK_USED ); 01096 } 01097 #endif 01098 01099 01100 /*********************************************************************** 01101 * Implement: R_OSPL_CallInterruptCallback 01102 ************************************************************************/ 01103 void R_OSPL_CallInterruptCallback( const r_ospl_caller_t *const self, 01104 const r_ospl_interrupt_t *const InterruptSource ) 01105 { 01106 errnum_t e; 01107 r_ospl_async_t *async; 01108 #if ! R_OSPL_IS_PREEMPTION 01109 r_ospl_master_t *const gs_master = R_OSPL_GetPrivateContext(); 01110 r_ospl_thread_def_t *current_thread = NULL; /* NULL is for avoid QAC 3353 */ 01111 #endif 01112 #if R_OSPL_ERROR_BREAK 01113 static int_fast32_t gs_nested_interrupt_level = 0; 01114 #endif 01115 01116 #if R_OSPL_ERROR_BREAK 01117 gs_nested_interrupt_level += 1; 01118 #endif 01119 01120 #if ! R_OSPL_IS_PREEMPTION 01121 IF_DQ( gs_master == NULL ) { 01122 e=E_OTHERS; 01123 goto fin; 01124 } 01125 01126 #if R_OSPL_CPU_LOAD 01127 e= gs_master->IdleCallback( R_OSPL_INTERRUPT_START ); 01128 IF(e) { 01129 goto fin; 01130 } 01131 #endif 01132 01133 current_thread = gs_master->CurrentThread; 01134 #endif 01135 01136 IF_DQ( self == NULL ) { 01137 e=E_OTHERS; 01138 goto fin; 01139 } 01140 IF_DQ( self->Async == NULL ) { 01141 e=E_OTHERS; 01142 goto fin; 01143 } 01144 01145 async = self->Async; 01146 01147 ASSERT_D( ( async->Flags & R_F_OSPL_ASYNC_FLAGS_SENTINEL_MASK ) == 01148 R_F_OSPL_ASYNC_FLAGS_SENTINEL_VALUE, e=E_OTHERS; goto fin ); 01149 /* If failed, memory area of "Async" variable was overwritten by other variable. */ 01150 /* Reason of failed may be not disabled interrupt */ 01151 /* or not called "*_I_LOCK_Unlock()" disabling interrupt by "*_I_LOCK_Disable()". */ 01152 01153 IF_DQ( self->PointerToState == NULL ) { 01154 e=E_OTHERS; 01155 goto fin; 01156 } 01157 IF_DQ( async->InterruptCallback == NULL ) { 01158 e=E_OTHERS; 01159 goto fin; 01160 } 01161 01162 #if ! R_OSPL_IS_PREEMPTION 01163 gs_master->CurrentThread = NULL; /* Interrupt */ 01164 #endif 01165 01166 *self->PointerToState = self->StateValueOfOnInterrupting; 01167 01168 01169 01170 e= async->InterruptCallback( InterruptSource, self ); /* Main of callback */ 01171 01172 01173 01174 if ( e != 0 ) { 01175 if ( async->ReturnValue == 0 ) { 01176 async->ReturnValue = e; 01177 } 01178 R_OSPL_CLEAR_ERROR(); 01179 } 01180 01181 e=0; 01182 fin: 01183 #if ! R_OSPL_IS_PREEMPTION 01184 IF_DQ ( gs_master == NULL ) {} 01185 else { 01186 gs_master->CurrentThread = current_thread; 01187 01188 #if R_OSPL_CPU_LOAD 01189 { 01190 errnum_t ee; 01191 01192 ee= gs_master->IdleCallback( R_OSPL_INTERRUPT_END ); 01193 e= R_OSPL_MergeErrNum( e, ee ); 01194 } 01195 #endif 01196 } 01197 #endif 01198 01199 01200 #if R_OSPL_ERROR_BREAK 01201 gs_nested_interrupt_level -= 1; 01202 01203 if ( gs_nested_interrupt_level == 0 ) { 01204 if ( gs_master != NULL ) { 01205 current_thread = gs_master->CurrentThread; 01206 gs_master->CurrentThread = NULL; 01207 } 01208 01209 01210 R_DEBUG_BREAK_IF_ERROR(); 01211 01212 01213 if ( gs_master != NULL ) { 01214 gs_master->CurrentThread = current_thread; 01215 } 01216 } 01217 #endif 01218 R_UNREFERENCED_VARIABLE( e ); 01219 } 01220 01221 01222 /*********************************************************************** 01223 * Implement: R_OSPL_SetErrNum 01224 ************************************************************************/ 01225 #if R_OSPL_TLS_ERROR_CODE 01226 void R_OSPL_SetErrNum( errnum_t const e ) 01227 { 01228 r_ospl_error_t *err; 01229 01230 if ( e != 0 ) { 01231 01232 err = R_OSPL_GetCurrentThreadError_Sub( R_OSPL_ALLOCATE_IF_NOT ); 01233 01234 if ( err != NULL ) { 01235 if ( err->ErrNum == 0 ) { 01236 err->ErrNum = e; 01237 } 01238 } 01239 } 01240 } 01241 #endif 01242 01243 01244 /*********************************************************************** 01245 * Implement: R_OSPL_GetErrNum 01246 ************************************************************************/ 01247 #if R_OSPL_TLS_ERROR_CODE 01248 errnum_t R_OSPL_GetErrNum(void) 01249 { 01250 errnum_t e; 01251 r_ospl_error_t *err; 01252 01253 err = R_OSPL_GetCurrentThreadError_Sub( R_OSPL_ALLOCATE_IF_NOT ); 01254 01255 if ( err != NULL ) { 01256 e = err->ErrNum; 01257 } else { 01258 e = E_NO_DEBUG_TLS; 01259 } 01260 01261 return e; 01262 } 01263 #endif 01264 01265 01266 /*********************************************************************** 01267 * Implement: R_OSPL_CLEAR_ERROR 01268 ************************************************************************/ 01269 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 01270 void R_OSPL_CLEAR_ERROR(void) 01271 { 01272 r_ospl_error_t *err; 01273 01274 err = R_OSPL_GetCurrentThreadError_Sub( R_OSPL_DO_NOTHING_IF_NOT ); 01275 01276 if ( err != NULL ) { 01277 #if R_OSPL_ERROR_BREAK 01278 err->IsError = false; 01279 #endif 01280 01281 #if R_OSPL_TLS_ERROR_CODE 01282 err->ErrNum = 0; 01283 #endif 01284 } 01285 } 01286 #endif 01287 01288 01289 /** 01290 * @brief Function part of error break 01291 * 01292 * @par Parameters 01293 * None 01294 * @return None. 01295 */ 01296 #if R_OSPL_ERROR_BREAK 01297 static bool_t R_OSPL_OnRaisingError_Sub( const char_t *const FilePath, 01298 int_fast32_t const LineNum ); /* QAC-3450 */ 01299 static bool_t R_OSPL_OnRaisingError_Sub( const char_t *const FilePath, 01300 int_fast32_t const LineNum ) 01301 { 01302 #if ! defined( R_OSPL_NDEBUG ) || R_OSPL_IS_PREEMPTION 01303 errnum_t e; 01304 #endif 01305 bool_t is_break = false; 01306 #if R_OSPL_IS_PREEMPTION 01307 bool_t is_lock = false; 01308 #endif 01309 r_ospl_error_t *err; 01310 01311 01312 err = R_OSPL_GetCurrentThreadError_Sub( R_OSPL_ALLOCATE_IF_NOT ); 01313 01314 01315 if ( err != NULL ) { 01316 if ( IS( err->IsError ) ) { 01317 is_break = false; 01318 } else { 01319 #if R_OSPL_IS_PREEMPTION 01320 if ( R_OSPL_THREAD_GetCurrentId() != NULL ) { /* If not interrrupt context */ 01321 e= R_OSPL_Start_T_Lock(); 01322 if(e!=0) { 01323 goto fin; 01324 } 01325 is_lock = true; /* T-Lock to "gs_global_error" */ 01326 } 01327 #endif 01328 01329 gs_global_error.RaisedGlobalErrorID ++; 01330 is_break = ( gs_global_error.RaisedGlobalErrorID == 01331 gs_global_error.BreakGlobalErrorID ); 01332 01333 err->IsError = true; 01334 err->ErrorID = gs_global_error.RaisedGlobalErrorID; 01335 err->FilePath = FilePath; 01336 err->LineNum = LineNum; 01337 } 01338 } 01339 01340 #ifndef R_OSPL_NDEBUG 01341 e=0; 01342 #endif 01343 #if R_OSPL_IS_PREEMPTION 01344 fin: 01345 if ( IS( is_lock ) ) { 01346 R_OSPL_End_T_Lock(); 01347 } 01348 #endif 01349 #ifndef R_OSPL_NDEBUG 01350 if ( e != 0 ) { 01351 R_DebugBreak( NULL, e ); 01352 } 01353 #endif 01354 return is_break; 01355 } 01356 #endif 01357 01358 01359 /*********************************************************************** 01360 * Implement: R_OSPL_OnRaisingErrorForMISRA 01361 ************************************************************************/ 01362 #if R_OSPL_ERROR_BREAK 01363 bool_t R_OSPL_OnRaisingErrorForMISRA( bool_t const Condition, const char_t *const File, 01364 int_t const Line ) 01365 { 01366 if ( IS( Condition ) ) { 01367 if ( R_OSPL_OnRaisingError_Sub( File, Line ) != 0 ) { 01368 R_DebugBreak( File, Line ); 01369 } 01370 } 01371 return Condition; 01372 } 01373 #endif 01374 01375 01376 /** 01377 * @brief Function part of <R_DEBUG_BREAK_IF_ERROR> 01378 * 01379 * @par Parameters 01380 * None 01381 * @return None. 01382 */ 01383 #if R_OSPL_ERROR_BREAK 01384 void R_OSPL_DebugBreakIfError( const char_t *const File, int_t const Line ) 01385 { 01386 r_ospl_error_t *err; 01387 01388 err = R_OSPL_GetCurrentThreadError_Sub( R_OSPL_DO_NOTHING_IF_NOT ); 01389 01390 if ( err != NULL && err->IsError ) { 01391 /* See the value of "err->ErrorID" in watch window. */ 01392 /* Call R_OSPL_SET_BREAK_ERROR_ID( N ); at main function. */ 01393 printf( "<ERROR error_ID=\"0x%X\" file=\"%s(%d)\"/>\n", 01394 err->ErrorID, err->FilePath, err->LineNum ); 01395 R_DebugBreak( File, Line ); 01396 } 01397 01398 R_OSPL_CLEAR_ERROR(); 01399 } 01400 #endif 01401 01402 01403 /*********************************************************************** 01404 * Implement: R_OSPL_GET_ERROR_ID 01405 ************************************************************************/ 01406 #if R_OSPL_ERROR_BREAK 01407 int_fast32_t R_OSPL_GET_ERROR_ID(void) 01408 { 01409 return gs_global_error.RaisedGlobalErrorID; 01410 } 01411 #endif 01412 01413 01414 /*********************************************************************** 01415 * Implement: R_OSPL_SET_BREAK_ERROR_ID 01416 ************************************************************************/ 01417 #if R_OSPL_ERROR_BREAK 01418 void R_OSPL_SET_BREAK_ERROR_ID( int_fast32_t const ErrorID ) 01419 { 01420 #ifndef R_OSPL_NDEBUG 01421 if ( gs_global_error.BreakGlobalErrorID != ErrorID ) { 01422 printf( ">R_OSPL_SET_BREAK_ERROR_ID( %d );\n", ErrorID ); 01423 } 01424 #endif 01425 01426 gs_global_error.BreakGlobalErrorID = ErrorID; 01427 } 01428 #endif 01429 01430 01431 /*********************************************************************** 01432 * Implement: R_OSPL_GetCurrentThreadError 01433 ************************************************************************/ 01434 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 01435 r_ospl_error_t *R_OSPL_GetCurrentThreadError(void) 01436 { 01437 return R_OSPL_GetCurrentThreadError_Sub( R_OSPL_ALLOCATE_IF_NOT ); 01438 } 01439 #endif 01440 01441 01442 /** 01443 * @brief GetCurrentThreadError 01444 * 01445 * @param TypeOfIfNot <r_ospl_if_not_t> 01446 * @return Error information of current thread 01447 */ 01448 #if R_OSPL_ERROR_BREAK || R_OSPL_TLS_ERROR_CODE 01449 static r_ospl_error_t *R_OSPL_GetCurrentThreadError_Sub( r_ospl_if_not_t const TypeOfIfNot ) 01450 { 01451 errnum_t e; 01452 int_fast32_t index; 01453 r_ospl_error_t *err = NULL; 01454 r_ospl_thread_id_t th; /* QAC 3441 */ 01455 01456 index = R_OSPL_NO_INDEX; 01457 01458 th = R_OSPL_THREAD_GetCurrentId(); 01459 e= R_OSPL_TABLE_GetIndex( &gs_global_error.ThreadIndexTable, th, &index, TypeOfIfNot ); 01460 if ( e == E_FEW_ARRAY ) { 01461 #ifndef R_OSPL_NDEBUG 01462 if ( gs_global_error.ThreadIndexTable.Area == gs_thread_index_table_body ) { 01463 e = E_NO_DEBUG_TLS; 01464 } 01465 #endif 01466 goto fin; 01467 } 01468 if ( e != 0 ) { 01469 goto fin; 01470 } 01471 01472 if ( index != R_OSPL_NO_INDEX ) { 01473 IF_DQ( gs_global_error.ErrorArray == NULL ) { 01474 #ifndef R_OSPL_NDEBUG 01475 e=E_OTHERS; 01476 #endif 01477 goto fin; 01478 } 01479 IF_DQ( index < -1 ) { 01480 #ifndef R_OSPL_NDEBUG 01481 e=E_OTHERS; 01482 #endif 01483 goto fin; 01484 } 01485 01486 err = &gs_global_error.ErrorArray[ index ]; 01487 } 01488 01489 #ifndef R_OSPL_NDEBUG 01490 e=0; 01491 #endif 01492 fin: 01493 #ifndef R_OSPL_NDEBUG 01494 if ( e != 0 ) { 01495 R_DebugBreak( NULL, e ); 01496 /* If e == 2 (E_FEW_ARRAY), Set big work area by "R_OSPL_SET_DEBUG_WORK". */ 01497 /* If e == 29 (E_NO_DEBUG_TLS), Call "R_OSPL_SET_DEBUG_WORK". */ 01498 } 01499 #endif 01500 01501 return err; 01502 } 01503 #endif 01504 01505 01506 /*********************************************************************** 01507 * Implement: R_OSPL_SET_DEBUG_WORK 01508 ************************************************************************/ 01509 #if R_OSPL_ERROR_BREAK 01510 void R_OSPL_SET_DEBUG_WORK( void *const WorkArea, uint32_t const WorkAreaSize ) 01511 { 01512 errnum_t e; 01513 int_fast32_t count = WorkAreaSize / R_OSPL_DEBUG_WORK_1_SIZE; 01514 uint8_t *work = WorkArea; 01515 r_ospl_table_block_t *thread_index_array; 01516 r_ospl_error_t *error_array; 01517 int_fast32_t index; 01518 #if R_OSPL_IS_PREEMPTION 01519 bool_t is_lock = false; 01520 #endif 01521 01522 #if R_OSPL_IS_PREEMPTION 01523 if ( R_OSPL_THREAD_GetCurrentId() != NULL ) { /* If not interrrupt context */ 01524 e= R_OSPL_Start_T_Lock(); 01525 if(e!=0) { 01526 goto fin; 01527 } 01528 is_lock = true; /* T-Lock to "gs_global_error" */ 01529 } 01530 #endif 01531 01532 01533 if ( gs_global_error.ThreadIndexTable.Area != gs_thread_index_table_body ) { 01534 e = E_ACCESS_DENIED; 01535 goto fin; 01536 } 01537 01538 thread_index_array = (r_ospl_table_block_t *) &work[0]; 01539 error_array = (r_ospl_error_t *) &thread_index_array[ count ]; 01540 ASSERT_D( (uint8_t *) &error_array[ count ] <= &work[ WorkAreaSize ], e=E_FEW_ARRAY; goto fin ); 01541 01542 R_OSPL_TABLE_InitConst( &gs_global_error.ThreadIndexTable, 01543 thread_index_array, count * sizeof( thread_index_array[0] ), true ); 01544 01545 e= R_OSPL_TABLE_GetIndex( &gs_global_error.ThreadIndexTable, 01546 gs_thread_index_table_body[0].Key, &index, R_OSPL_ALLOCATE_IF_NOT ); 01547 if(e!=0) { 01548 goto fin; 01549 } 01550 01551 gs_global_error.ErrorArray = error_array; 01552 gs_global_error.ErrorArray[ index ] = gs_error; 01553 01554 #ifndef R_OSPL_NDEBUG 01555 memset( gs_thread_index_table_body, 0xFE, sizeof(gs_thread_index_table_body) ); 01556 memset( &gs_error, 0xFE, sizeof(gs_error) ); 01557 #endif 01558 01559 e=0; 01560 fin: 01561 #if R_OSPL_IS_PREEMPTION 01562 if ( IS( is_lock ) ) { 01563 R_OSPL_End_T_Lock(); 01564 } 01565 #endif 01566 #ifndef R_OSPL_NDEBUG 01567 if ( e != 0 ) { 01568 R_DebugBreak( NULL, e ); 01569 } 01570 #endif 01571 } 01572 #endif 01573 01574 01575 /*********************************************************************** 01576 * Implement: R_OSPL_MODIFY_THREAD_LOCKED_COUNT 01577 ************************************************************************/ 01578 #if R_OSPL_ERROR_BREAK && R_OSPL_IS_PREEMPTION 01579 void R_OSPL_MODIFY_THREAD_LOCKED_COUNT( int_fast32_t Plus ) 01580 { 01581 r_ospl_error_t *err; 01582 01583 err = R_OSPL_GetCurrentThreadError_Sub( R_OSPL_ALLOCATE_IF_NOT ); 01584 01585 if ( err != NULL ) { 01586 err->ThreadLockedCount += Plus; 01587 } 01588 } 01589 #endif 01590 01591 01592 /*********************************************************************** 01593 * Implement: R_OSPL_GET_THREAD_LOCKED_COUNT 01594 ************************************************************************/ 01595 #if R_OSPL_ERROR_BREAK && R_OSPL_IS_PREEMPTION 01596 int_fast32_t R_OSPL_GET_THREAD_LOCKED_COUNT(void) 01597 { 01598 int_fast32_t count; 01599 r_ospl_error_t *err; 01600 01601 err = R_OSPL_GetCurrentThreadError_Sub( R_OSPL_ALLOCATE_IF_NOT ); 01602 01603 if ( err != NULL ) { 01604 count = err->ThreadLockedCount; 01605 } else { 01606 count = 0; 01607 } 01608 01609 return count; 01610 } 01611 #endif 01612 01613
Generated on Wed Jul 13 2022 05:33:36 by 1.7.2