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

📄 arm-dis.c

📁 基于4个mips核的noc设计
💻 C
📖 第 1 页 / 共 2 页
字号:
/* Instruction printing code for the ARM   Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001   Free Software Foundation, Inc.   Contributed by Richard Earnshaw (rwe@pegasus.esprit.ec.org)   Modification by James G. Smith (jsmith@cygnus.co.uk)This file is part of libopcodes. This program is free software; you can redistribute it and/or modify it underthe terms of the GNU General Public License as published by the FreeSoftware Foundation; either version 2 of the License, or (at your option)any later version. This program is distributed in the hope that it will be useful, but WITHOUTANY WARRANTY; without even the implied warranty of MERCHANTABILITY orFITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License formore details. You should have received a copy of the GNU General Public Licensealong with this program; if not, write to the Free SoftwareFoundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */#include "sysdep.h"#include "dis-asm.h"#define DEFINE_TABLE#include "arm-opc.h"#include "coff/internal.h"#include "libcoff.h"#include "opintl.h"/* FIXME: This shouldn't be done here */#include "elf-bfd.h"#include "elf/internal.h"#include "elf/arm.h"#ifndef streq#define streq(a,b)	(strcmp ((a), (b)) == 0)#endif#ifndef strneq#define strneq(a,b,n)	(strncmp ((a), (b), (n)) == 0)#endif#ifndef NUM_ELEM#define NUM_ELEM(a)     (sizeof (a) / sizeof (a)[0])#endifstatic char * arm_conditional[] ={"eq", "ne", "cs", "cc", "mi", "pl", "vs", "vc", "hi", "ls", "ge", "lt", "gt", "le", "", "nv"};typedef struct{  const char * name;  const char * description;  const char * reg_names[16];}arm_regname;static arm_regname regnames[] ={  { "raw" , "Select raw register names",    { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"}},  { "gcc",  "Select register names used by GCC",    { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "sl",  "fp",  "ip",  "sp",  "lr",  "pc" }},  { "std",  "Select register names used in ARM's ISA documentation",    { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "sp",  "lr",  "pc" }},  { "apcs", "Select register names used in the APCS",    { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "sl",  "fp",  "ip",  "sp",  "lr",  "pc" }},  { "atpcs", "Select register names used in the ATPCS",    { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "v4", "v5", "v6", "v7",  "v8",  "IP",  "SP",  "LR",  "PC" }},  { "special-atpcs", "Select special register names used in the ATPCS",    { "a1", "a2", "a3", "a4", "v1", "v2", "v3", "WR", "v5", "SB", "SL",  "FP",  "IP",  "SP",  "LR",  "PC" }}};/* Default to GCC register name set.  */static unsigned int regname_selected = 1;#define NUM_ARM_REGNAMES  NUM_ELEM (regnames)#define arm_regnames      regnames[regname_selected].reg_namesstatic boolean force_thumb = false;static char * arm_fp_const[] ={"0.0", "1.0", "2.0", "3.0", "4.0", "5.0", "0.5", "10.0"};static char * arm_shift[] = {"lsl", "lsr", "asr", "ror"};/* Forward declarations.  */static void arm_decode_shift PARAMS ((long, fprintf_ftype, void *));static int  print_insn_arm   PARAMS ((bfd_vma, struct disassemble_info *, long));static int  print_insn_thumb PARAMS ((bfd_vma, struct disassemble_info *, long));static void parse_disassembler_options PARAMS ((char *));static int  print_insn       PARAMS ((bfd_vma, struct disassemble_info *, boolean));int get_arm_regname_num_options (void);int set_arm_regname_option (int option);int get_arm_regnames (int option, const char **setname,		      const char **setdescription,		      const char ***register_names);/* Functions. */intget_arm_regname_num_options (void){  return NUM_ARM_REGNAMES;}intset_arm_regname_option (int option){  int old = regname_selected;  regname_selected = option;  return old;}intget_arm_regnames (int option, const char **setname,		  const char **setdescription,                  const char ***register_names){  *setname = regnames[option].name;  *setdescription = regnames[option].description;  *register_names = regnames[option].reg_names;  return 16;}static voidarm_decode_shift (given, func, stream)     long given;     fprintf_ftype func;     void * stream;{  func (stream, "%s", arm_regnames[given & 0xf]);    if ((given & 0xff0) != 0)    {      if ((given & 0x10) == 0)	{	  int amount = (given & 0xf80) >> 7;	  int shift = (given & 0x60) >> 5;	  	  if (amount == 0)	    {	      if (shift == 3)		{		  func (stream, ", rrx");		  return;		}	      	      amount = 32;	    }	  	  func (stream, ", %s #%d", arm_shift[shift], amount);	}      else	func (stream, ", %s %s", arm_shift[(given & 0x60) >> 5],	      arm_regnames[(given & 0xf00) >> 8]);    }}/* Print one instruction from PC on INFO->STREAM.   Return the size of the instruction (always 4 on ARM). */static intprint_insn_arm (pc, info, given)     bfd_vma                   pc;     struct disassemble_info * info;     long                      given;{  struct arm_opcode *  insn;  void *               stream = info->stream;  fprintf_ftype        func   = info->fprintf_func;  for (insn = arm_opcodes; insn->assembler; insn++)    {      if ((given & insn->mask) == insn->value)	{	  char * c;	  	  for (c = insn->assembler; *c; c++)	    {	      if (*c == '%')		{		  switch (*++c)		    {		    case '%':		      func (stream, "%%");		      break;		    case 'a':		      if (((given & 0x000f0000) == 0x000f0000)			  && ((given & 0x02000000) == 0))			{			  int offset = given & 0xfff;			  			  func (stream, "[pc"); 			  if (given & 0x01000000)			    {			      if ((given & 0x00800000) == 0)				offset = - offset;			  			      /* pre-indexed */			      func (stream, ", #%x]", offset);			      offset += pc + 8;			      /* Cope with the possibility of write-back				 being used.  Probably a very dangerous thing				 for the programmer to do, but who are we to				 argue ?  */			      if (given & 0x00200000)				func (stream, "!");			    }			  else			    {			      /* Post indexed.  */			      func (stream, "], #%x", offset);			      offset = pc + 8;  /* ie ignore the offset.  */			    }			  			  func (stream, "\t; ");			  info->print_address_func (offset, info);			}		      else			{			  func (stream, "[%s", 				arm_regnames[(given >> 16) & 0xf]);			  if ((given & 0x01000000) != 0)			    {			      if ((given & 0x02000000) == 0)				{				  int offset = given & 0xfff;				  if (offset)				    func (stream, ", %s#%d",					  (((given & 0x00800000) == 0)					   ? "-" : ""), offset);				}			      else				{				  func (stream, ", %s",					(((given & 0x00800000) == 0)					 ? "-" : ""));				  arm_decode_shift (given, func, stream);				}			      func (stream, "]%s", 				    ((given & 0x00200000) != 0) ? "!" : "");			    }			  else			    {			      if ((given & 0x02000000) == 0)				{				  int offset = given & 0xfff;				  if (offset)				    func (stream, "], %s#%d",					  (((given & 0x00800000) == 0)					   ? "-" : ""), offset);				  else 				    func (stream, "]");				}			      else				{				  func (stream, "], %s",					(((given & 0x00800000) == 0) 					 ? "-" : ""));				  arm_decode_shift (given, func, stream);				}			    }			}		      break;		    case 's':                      if ((given & 0x004f0000) == 0x004f0000)			{                          /* PC relative with immediate offset.  */			  int offset = ((given & 0xf00) >> 4) | (given & 0xf);			  			  if ((given & 0x00800000) == 0)			    offset = -offset;			  			  func (stream, "[pc, #%x]\t; ", offset);			  			  (*info->print_address_func)			    (offset + pc + 8, info);			}		      else			{			  func (stream, "[%s", 				arm_regnames[(given >> 16) & 0xf]);			  if ((given & 0x01000000) != 0)			    {                              /* Pre-indexed.  */			      if ((given & 0x00400000) == 0x00400000)				{                                  /* Immediate.  */                                  int offset = ((given & 0xf00) >> 4) | (given & 0xf);				  if (offset)				    func (stream, ", %s#%d",					  (((given & 0x00800000) == 0)					   ? "-" : ""), offset);				}			      else				{                                  /* Register.  */				  func (stream, ", %s%s",					(((given & 0x00800000) == 0)					 ? "-" : ""),                                        arm_regnames[given & 0xf]);				}			      func (stream, "]%s", 				    ((given & 0x00200000) != 0) ? "!" : "");			    }			  else			    {                              /* Post-indexed.  */			      if ((given & 0x00400000) == 0x00400000)				{                                  /* Immediate.  */                                  int offset = ((given & 0xf00) >> 4) | (given & 0xf);				  if (offset)				    func (stream, "], %s#%d",					  (((given & 0x00800000) == 0)					   ? "-" : ""), offset);				  else 				    func (stream, "]");				}			      else				{                                  /* Register.  */				  func (stream, "], %s%s",					(((given & 0x00800000) == 0)					 ? "-" : ""),                                        arm_regnames[given & 0xf]);				}			    }			}		      break;			  		    case 'b':		      (*info->print_address_func)			(BDISP (given) * 4 + pc + 8, info);		      break;		    case 'c':		      func (stream, "%s",			    arm_conditional [(given >> 28) & 0xf]);		      break;		    case 'm':		      {			int started = 0;			int reg;			func (stream, "{");			for (reg = 0; reg < 16; reg++)			  if ((given & (1 << reg)) != 0)			    {			      if (started)				func (stream, ", ");			      started = 1;			      func (stream, "%s", arm_regnames[reg]);			    }			func (stream, "}");		      }		      break;		    case 'o':		      if ((given & 0x02000000) != 0)			{			  int rotate = (given & 0xf00) >> 7;			  int immed = (given & 0xff);			  immed = (((immed << (32 - rotate))				    | (immed >> rotate)) & 0xffffffff);			  func (stream, "#%d\t; 0x%x", immed, immed);			}		      else			arm_decode_shift (given, func, stream);		      break;		    case 'p':		      if ((given & 0x0000f000) == 0x0000f000)			func (stream, "p");		      break;		    case 't':		      if ((given & 0x01200000) == 0x00200000)			func (stream, "t");		      break;		    case 'h':		      if ((given & 0x00000020) == 0x00000020)			func (stream, "h");                      else                        func (stream, "b");		      break;		    case 'A':		      func (stream, "[%s", arm_regnames [(given >> 16) & 0xf]);		      if ((given & 0x01000000) != 0)			{			  int offset = given & 0xff;			  if (offset)			    func (stream, ", %s#%d]%s",				  ((given & 0x00800000) == 0 ? "-" : ""),				  offset * 4,				  ((given & 0x00200000) != 0 ? "!" : ""));			  else			    func (stream, "]");			}		      else			{			  int offset = given & 0xff;			  if (offset)			    func (stream, "], %s#%d",				  ((given & 0x00800000) == 0 ? "-" : ""),				  offset * 4);			  else			    func (stream, "]");			}		      break;		    case 'B':		      /* Print ARM V5 BLX(1) address: pc+25 bits.  */		      {			bfd_vma address;			bfd_vma offset = 0;						if (given & 0x00800000)			  /* Is signed, hi bits should be ones.  */			  offset = (-1) ^ 0x00ffffff;			/* Offset is (SignExtend(offset field)<<2).  */			offset += given & 0x00ffffff;			offset <<= 2;			address = offset + pc + 8;						if (given & 0x01000000)			  /* H bit allows addressing to 2-byte boundaries.  */			  address += 2;		        info->print_address_func (address, info);		      }		      break;		    case 'C':		      func (stream, "_");		      if (given & 0x80000)			func (stream, "f");		      if (given & 0x40000)			func (stream, "s");		      if (given & 0x20000)			func (stream, "x");		      if (given & 0x10000)			func (stream, "c");		      break;		    case 'F':		      switch (given & 0x00408000)			{			case 0:			  func (stream, "4");			  break;			case 0x8000:			  func (stream, "1");			  break;			case 0x00400000:			  func (stream, "2");			  break;			default:			  func (stream, "3");			}		      break;					    case 'P':		      switch (given & 0x00080080)			{			case 0:			  func (stream, "s");			  break;			case 0x80:			  func (stream, "d");			  break;			case 0x00080000:			  func (stream, "e");			  break;			default:			  func (stream, _("<illegal precision>"));			  break;			}		      break;		    case 'Q':		      switch (given & 0x00408000)			{			case 0:			  func (stream, "s");			  break;			case 0x8000:			  func (stream, "d");			  break;			case 0x00400000:			  func (stream, "e");			  break;			default:			  func (stream, "p");			  break;			}		      break;		    case 'R':		      switch (given & 0x60)			{			case 0:			  break;			case 0x20:			  func (stream, "p");			  break;			case 0x40:			  func (stream, "m");			  break;			default:			  func (stream, "z");			  break;			}		      break;		    case '0': case '1': case '2': case '3': case '4': 		    case '5': case '6': case '7': case '8': case '9':		      {			int bitstart = *c++ - '0';			int bitend = 0;			while (*c >= '0' && *c <= '9')			  bitstart = (bitstart * 10) + *c++ - '0';			switch (*c)			  {			  case '-':			    c++;			    			    while (*c >= '0' && *c <= '9')			      bitend = (bitend * 10) + *c++ - '0';			    			    if (!bitend)			      abort ();			    			    switch (*c)			      {			      case 'r':

⌨️ 快捷键说明

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