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

📄 monitor.c

📁 eCos操作系统源码
💻 C
字号:
//==========================================================================////      monitor.c////      Monitor shell and main routines for CygMON the Wonder Monitor////==========================================================================//####ECOSGPLCOPYRIGHTBEGIN####// -------------------------------------------// This file is part of eCos, the Embedded Configurable Operating System.// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.//// eCos is free software; you can redistribute it and/or modify it under// the terms of the GNU General Public License as published by the Free// Software Foundation; either version 2 or (at your option) any later version.//// eCos is distributed in the hope that it will be useful, but WITHOUT ANY// WARRANTY; without even the implied warranty of MERCHANTABILITY or// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License// for more details.//// You should have received a copy of the GNU General Public License along// with eCos; if not, write to the Free Software Foundation, Inc.,// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.//// As a special exception, if other files instantiate templates or use macros// or inline functions from this file, or you compile this file and link it// with other works to produce a work based on this file, this file does not// by itself cause the resulting work to be covered by the GNU General Public// License. However the source code for this file must still be made available// in accordance with section (3) of the GNU General Public License.//// This exception does not invalidate any other reasons why a work based on// this file might be covered by the GNU General Public License.//// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.// at http://sources.redhat.com/ecos/ecos-license/// -------------------------------------------//####ECOSGPLCOPYRIGHTEND####//==========================================================================//#####DESCRIPTIONBEGIN####//// Author(s):    // Contributors: gthomas, dmoseley// Date:         1999-10-20// Purpose:      Monitor shell and main routines for CygMON the Wonder Monitor// Description:  //               ////####DESCRIPTIONEND####////=========================================================================/* Platform-independent code for cygmon */#include <stdlib.h>#include <unistd.h>#ifdef HAVE_BSP#include <bsp/bsp.h>#include <bsp/cpu.h>#include <bsp/hex-utils.h>#endif#include <monitor.h>#ifdef HAVE_BSP#include "cpu_info.h"#endif#include <ledit.h>#include <signal.h>#include <string.h>#include <ctype.h>#if USE_CYGMON_PROTOTYPES/* Use common prototypes *//* Some of the composed board.h files compose these   prototypes redundently, but if they dont,   these are the common definitions */#include "fmt_util.h"   /* Interface to string formatting utilities */#include "tservice.h"   /* Interface to target specific services */#include "generic-stub.h" /* from libstub */#endif /* USE_CYGMON_PROTOTYPES */static int  cygmon_handle_exception (int sigval);static void monitor_take_control (void);#if CYGMON_SYSTEM_SERVICESextern int process_syscall (int syscall_num);#elif defined (USE_ECOS_HAL_EXCEPTIONS)static int cygmon_process_syscall (int sigval);#endifint stub_is_active = 0;mem_addr_t last_pc;#ifdef HAVE_BSP#if !defined(USE_ECOS_HAL_EXCEPTIONS)static int mon_dbg_handler(int exc_nr, void *regs);static int mon_kill_handler(int exc_nr, void *regs);#endif // USE_ECOS_HAL_EXCEPTIONS#ifndef USE_ECOS_HAL_BREAKPOINTS#define __is_breakpoint_function() (get_pc() == (target_register_t)bsp_breakinsn)#endif#ifdef __ECOS__/* * This global flag is used by generic-stub.c to communicate to us that we * are processing the breakpoint function within Cygmon itself. */extern int processing_breakpoint_function;#endif/* Global pointer to current set of saved registers. */void *mon_saved_regs;/* Original BSP debug vector replaced by monitor. */#if !defined(USE_ECOS_HAL_EXCEPTIONS)static bsp_handler_t old_dbg_vec;#endif // !defined(USE_ECOS_HAL_EXCEPTIONS)#elsestatic int handle_signal (int signal_val);__PFI user_signal_handler = NULL;#endif#if defined(__ECOS__)#include <cyg/hal/hal_stub.h>#endif#if defined(__ECOS__) && !defined(PROCESS_EXCEPTION_VEC_PROTOTYPE_EXISTS)#define PROCESS_EXCEPTION_VEC_PROTOTYPE_EXISTSextern volatile __PFI (*__process_exception_vec)(int);#endif#ifdef MONITOR_CONTROL_INTERRUPTS/* This is set if the user wants interrupts enabled in the monitor. */static int monitor_interrupts_enabled;#endif#if NOMAINint monitor_main (int argc, char **argv) /* Suppress default main() junk */#elseint main (int argc, char **argv)     #endif{#ifdef HAVE_BSP  int  cur_port;  struct bsp_comm_info comm_info;#else  /* Set up exception handling traps */  initialize_stub ();#endif  initialize_mon ();#ifdef HAVE_BSP  /* get info on debug channel */  cur_port = bsp_set_debug_comm(-1);  bsp_sysinfo(BSP_INFO_COMM, cur_port, &comm_info);  /*   * If we're using a network interface, don't install   * the cygmon vectors. Currently, we only support stub   * mode over a network connection.   */  if (comm_info.kind != BSP_COMM_ENET)    {      xprintf("\n");      version ();      /* replace original BSP debug and kill handler with ours */#if !defined(USE_ECOS_HAL_EXCEPTIONS)      old_dbg_vec = bsp_install_dbg_handler(mon_dbg_handler);      (void)bsp_install_kill_handler(mon_kill_handler);#else      /* replace original BSP debug and kill handler with ours using eCos stuff */      __process_exception_vec = (__PFI)cygmon_handle_exception;      __process_syscall_vec = cygmon_process_syscall;      __process_exit_vec = monitor_take_control;#endif // __ECOS__    }  else    {      /* This forces the console to use the gdb channel. */      bsp_set_console_comm(cur_port);    }#else  xprintf("\n");  version ();  __process_exception_vec = cygmon_handle_exception;  __process_exit_vec = monitor_take_control;#if CYGMON_SYSTEM_SERVICES  __process_syscall_vec = process_syscall;#endif    __process_signal_vec = handle_signal;  __init_vec = install_breakpoints;  __cleanup_vec = clear_breakpoints;#endif#if 0#ifdef __ECOS__  __process_exception_vec = cygmon_handle_exception;#endif#endif  while (1)    {      breakpoint ();      if (switch_to_stub_flag)        {	  xprintf("Switching to stub\n");	  switch_to_stub_flag = 0;	}    }  /* never reached */  exit (0);}/* Transfer control to gdb stub */ int transfer_to_stub (){  /* Return back to the exception handler, but the exception handler     should invoke the stub's exception handler instead of ours. */#if defined(HAVE_BSP) && !defined(USE_ECOS_HAL_EXCEPTIONS)  (void)bsp_install_dbg_handler(old_dbg_vec);#else  __switch_to_stub ();#endif  /* The stub is now active. */  stub_is_active = 1;  return -1;}voidclear_user_state (void){#ifdef HAS_TIMER  if (__timer_enabled ())    __settimer (0, 0);#endif  clear_breakpoints ();#ifndef HAVE_BSP  user_signal_handler = NULL;#endif  __clear_single_step ();}static voidmonitor_take_control (void){  stub_is_active = 0;  switch_to_stub_flag = 0;  // Flush the unget state.  This is because the ecos stub and Cygmon track this  // stuff separately.  bsp_debug_ungetc('\0');#ifdef INITIALIZE_MON_EACH_TIME  // Call the per-stop initialization routine if it is defined.  INITIALIZE_MON_EACH_TIME();#endif#if defined(HAVE_BSP) && !defined(USE_ECOS_HAL_EXCEPTIONS)  /* replace original BSP debug trap handler with ours */  (void)bsp_install_dbg_handler(mon_dbg_handler);#else  clear_user_state ();  __process_exception_vec = cygmon_handle_exception;#endif}#ifdef MONITOR_CONTROL_INTERRUPTSvoidmonitor_enable_interrupts (void){  monitor_interrupts_enabled = 1;  enable_interrupts ();}voidmonitor_disable_interrupts (void){  monitor_interrupts_enabled = 0;  disable_interrupts ();}intmonitor_interrupt_state (void){  return monitor_interrupts_enabled;}#endif#if defined(USE_ECOS_HAL_EXCEPTIONS)externC HAL_SavedRegisters *_hal_registers;extern int machine_syscall(HAL_SavedRegisters *regs);static intcygmon_process_syscall (int sigval){    return machine_syscall(_hal_registers);}#endifstatic intcygmon_handle_exception (int sigval){  target_register_t pc;#ifdef MONITOR_CONTROL_INTERRUPTS  if (monitor_interrupts_enabled)    {      if (! __in_interrupt)	enable_interrupts ();    }#endif#ifdef TARGET_EXCEPTION_CODE  TARGET_EXCEPTION_CODE#endif#ifndef HAVE_BSP  if (sigval != SIGKILL)    if (handle_signal (sigval) == 0)      return 0;#endif  clear_user_state ();  /* We may want to tweak the PC to point at the faulting instruction,     for example. (breakpoints on x86). */#ifdef TARGET_ADJUST_PC  TARGET_ADJUST_PC#endif  pc = get_pc();  MAKE_STD_ADDR (pc, &last_pc);#ifdef __ECOS__  if ((sigval == SIGTRAP) && (__is_breakpoint_function() || processing_breakpoint_function))#else  if ((sigval == SIGTRAP) && __is_breakpoint_function())#endif    {      /*       * This is the initial breakpoint inserted by the BSP       * Don't print anything for this as it is confusing       */    }  else    {      if (sigval == SIGTRAP)          xprintf ("Hit breakpoint");      else          xprintf ("Got signal %d", sigval);      xprintf (" at 0x%s\n", int2str (pc, 16, sizeof (target_register_t) * 2));#ifdef DISASSEMBLER      if (!__is_breakpoint_function ())	{	  do_dis (&last_pc);	  flush_dis ();	}#endif    }  monitor_take_control ();  return monitor_loop ();}#ifndef HAVE_BSP/* Returns 0 if the program should restart at the point at which the   signal was received, -1 otherwise. */static inthandle_signal (int signal){  if (signal == SIGKILL)    return -1;  if (user_signal_handler != NULL)    {      int result = user_signal_handler (signal);      switch (result)	{	  /* Don't ignore potential hardware signals. */	case 3:	  if (signal == SIGSEGV || signal == SIGBUS || signal == SIGFPE	      || signal == SIGTRAP || signal == SIGILL)	    return -1;	case 0:	  return 0;	default:	case 1:	case 2:	  return -1;	}    }    return -1;}#endifvoidversion (void){#ifdef HAVE_BSP  struct bsp_platform_info platform;  struct bsp_mem_info      mem;  int                      i;  unsigned long            u, totmem, topmem;#endif  extern char *build_date;  xprintf ("Cygmon, the Cygnus ROM monitor.\n");  xprintf ("Copyright(c) 1997, 1998, 1999, 2000 Red Hat\n\n");  xprintf ("Version: %s\nThis image was built on %s\n\n",	   VERSION, build_date);#ifdef HAVE_BSP  bsp_sysinfo(BSP_INFO_PLATFORM, &platform);  totmem = topmem = 0;  i = 0;  while (bsp_sysinfo(BSP_INFO_MEMORY, i++, &mem) == 0)    {      if (mem.kind == BSP_MEM_RAM)        {          totmem += mem.nbytes;          u = (unsigned long)mem.virt_start + mem.nbytes;	  if (u > topmem)	    topmem = u;        }    }  xprintf("CPU: %s\n", platform.cpu);  xprintf("Board: %s\n", platform.board);  if (*(platform.extra))      xprintf("%s\n", platform.extra);  xprintf("Total RAM: %d bytes\n", totmem);  xprintf("Top of RAM: 0x%x\n", topmem);#endif}#ifdef HAVE_BSP#if !defined(USE_ECOS_HAL_EXCEPTIONS)static intmon_kill_handler(int exc_nr, void *regs){    monitor_take_control();    return 1;}#endif // !defined(USE_ECOS_HAL_EXCEPTIONS)#if !defined(USE_ECOS_HAL_EXCEPTIONS)static intmon_dbg_handler(int exc_nr, void *regs){    int sig;    unsigned long cur_pc;    mon_saved_regs = regs;    sig = bsp_get_signal(exc_nr, regs);    cygmon_handle_exception(sig);    cur_pc = bsp_get_pc(regs);    if (cur_pc == (unsigned long)bsp_breakinsn)	bsp_skip_instruction(regs);    if (!stub_is_active)	install_breakpoints();    return 1;}#endif // !defined(USE_ECOS_HAL_EXCEPTIONS)#endif

⌨️ 快捷键说明

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