⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 semihost.c

📁 realview22.rar
💻 C
📖 第 1 页 / 共 5 页
字号:
   if (osstate == NULL) {
      Hostif_RaiseError(hostif,"OS_Init can't allocate state\n");
      return RDIError_OutOfStore;
      }

#ifdef VERBOSE_INIT
   printf("\n* OS_Init, osstate = %p, coredesc.rdi=%p type:%u\n", osstate, 
          osstate->coredesc.rdi, type);
#endif
   
   osstate->ErrorNo = 0;
   osstate->CommandLine = NULL ;

   osstate->simrdiprocvec = NULL;

   osstate->os_verbose = ToolConf_DLookupBool(
       config, (tag_t)"VERBOSE", TRUE);

   osstate->os_Trace_OutPut =  ToolConf_DLookupBool(
       config, (tag_t)"TRACE_SEMIHOST_CONOUT", TRUE);

   { char const *option = ToolConf_Lookup(config,
                                          (tag_t)"SEMIHOST_FILEOP_LOG");
   if (option&& option[0])
       state->os_file_log = fopen(option,"w");
   }

#ifdef VERBOSE_SYS_FILE
       osstate->verbose_sys_file = ToolConf_DLookupBool(
                    config, (tag_t)"VERBOSE_SYS_FILE", FALSE);
#endif

       osstate->semihostingstate = SEMIHOSTSTATE_ENABLED;

       osstate->sh_Bigend32 = 
           ((type & RDIOpen_ByteSexMask) == RDIOpen_BigEndian);
       osstate->Set_Endian = 
           ((type & RDIOpen_ByteSexMask) != RDIOpen_DontCareEndian);

       if (!osstate->Set_Endian)
       {
           char const *str_bytesex = ToolConf_Lookup(config, Dbg_Cnf_ByteSex);
           osstate->sh_Bigend32 = (str_bytesex && str_bytesex[0] == 'B') ?
               RDISex_Big : RDISex_Little;
           osstate->Set_Endian = (str_bytesex && (str_bytesex[0] == 'B' ||
                                                  str_bytesex[0] == 'L'));
       }

       /* Only set the endianness if we don't have HWENDIAN=True */

       osstate->Set_Endian &= !ToolConf_DLookupBool(
           config,Dbg_Cnf_TargetHWEndian,FALSE);

       /* And if we're boing asked for BE-8 mode... */
       if (ToolConf_DLookupBool(osstate->config, ARMulCnf_HAS_BE8, FALSE) &&
           ToolConf_DLookupBool(osstate->config, ARMulCnf_BIGEND_IS_BE8, FALSE))
       {
           /* In Pagetab, we also set MMU_EE and CPSR.E
            * Here, we do nothing for now. */
           osstate->Set_Endian = FALSE;
       }



       osstate->usersp = 0x80000000 ;
       osstate->map.soft_vectors = ToolConf_DLookupUInt(
           osstate->config, (tag_t)"AddrSoftVectors", 0xA40L) ;
       osstate->map.soft_vec_code = ToolConf_DLookupUInt(
           osstate->config, (tag_t)"SoftVectorCode", 0xB80L) ;
       osstate->map.handlers = ToolConf_DLookupUInt(
           osstate->config, (tag_t)"AddrsOfHandlers", 0xad0L) ;
       osstate->map.cmd_line = ToolConf_DLookupUInt(
           osstate->config, (tag_t)"AddrCmdLine", 0xf00L) ;

       osstate->AngelEnabled = ToolConf_DLookupBool(osstate->config, 
                                                (tag_t)ARMulCnf_Angel, FALSE);
       osstate->DemonEnabled = ToolConf_DLookupBool(osstate->config, 
                                               (tag_t)ARMulCnf_Demon, FALSE);
       osstate->ExitSwisEnabled = osstate->DemonEnabled ||
                               ToolConf_DLookupBool(osstate->config, 
                                            (tag_t)"EXIT_SWIS", FALSE);
       osstate->os_HaltOnUnknownAngelSwi = ToolConf_DLookupBool(config, 
                                (tag_t)"HALTONUNKNOWNSYSNUMBER", FALSE);

       osstate->os_CPUSpeed = ARMul_GetFCLK(osstate->config);
       osstate->os_BusSpeed = ARMul_GetMCLK(osstate->config);

       if (osstate->AngelEnabled || osstate->DemonEnabled || 
           osstate->ExitSwisEnabled)
       {
           ARMulif_InstallUnkRDIInfoHandler(&osstate->coredesc,
                                            OS_HandleUnkRDI,osstate);

           ARMulif_InstallExceptionHandler(
               &osstate->coredesc, OS_HandleException, osstate);
           ARMulif_InstallEventHandler(
               &osstate->coredesc, ConfigEventSel, OS_HandleEvent, osstate);

       }
      
       if (osstate->AngelEnabled) {
           osstate->AngelSWIARM = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AngelSWIARM, ANGEL_SWI_ARM) ;
           osstate->AngelSWIThumb = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AngelSWIThumb, ANGEL_SWI_THUMB) ;
           osstate->heap_base = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_HeapBase,      ANGEL_HEAPBASE) ;
           osstate->heap_limit = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_HeapLimit,     ANGEL_HEAPLIMIT) ;
           osstate->stack_base = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_StackBase,     ANGEL_STACKBASE) ;
           osstate->stack_limit = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_StackLimit,    ANGEL_STACKLIMIT) ;
           Hostif_PrettyPrint(osstate->hostif, osstate->config, ", Semihosting");
           if (osstate->os_verbose)
           {
               if (osstate->DemonEnabled)
                   Hostif_PrettyPrint(osstate->hostif, osstate->config,
                                      "+DEMON");
               if (osstate->AngelEnabled)
                   Hostif_PrettyPrint(osstate->hostif, osstate->config,
                                      "+ANGEL");
           }
       }
       
       if (osstate->DemonEnabled) {
           ARMword value ;
           
           value = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AddrSuperStack,  DEMON_ADDRSUPERSTACK) ; /* supervisor stack space */
           ARMulif_SetReg(&osstate->coredesc, ARMulif_GetCPSR(&osstate->coredesc) & 0x1f,
                          13, value) ; 
           ARMulif_SetReg(&osstate->coredesc, ARM_MODE_V5_SVC32,   13, value) ;
           value = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AddrAbortStack,  DEMON_ADDRABORTSTACK) ; /* abort stack space */
           ARMulif_SetReg(&osstate->coredesc, ARM_MODE_V5_ABORT32, 13, value) ;
           value = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AddrUndefStack,  DEMON_ADDRUNDEFSTACK); /* undef stack space */
           ARMulif_SetReg(&osstate->coredesc, ARM_MODE_V5_UNDEF32, 13, value) ; 
           value = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AddrIRQStack,    DEMON_ADDRIRQSTACK) ; /* IRQ stack space */
           ARMulif_SetReg(&osstate->coredesc, ARM_MODE_V5_IRQ32,   13, value) ;
           value = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AddrFIQStack,    DEMON_ADDRFIQSTACK) ; /* FIQ stack space */
           ARMulif_SetReg(&osstate->coredesc, ARM_MODE_V5_FIQ32,   13, value) ;
           osstate->usersp = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AddrUserStack, DEMON_ADDRUSERSTACK) ; /* default user stack start */
           osstate->cmdlineaddr = ToolConf_DLookupUInt(osstate->config, (tag_t)ARMulCnf_AddrCmdLine,   DEMON_ADDRCMDLINE) ; /* command line is here after a SWI GetEnv */
           Hostif_PrettyPrint(osstate->hostif, osstate->config, ", Demon");
       }
       ARMulif_InstallEventHandler(&state->coredesc,
                                   ConfigEventSel,
                                   Angel_ConfigEvents, osstate);

       ARMulif_InstallSimRdiRegistration( &state->coredesc,
                                          OS_SimRdiListener,
                                          osstate );

       Time_PropDesc.gacb.handle = state;
       ARMulif_AddProperty(&state->coredesc, RDIPropertyGroup_SuperGroup,
                           &Time_PropDesc);
#ifdef CPUTIME_HI
       TimeHi_PropDesc.gacb.handle = state;
       ARMulif_AddProperty(&state->coredesc, RDIPropertyGroup_SuperGroup,
                           &TimeHi_PropDesc);
#endif
       Clock_PropDesc.gacb.handle = state;
       ARMulif_AddProperty(&state->coredesc, RDIPropertyGroup_SuperGroup,
                           &Clock_PropDesc);


   {
     state->os_bUseRealTime = !ARMul_ClockIsEmulated(config);
     if (osstate->os_verbose && state->os_bUseRealTime)
     {
       Hostif_PrettyPrint(osstate->hostif, osstate->config, " Clock=Real Time");
     }
   }

   osstate->os_FakeTimeFrom = ToolConf_DLookupUInt(osstate->config, (tag_t)"FAKETIMEFROM", 0);

   for (i = 0; i < FOPEN_MAX; i++) {
      osstate->FileTable[i] = NULL;
      osstate->FileCount[i] = 0;
      }

   for (i = 0; i < UNIQUETEMPS; i++)
      osstate->tempnames[i] = NULL;
}
END_INIT(OS)


#define ADD_TO_NEW_TAB
#ifdef ADD_TO_NEW_TAB

#define FOE(a) OS_FreeOnExit(state,a)

/* Returns an allocated string, pre-FOE'd, (or NULL on out-of-memory). */
static char *make_enum_name(OSState *state)
{
    (void)state;
    return "OS_OffOn=Off,On";
}

static RegWin *new_RegWin(OSState *state)
{
    RegWin *rw = (RegWin*)calloc(1,sizeof(RegWin));
    if (rw != NULL)
    {
        unsigned i;
        unsigned numr = sizeof(semihost_reg_defs)/sizeof(semihost_reg_defs[0]);
        /* {{{ Fill in the RegWin fields. */
        /* !Todo: Use the instance-name in case we have a multi-core system! */
        rw->tab_name = "Semihost,Semihosting Information";
#define NUM_HEADER_LINES 0
        rw->line_cnt = numr + NUM_HEADER_LINES;
        rw->lines = (char**)FOE(calloc(rw->line_cnt,sizeof(char *)));
#define NUM_ENUMS 0
        rw->enum_cnt = NUM_ENUMS;
        rw->enum_list = NUM_ENUMS > 0 ? FOE(calloc(NUM_ENUMS,sizeof(char*))) : NULL;
        if (NUM_ENUMS > 0)
        {
            rw->enum_list[0] = FOE(StrDup(make_enum_name(state)));
        }
        /* {{ Fill in Lines */
#if NUM_HEADER_LINES
        rw->lines[0] = "_Name                  Value                 ";
#endif
        for (i = 0; i < numr; i++)
        {
            char *str1;
            if (rw->enum_cnt > 0 && strcmp(semihost_reg_defs[i].name, "@semihost_state") == 0)
            {
                str1 = StrMultiCat( "=", semihost_reg_defs[i].name, "=OS_OffOn", NULL);
            }
            else
            {
                str1 = StrMultiCat( "=", semihost_reg_defs[i].name, NULL);
            }
            rw->lines[i+ NUM_HEADER_LINES] = FOE(str1);
        }
        /* }} Fill in Lines */
        /* }}} RegWin fields. */
    }
    return FOE(rw);
}
#endif


static void
OS_SimRdiListener( SimRdiRegistrationProcVec* srpv,
                   void* handle )
{
  OSState *osstate = (OSState *)handle;
  SimRdiProcVec* spv = srpv->simrdiprocvec;
  SimRdi_Callback_Advert* advert;

  if( srpv->number < 1
      || spv == NULL
      || spv->signature != SIMRDIPROCVEC_SIGNATURE
      || (spv->version.major) != 0x01
      || spv->null == NULL
      || spv->null->advertise == NULL
      || spv->null->c_new == NULL
      )
    {
      return;
    }

  advert = spv->null->c_new(spv->null);
  if( advert != NULL )
    {
      osstate->advert        = advert->x.id;
      osstate->simrdiprocvec = spv;
      
      advert->x.name           =
        __FILE__ ": semi-hosting returns exit information through "
        "stop_info";
      advert->x.handle         = osstate;
      advert->x.coredesc       = &osstate->coredesc;
      advert->x.config_flags   = semihosting_null_config_flag;
      advert->simregistercallback  = NULL;
#ifdef ADD_TO_NEW_TAB
      advert->x.config_flags |= UNIREGS_DO_NOT_AUTO_GENERATE_REG_WIN;
#endif
      spv->null->advertise( spv->null, advert );
    }

  /* add all funky semihosting stuff to the output pane */
  {
      SimRdi_Uniregs_Advert* ad =
          spv->uniregs->c_new( spv->uniregs );
      if( ad != NULL )
      {
          osstate->advert_regs = advert->x.id;

          ad->x.name        = "Semihosting information";
          ad->x.handle      = osstate;
          ad->x.coredesc    = &osstate->coredesc;

          ad->description = "Semihosting Parameters";

          ad->len        = sizeof(semihost_reg_defs)/sizeof(semihost_reg_defs[0]);
#if 0     /* If you've got it... */
          ad->block_num  = uniregs_model_debugging_registers;
#else
          /* ... Flaunt it! */
          ad->block_num  = uniregs_cycle_counter /*uniregs_extensions */;
#endif
          ad->desc       = semihost_reg_defs;

          ad->handle_for_function = (void*)osstate;
          ad->_SimReg             = OS_SimReg;
          ad->start_reg_number = 0;
#ifdef ADD_TO_NEW_TAB
          /* Otherwise we add to predefined ad->block_num */
          ad->x.config_flags |= UNIREGS_DO_NOT_AUTO_GENERATE_REG_WIN;
#endif
          spv->uniregs->advertise( spv->uniregs, ad );
      }
  }
#ifdef ADD_TO_NEW_TAB
    {
    RegWin *rw = new_RegWin(osstate);
    if (rw != NULL)
    {
        SimRdi_Regwin_Advert* ad =
            spv->regwin->c_new( spv->regwin );

        ad->regwin = rw;
        osstate->os_ad_to_destroy = ad->x.id;
        spv->regwin->advertise( spv->regwin, ad );
    }
    }
#endif
}

#define OS_State OSState

/*void OS_Exit(void *voidosstate)*/
int OS_Exit(RDI_AgentHandle agent)
{
   OS_State *osstate = (OS_State *)agent;
   unsigned i ;

   if (osstate != NULL) {
      if (osstate->CommandLine != NULL)
         free((char *)(osstate->CommandLine));
      for (i = 0; i < UNIQUETEMPS; i++)
         if (osstate->tempnames[i] != NULL)
            free(osstate->tempnames[i]);
      if (osstate->os_file_log)
      {
          fclose(osstate->os_file_log);
      }

      if (osstate->simrdiprocvec)
      {
          if (osstate->simrdiprocvec->null->destroy)
          {
              osstate->simrdiprocvec
                  ->null->destroy(osstate->simrdiprocvec->null,
                                  osstate->advert);
          }
#ifdef ADD_TO_NEW_TAB
          if (osstate->simrdiprocvec->regwin->destroy)
          {
              osstate->simrdiprocvec->regwin->destroy(
                  osstate->simrdiprocvec->regwin,
                  osstate->os_ad_to_destroy);
          }
#endif
      }


      free((char *)osstate);
   }

   return RDIError_NoError;
}


/* This is an RDI_InfoProc, so must validate its inputs */

static int OS_HandleUnkRDI(void *handle,
                          unsigned subcode,
                          ARMword *arg1, ARMword *arg2)
{

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -