URL
https://opencores.org/ocsvn/or1k/or1k/trunk
Subversion Repositories or1k
Compare Revisions
- This comparison shows the changes necessary to convert path
/or1k/tags/start/gdb-5.0/utils/amd-udi/mondfe
- from Rev 579 to Rev 1765
- ↔ Reverse comparison
Rev 579 → Rev 1765
/bkpt.c
0,0 → 1,474
static char _[] = " @(#)bkpt.c 5.20 93/07/30 16:38:20, Srini, AMD "; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This module contains the functions used to provide breakpointing |
** capability. |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <ctype.h> |
#include "memspcs.h" |
#include "main.h" |
#include "monitor.h" |
#include "miniint.h" |
#include "error.h" |
|
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
|
#else |
#include <strings.h> |
|
#endif |
|
/* |
** Definitions |
*/ |
|
int get_addr_29k_m PARAMS((char *, struct addr_29k_t *, INT32)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
int get_word PARAMS((char *, INT32 *)); |
int get_word_decimal PARAMS((char *, INT32 *)); |
|
INT32 clear_table PARAMS((void)); |
INT32 clear_bkpt PARAMS((struct addr_29k_t)); |
INT32 show_table PARAMS((void)); |
INT32 set_bkpt PARAMS((struct addr_29k_t, |
INT32, |
INT32)); |
|
INT32 match_entry PARAMS((ADDR32 offset, |
INT32 space, |
int *id)); |
INT32 remove_from_table PARAMS((int id)); |
|
INT32 add_to_table PARAMS((ADDR32 offset, |
INT32 space, |
INT32 passcnt, |
INT32 bktype, |
int id)); |
|
extern struct bkpt_t *bkpt_table; |
|
/* |
** The function below is used in manipulating breakpoints. |
** This function is called in the main command loop parser |
** of the monitor. The parameters passed to this function |
** are: |
** |
** token - This is an array of pointers to strings. Each string |
** referenced by this array is a "token" of the user's |
** input, translated to lower case. |
** |
** token_count - This is the number of tokens in "token". |
** |
*/ |
|
|
INT32 |
bkpt_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
INT32 result; |
struct addr_29k_t addr_29k; |
INT32 pass_count; |
INT32 bkpt_type; |
|
/* |
** Clear breakpoint(s) |
*/ |
if (strcmp(token[0], "bc") == 0) { |
if (token_count == 1) { |
result = clear_table(); |
return (result); |
} |
else |
|
/* Clear a specific breakpoints */ |
if (token_count == 2) { |
result = get_addr_29k_m(token[1], &addr_29k, I_MEM); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k); |
if (result != 0) |
return (result); |
if (addr_29k.memory_space == (INT32) GENERIC_SPACE) |
addr_29k.memory_space = (INT32) I_MEM; |
result = clear_bkpt(addr_29k); |
return (result); |
} |
else /* token_count != 1 or 2 */ |
return (EMSYNTAX); |
} |
else |
|
/* |
** Set breakpoint(s) |
*/ |
|
if ((strcmp(token[0], "b") == 0) || |
(strcmp(token[0], "b050p") == 0) || |
(strcmp(token[0], "b050v") == 0) || |
(strcmp(token[0], "b050") == 0)) { /* b050 defaults to b050p */ |
|
if (strcmp(token[0], "b") == 0) |
bkpt_type = BKPT_29000; |
else |
if (strcmp(token[0], "b050p") == 0) |
bkpt_type = BKPT_29050_BTE_0; /* translation disabled */ |
else |
if (strcmp(token[0], "b050v") == 0) |
bkpt_type = BKPT_29050_BTE_1; |
else |
if (strcmp(token[0], "b050") == 0) |
bkpt_type = BKPT_29050_BTE_0; /* translation disabled */ |
else |
return (EMSYNTAX); |
|
if (token_count == 1) { |
result = show_table(); |
return (result); |
} |
else |
|
/* Set breakpoint with pass count of 1 */ |
if (token_count == 2) { |
result = get_addr_29k_m(token[1], &addr_29k, I_MEM); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k); |
if (result != 0) |
return (result); |
/* The TIP checks the memory space for acceptance */ |
if (addr_29k.memory_space == (INT32) GENERIC_SPACE) |
addr_29k.memory_space = (INT32) I_MEM; |
result = set_bkpt(addr_29k, (INT32) 1, bkpt_type); |
return (result); |
} |
else |
|
/* Set breakpoint with pass count */ |
if (token_count == 3) { |
result = get_addr_29k_m(token[1], &addr_29k, I_MEM); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k); |
if (result != 0) |
return (result); |
result = get_word_decimal(token[2], &pass_count); |
if (result != 0) |
return (EMSYNTAX); |
if (addr_29k.memory_space == (INT32) GENERIC_SPACE) |
addr_29k.memory_space = (INT32) I_MEM; |
result = set_bkpt(addr_29k, pass_count, bkpt_type); |
return (result); |
} |
else /* too many parms for set breakpoint */ |
return (EMSYNTAX); |
} |
else /* not a proper 'b" command */ |
return (EMSYNTAX); |
|
} /* end bkpt_cmd() */ |
|
|
|
/* |
** Functions used by bkpt_cmd() |
*/ |
|
|
/* |
** This function is used to remove a breakpoint from the |
** target and from the host breakpoint table. |
*/ |
|
INT32 |
clear_bkpt(addr_29k) |
struct addr_29k_t addr_29k; |
{ |
int breakid; |
INT32 retval; |
|
(void) match_entry (addr_29k.address, |
addr_29k.memory_space, |
&breakid); |
|
/* Did we find the breakpoint? */ |
if (breakid <= (int) 0) { |
warning (EMBKPTRM); |
return (FAILURE); |
}; |
|
/* if a valid breakpoint entry is found */ |
if ((retval = Mini_bkpt_rm (breakid)) != SUCCESS) { |
return(FAILURE); |
} else if (retval == SUCCESS) { |
/* remove breakpoint from table */ |
if (remove_from_table(breakid) != SUCCESS) { |
/* this shouldn't occur */ |
return(FAILURE); |
}; |
return(SUCCESS); |
}; |
|
} /* end clear_bkpt() */ |
|
|
|
/* |
** This function is used to set a breakpoint on the |
** target and in the host breakpoint table. |
*/ |
|
INT32 |
set_bkpt(addr_29k, pass_count, bkpt_type) |
struct addr_29k_t addr_29k; |
INT32 pass_count; |
INT32 bkpt_type; |
{ |
INT32 retval; |
int breakid; |
|
/* is there one already at the same place */ |
(void) match_entry(addr_29k.address, |
addr_29k.memory_space, |
&breakid); |
|
if (breakid > (int) 0) { |
warning (EMBKPTUSED); |
return (FAILURE); |
}; |
|
/* else set the breakpoint */ |
breakid = (int) 0; |
if ((retval = Mini_bkpt_set (addr_29k.memory_space, |
addr_29k.address, |
pass_count, |
bkpt_type, |
&breakid)) != SUCCESS) { |
return(FAILURE); |
} else { |
/* Add breakpoint to table */ |
if (breakid > (int) 0) { /* double checking */ |
return (add_to_table(addr_29k.address, |
addr_29k.memory_space, |
pass_count, |
bkpt_type, |
breakid)); |
}; |
return(FAILURE); |
}; |
} /* end set_bkpt() */ |
|
|
|
INT32 |
add_to_table(offset, space, passcnt, bktype, id ) |
ADDR32 offset; |
INT32 space; |
INT32 passcnt; |
INT32 bktype; |
int id; |
{ |
struct bkpt_t *temp, *temp2; |
|
if ((temp = (struct bkpt_t *) malloc (sizeof(struct bkpt_t))) == NULL) { |
return(EMALLOC); |
} else { |
temp->break_id = id; |
temp->memory_space = space; |
temp->address = offset; |
temp->pass_count = passcnt; |
temp->curr_count = passcnt; |
temp->bkpt_type = bktype; |
temp->next = NULL; |
}; |
|
if (bkpt_table == NULL) { /* first element */ |
bkpt_table = temp; |
} else { /* add at end */ |
temp2 = bkpt_table; |
while (temp2->next != NULL) |
temp2 = temp2->next; |
temp2->next = temp; /* add */ |
} |
return(SUCCESS); |
} |
|
INT32 |
match_entry(offset, space, id) |
ADDR32 offset; |
INT32 space; |
int *id; |
{ |
struct bkpt_t *temp; |
|
if (bkpt_table == NULL) { /* empty, so no match */ |
*id = (int) 0; |
return(SUCCESS); |
} else { |
temp = bkpt_table; |
if ((temp->address == offset) && |
(temp->memory_space == space)) { /* match */ |
*id = temp->break_id; |
return(SUCCESS); |
} else { |
while (temp->next != NULL) { |
if ((temp->next->address == offset) && |
(temp->next->memory_space == space)) { |
*id = temp->next->break_id; |
return(SUCCESS); |
} else { |
temp = temp->next; |
}; |
} |
*id = (int) 0; |
return(SUCCESS); |
}; |
}; |
} |
|
INT32 |
remove_from_table(id) |
int id; |
{ |
struct bkpt_t *temp; |
|
if (bkpt_table == NULL) { /* empty table */ |
return(FAILURE); |
} else { |
temp = bkpt_table; |
if (bkpt_table->break_id == id) { /* remove first element */ |
bkpt_table = bkpt_table->next; |
return(SUCCESS); |
} else { |
while (temp->next != NULL) { |
if (temp->next->break_id == id) { |
temp->next = temp->next->next; |
return(SUCCESS); |
} else { |
temp = temp->next; |
}; |
} |
return(FAILURE); |
}; |
} |
} |
|
INT32 |
clear_table() |
{ |
struct bkpt_t *tmp; |
INT32 retval; |
|
|
if (bkpt_table == NULL) { /* no entries */ |
fprintf(stderr, "no breakpoints in use.\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "no breakpoints in use.\n"); |
} else { |
while (bkpt_table) { |
if ((retval = Mini_bkpt_rm (bkpt_table->break_id)) != SUCCESS) { |
return(FAILURE); |
} else if (retval == SUCCESS) { |
/* remove breakpoint from table */ |
tmp = bkpt_table; |
bkpt_table = bkpt_table->next; |
(void) free ((char *) tmp); |
}; |
}; |
} |
return(SUCCESS); |
} |
|
INT32 |
show_table() |
{ |
struct bkpt_t *temp; |
INT32 retval; |
ADDR32 temp_addr; |
INT32 temp_space; |
INT32 curr_count; |
INT32 temp_passcnt, temp_bktype; |
int i; |
|
if (bkpt_table == NULL) { /* no entries */ |
} else { |
do { |
temp = bkpt_table; |
bkpt_table = bkpt_table->next; |
(void) free ((char *) temp); |
} while (bkpt_table != NULL); |
}; |
|
for (i = 1;1;i++) { |
retval = Mini_bkpt_stat( i, |
&temp_addr, |
&temp_space, |
&temp_passcnt, |
&temp_bktype, |
&curr_count); |
if ((retval == (INT32) MONBreakInvalid) || |
(retval == (INT32) FAILURE)) { |
continue; |
} else if (retval == (INT32) MONBreakNoMore) { |
return (SUCCESS); |
} else { |
/* add entry in the table */ |
if ((retval = add_to_table ((ADDR32) temp_addr, |
(INT32) temp_space, |
(INT32) temp_passcnt, |
(INT32) temp_bktype, |
i)) != SUCCESS) |
return (retval); |
/* Mark Am29050 breakpoints with a '*' */ |
if (temp_bktype == BKPT_29050) |
fprintf(stderr, "*"); |
else |
fprintf(stderr, " "); |
fprintf(stderr, "(%#05d: %#08lx[%#02d])\n", i, |
temp_addr, |
temp_passcnt); |
if (io_config.echo_mode == (INT32) TRUE) { |
if (temp_bktype == BKPT_29050) |
fprintf(io_config.echo_file, "*"); |
else |
fprintf(io_config.echo_file, " "); |
fprintf(io_config.echo_file, "(%#05d: %#08lx[%#02d])\n", i, |
temp_addr, |
temp_passcnt); |
} |
}; |
} |
return(SUCCESS); |
} |
|
/regs.c
0,0 → 1,167
static char _[] = "@(#)regs.c 5.20 93/07/30 16:38:58, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This file contains arrays of ASCII strings which represent |
** the register names for the the Am29000 processor. |
***************************************************************************** |
*/ |
|
char *reg[] = { |
"gr0", "gr1", "gr2", "gr3", |
"gr4", "gr5", "gr6", "gr7", |
"gr8", "gr9", "gr10", "gr11", |
"gr12", "gr13", "gr14", "gr15", |
"gr16", "gr17", "gr18", "gr19", |
"gr20", "gr21", "gr22", "gr23", |
"gr24", "gr25", "gr26", "gr27", |
"gr28", "gr29", "gr30", "gr31", |
"gr32", "gr33", "gr34", "gr35", |
"gr36", "gr37", "gr38", "gr39", |
"gr40", "gr41", "gr42", "gr43", |
"gr44", "gr45", "gr46", "gr47", |
"gr48", "gr49", "gr50", "gr51", |
"gr52", "gr53", "gr54", "gr55", |
"gr56", "gr57", "gr58", "gr59", |
"gr60", "gr61", "gr62", "gr63", |
"gr64", "gr65", "gr66", "gr67", |
"gr68", "gr69", "gr70", "gr71", |
"gr72", "gr73", "gr74", "gr75", |
"gr76", "gr77", "gr78", "gr79", |
"gr80", "gr81", "gr82", "gr83", |
"gr84", "gr85", "gr86", "gr87", |
"gr88", "gr89", "gr90", "gr91", |
"gr92", "gr93", "gr94", "gr95", |
"gr96", "gr97", "gr98", "gr99", |
"gr100", "gr101", "gr102", "gr103", |
"gr104", "gr105", "gr106", "gr107", |
"gr108", "gr109", "gr110", "gr111", |
"gr112", "gr113", "gr114", "gr115", |
"gr116", "gr117", "gr118", "gr119", |
"gr120", "gr121", "gr122", "gr123", |
"gr124", "gr125", "gr126", "gr127", |
"lr0", "lr1", "lr2", "lr3", |
"lr4", "lr5", "lr6", "lr7", |
"lr8", "lr9", "lr10", "lr11", |
"lr12", "lr13", "lr14", "lr15", |
"lr16", "lr17", "lr18", "lr19", |
"lr20", "lr21", "lr22", "lr23", |
"lr24", "lr25", "lr26", "lr27", |
"lr28", "lr29", "lr30", "lr31", |
"lr32", "lr33", "lr34", "lr35", |
"lr36", "lr37", "lr38", "lr39", |
"lr40", "lr41", "lr42", "lr43", |
"lr44", "lr45", "lr46", "lr47", |
"lr48", "lr49", "lr50", "lr51", |
"lr52", "lr53", "lr54", "lr55", |
"lr56", "lr57", "lr58", "lr59", |
"lr60", "lr61", "lr62", "lr63", |
"lr64", "lr65", "lr66", "lr67", |
"lr68", "lr69", "lr70", "lr71", |
"lr72", "lr73", "lr74", "lr75", |
"lr76", "lr77", "lr78", "lr79", |
"lr80", "lr81", "lr82", "lr83", |
"lr84", "lr85", "lr86", "lr87", |
"lr88", "lr89", "lr90", "lr91", |
"lr92", "lr93", "lr94", "lr95", |
"lr96", "lr97", "lr98", "lr99", |
"lr100", "lr101", "lr102", "lr103", |
"lr104", "lr105", "lr106", "lr107", |
"lr108", "lr109", "lr110", "lr111", |
"lr112", "lr113", "lr114", "lr115", |
"lr116", "lr117", "lr118", "lr119", |
"lr120", "lr121", "lr122", "lr123", |
"lr124", "lr125", "lr126", "lr127" |
}; |
|
char *spreg[] = { |
"vab", "ops", "cps", "cfg", |
"cha", "chd", "chc", "rbp", |
"tmc", "tmr", "pc0", "pc1", |
"pc2", "mmu", "lru", "rsn", |
"rma0", "rmc0", "rma1", "rmc1", |
"spc0", "spc1", "spc2", "iba0", |
"ibc0", "iba1", "ibc1", "sr27", |
"sr28", "cir", "cdr", "sr31", |
"sr32", "sr33", "sr34", "sr35", |
"sr36", "sr37", "sr38", "sr39", |
"sr40", "sr41", "sr42", "sr43", |
"sr44", "sr45", "sr46", "sr47", |
"sr48", "sr49", "sr50", "sr51", |
"sr52", "sr53", "sr54", "sr55", |
"sr56", "sr57", "sr58", "sr59", |
"sr60", "sr61", "sr62", "sr63", |
"sr64", "sr65", "sr66", "sr67", |
"sr68", "sr69", "sr70", "sr71", |
"sr72", "sr73", "sr74", "sr75", |
"sr76", "sr77", "sr78", "sr79", |
"sr80", "sr81", "sr82", "sr83", |
"sr84", "sr85", "sr86", "sr87", |
"sr88", "sr89", "sr90", "sr91", |
"sr92", "sr93", "sr94", "sr95", |
"sr96", "sr97", "sr98", "sr99", |
"sr100", "sr101", "sr102", "sr103", |
"sr104", "sr105", "sr106", "sr107", |
"sr108", "sr109", "sr110", "sr111", |
"sr112", "sr113", "sr114", "sr115", |
"sr116", "sr117", "sr118", "sr119", |
"sr120", "sr121", "sr122", "sr123", |
"sr124", "sr125", "sr126", "sr127", |
"ipc", "ipa", "ipb", "q", |
"alu", "bp", "fc", "cr", |
"sr136", "sr137", "sr138", "sr139", |
"sr140", "sr141", "sr142", "sr143", |
"sr144", "sr145", "sr146", "sr147", |
"sr148", "sr149", "sr150", "sr151", |
"sr152", "sr153", "sr154", "sr155", |
"sr156", "sr157", "sr158", "sr159", |
"fpe", "inte", "fps", "sr163", |
"exop", "sr165", "sr166", "sr167", |
"sr168", "sr169", "sr170", "sr171", |
"sr172", "sr173", "sr174", "sr175", |
"sr176", "sr177", "sr178", "sr179", |
"sr180", "sr181", "sr182", "sr183", |
"sr184", "sr185", "sr186", "sr187", |
"sr188", "sr189", "sr190", "sr191", |
"sr192", "sr193", "sr194", "sr195", |
"sr196", "sr197", "sr198", "sr199", |
"sr200", "sr201", "sr202", "sr203", |
"sr204", "sr205", "sr206", "sr207", |
"sr208", "sr209", "sr210", "sr211", |
"sr212", "sr213", "sr214", "sr215", |
"sr216", "sr217", "sr218", "sr219", |
"sr220", "sr221", "sr222", "sr223", |
"sr224", "sr225", "sr226", "sr227", |
"sr228", "sr229", "sr230", "sr231", |
"sr232", "sr233", "sr234", "sr235", |
"sr236", "sr237", "sr238", "sr239", |
"sr240", "sr241", "sr242", "sr243", |
"sr244", "sr245", "sr246", "sr247", |
"sr248", "sr249", "sr250", "sr251", |
"sr252", "sr253", "sr254", "sr255" |
}; |
|
/commands.c
0,0 → 1,602
static char _[] = " @(#)commands.c 5.23 93/08/23 15:30:30, Srini, AMD "; |
/****************************************************************************** |
* Copyright 1992 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This file contains the functions associated with |
** commands used by the main program. In general, |
** the commands in this file are fairly simple and |
** were not given a source file of their own. |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <ctype.h> |
#include "memspcs.h" |
#include "main.h" |
#include "monitor.h" |
#include "macros.h" |
#include "help.h" |
#include "miniint.h" |
#include "error.h" |
|
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
#else |
#include <strings.h> |
#endif |
|
|
extern int get_addr_29k PARAMS((char *, struct addr_29k_t *)); |
extern int addr_29k_ok PARAMS((struct addr_29k_t *)); |
|
extern int get_word PARAMS((char *, INT32 *)); |
|
/* |
** Global variables |
*/ |
|
static char *processor_name[] = { |
/* 0 */ "Am29000", |
/* 1 */ "Am29005", |
/* 2 */ "Am29050", |
/* 3 */ "Am29035", |
/* 4 */ "Am29030", |
/* 5 */ "Am29200", |
/* 6 */ "Am29240", |
/* 7 */ "Cougar", |
/* 8 */ "TBA", |
/* 9 */ "TBA" |
}; |
#define NO_PROCESSOR 9 |
|
static char *coprocessor_name[] = { |
/* 0 */ "None", |
/* 1 */ "Am29027 (revision A)", |
}; |
|
static char *io_control_name[] = { |
/* 0 */ "Console controlled by target.", |
/* 1 */ "Console controlled by host." |
}; |
|
|
|
/* |
** This command is used to print out the configuration |
** of the system. This includes both host and target |
** configurations. |
** |
** This command also re-allocates the message buffers |
** and the breakpoint array. This permits this command |
** to be used to re-configure the host for a new target |
** without restarting the monitor. This is useful in cases |
** where the target is reset or changed. |
*/ |
|
INT32 |
config_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int processor; |
int coprocessor; |
char revision; |
char prtbuf[256]; |
|
INT32 retval; |
|
|
/* Get target CONFIG */ |
if ((retval = Mini_config_req(&target_config, &versions_etc)) != SUCCESS) { |
return(retval); |
}; |
/* If returned SUCCESSfully do the rest */ |
|
|
|
/* Print out configuration information |
** Note: a -1 is no coprocessor present, 0 is an |
** Am29027 (revision A), etc ... To get |
** the array index for the coprocessor_name, |
** add one to the target_config.coprocessor. |
*/ |
|
/* ----------------------------------------------------------------- */ |
sprintf(&prtbuf[0], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], " MiniMON29K R 3.0 Debugger Front End.\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* ----------------------------------------------------------------- */ |
sprintf(&prtbuf[0], " Copyright 1993 Advanced Micro Devices, Inc.\n"); |
sprintf(&prtbuf[strlen(prtbuf)], " Version %s (%s)\n", |
host_config.version, |
host_config.date); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* ----------------------------------------------------------------- */ |
sprintf(&prtbuf[0], "\n"); |
if (target_config.processor_id == (UINT32) -1) |
sprintf(&prtbuf[strlen(prtbuf)], "\tProcessor type: %s \n", processor_name[NO_PROCESSOR]); |
|
else { |
|
if ((target_config.processor_id & 0x58) == 0x58) { |
revision = (char) ('A' + (target_config.processor_id & 0x07)); |
sprintf(&prtbuf[strlen(prtbuf)], "\tProcessor type: %s (revision %c)\n", "Am29205", (char) revision); |
|
} else { |
|
processor = (int) (target_config.processor_id >> 4); |
revision = (char) ('A' + (target_config.processor_id & 0x0f)); |
sprintf(&prtbuf[strlen(prtbuf)], "\tProcessor type: %s (revision %c)\n", processor_name[processor], revision); |
|
} |
|
} |
|
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
/* ----------------------------------------------------------------- */ |
coprocessor = (int) target_config.coprocessor + 1; |
sprintf(&prtbuf[0], "\tCoprocessor: %s\n", |
coprocessor_name[coprocessor]); |
/* ----------------------------------------------------------------- */ |
if ((target_config.ROM_start == (ADDR32) -1) && |
(target_config.ROM_size == (INT32) -1)) { |
sprintf(&prtbuf[strlen(prtbuf)], "\tROM range: Unavailable\n"); |
} else { |
sprintf(&prtbuf[strlen(prtbuf)], "\tROM range: 0x%lx to 0x%lx (%luK)\n", |
target_config.ROM_start, |
(target_config.ROM_start + (ADDR32) target_config.ROM_size - 1), |
(unsigned long) target_config.ROM_size/1024); |
} |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
/* ----------------------------------------------------------------- */ |
if ((target_config.I_mem_start == (ADDR32) -1) && |
(target_config.I_mem_size == (INT32) -1)) { |
sprintf(&prtbuf[0], "\tInstruction memory range: Unavailable\n"); |
} else { |
sprintf(&prtbuf[0], "\tInstruction memory range: 0x%lx to 0x%lx (%luK)\n", |
target_config.I_mem_start, |
(target_config.I_mem_start + (ADDR32) target_config.I_mem_size - 1), |
(unsigned long) target_config.I_mem_size/1024); |
} |
/* ----------------------------------------------------------------- */ |
if ((target_config.D_mem_start == (ADDR32) -1) && |
(target_config.D_mem_size == (INT32) -1)) { |
sprintf(&prtbuf[strlen(prtbuf)], "\tData memory range: Unavailable\n"); |
} else { |
sprintf(&prtbuf[strlen(prtbuf)], "\tData memory range: 0x%lx to 0x%lx (%luK)\n", |
target_config.D_mem_start, |
(target_config.D_mem_start + (ADDR32) target_config.D_mem_size - 1), |
(unsigned long) target_config.D_mem_size/1024); |
} |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
/* ----------------------------------------------------------------- */ |
sprintf(&prtbuf[0], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\t (Enter 'h' or '?' for help)\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
/* ----------------------------------------------------------------- */ |
|
return (SUCCESS); |
|
} /* end config_cmd() */ |
|
|
|
|
/* |
** This command is used to print out help information. |
*/ |
|
INT32 |
help_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int i; |
char **help_ptr; |
|
if (((strcmp(token[0], "h") != 0) && |
(strcmp(token[0], "?") != 0)) || |
(token_count > 2)) |
return (EMSYNTAX); |
|
if (token_count == 1) { |
help_ptr = help_main; |
} |
else |
/* Print command-specific help line */ |
if (token_count == 2) |
switch (*token[1]) { |
case 'a': help_ptr = help_a; |
break; |
case 'b': help_ptr = help_b; |
break; |
case 'c': |
if (strcmp(token[1], "caps") == 0) |
help_ptr = help_caps; |
else if (strcmp(token[1], "cp") == 0) |
help_ptr = help_cp; |
else if (strcmp(token[1], "con") == 0) |
help_ptr = help_con; |
else if (strcmp(token[1], "ch0") == 0) |
help_ptr = help_ch0; |
else |
help_ptr = help_c; |
break; |
case 'd': help_ptr = help_d; |
if (strcmp(token[1], "disc") == 0) |
help_ptr = help_disc; |
else if (strcmp(token[1], "dp") == 0) |
help_ptr = help_dp; |
break; |
case 'e': help_ptr = help_e; |
if (strcmp(token[1], "ex") == 0) |
help_ptr = help_ex; |
else if (strcmp(token[1], "esc") == 0) |
help_ptr = help_esc; |
else if (strcmp(token[1], "eon") == 0) |
help_ptr = help_eon; |
else if (strcmp(token[1], "eoff") == 0) |
help_ptr = help_eon; |
break; |
case 'f': help_ptr = help_f; |
break; |
case 'g': help_ptr = help_g; |
break; |
case 'h': help_ptr = help_h; |
break; |
case 'i': help_ptr = help_i; |
if (strcmp (token[1],"init") == 0) |
help_ptr = help_init; |
break; |
case 'k': help_ptr = help_k; |
break; |
case 'l': help_ptr = help_l; |
if (strcmp (token[1], "logon") == 0) |
help_ptr = help_logon; |
else if (strcmp (token[1], "logoff") == 0) |
help_ptr = help_logon; |
break; |
case 'm': help_ptr = help_m; |
break; |
case 'p': help_ptr = help_pid; |
break; |
case 'q': help_ptr = help_q; |
if (strcmp(token[1], "qon") == 0) |
help_ptr = help_qoff; |
else if (strcmp(token[1], "qoff") == 0) |
help_ptr = help_qoff; |
break; |
case 'r': help_ptr = help_r; |
break; |
case 's': help_ptr = help_s; |
if (strcmp(token[1], "sid") == 0) |
help_ptr = help_sid; |
break; |
case 't': help_ptr = help_t; |
if (strcmp(token[1], "tip") == 0) |
help_ptr = help_tip; |
break; |
case 'x': help_ptr = help_x; |
break; |
case 'y': help_ptr = help_y; |
break; |
case 'z': help_ptr = help_zc; |
if (strcmp(token[1], "ze") == 0) |
help_ptr = help_ze; |
else if (strcmp(token[1], "zl") == 0) |
help_ptr = help_zl; |
break; |
default: help_ptr = help_main; |
break; |
} /* end switch */ |
else |
/* Too many parameters */ |
return (EMSYNTAX); |
|
|
i=0; |
while (*help_ptr[i] != '\0') { |
fprintf(stderr, "\n%s", help_ptr[i]); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "\n%s", help_ptr[i]); |
i=i+1; |
} /* end while */ |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (SUCCESS); |
} /* end help_cmd() */ |
|
|
|
/* |
** This command toggles control of the keyboard between |
** TERM_USER and TERM_29K. |
** |
** IMPORTANT NOTE |
** This command is no longer used. It was an attempt to |
** toggle control between the host and the target when the |
** target is displaying output and accepting input. |
** The UDI methodology allows this control to be handled by the |
** UDIWait procedures. Hence, this io_toggle_cmd is not used. |
** It is left here only as an historical anomoly |
** |
** The i command is now used for ix, ia, il the 2903x cashe |
** which is contained in the monitor.c code. |
** END OF IMPORTANT NOTE |
*/ |
|
INT32 |
io_toggle_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
|
if ((strcmp(token[0], "io_toggle") != 0) || |
(token_count != 1)) |
return (EMSYNTAX); |
|
if (io_config.io_control == TERM_29K) |
io_config.io_control = TERM_USER; |
else |
if (io_config.io_control == TERM_USER) |
io_config.io_control = TERM_29K; |
else |
return(EMFAIL); |
|
fprintf(stderr, "%s\n", io_control_name[io_config.io_control]); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s\n", io_control_name[io_config.io_control]); |
|
return(0); |
|
} /* end io_toggle_cmd() */ |
|
|
|
|
/* |
** This command send a BREAK message to the target. This |
** should halt execution of user code. A HALT message should |
** be returned by the target. This function deos not, however, |
** wait for the HALT message. |
*/ |
|
INT32 |
kill_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int result; |
INT32 retval; |
|
result = -1; |
if ((strcmp(token[0], "k") != 0) || |
(token_count != 1)) |
return (EMSYNTAX); |
|
if ((retval = Mini_break()) != SUCCESS) { |
return(FAILURE); |
}; |
return(SUCCESS); |
|
} /* end kill_cmd() */ |
|
|
|
/* |
** This command send a RESET message to the target. This |
** should restart the target code. A HALT message should |
** be returned by the target. This function deos not, however, |
** wait for the HALT message. |
*/ |
|
INT32 |
reset_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int result; |
INT32 retval; |
|
result = -1; |
if ((strcmp(token[0], "r") != 0) || |
(token_count != 1)) |
return (EMSYNTAX); |
|
if ((retval = Mini_reset_processor()) != SUCCESS) { |
return(FAILURE); |
} else |
return(SUCCESS); |
|
} /* end reset_cmd() */ |
|
|
|
|
|
|
|
/* |
** This command is used to display the versions of the various |
** MINIMON 29K modules. First the version of the host code and |
** its date is printed from the global data structure "host_config". |
** Next the montip version field and date is printed from |
** the VERSION_SPACE UDIRead call. This is an ascii zero terminated |
** field of ** less than 11 characters. |
** Next the "version" field in the "target_config" data structure is |
** printed. This "version field is encoded as follows: |
** |
** Bits 0 - 7: Target debug core version |
** Bits 8 - 15: Configuration version |
** Bits 16 - 23: Message system version |
** Bits 24 - 31: Communication driver version |
** |
** Each eight bit field is further broken up into two four bit |
** fields. The first four bits is the "release" number, the |
** second is the "version" number. This is typically printed |
** as <version>.<release>. i.e. version=2, release=6 is |
** printed as "2.6". |
** |
*/ |
|
/* |
** The os version number is coded into the eighth word of the |
**configuration message. It is in the lower 8 bits. |
** Bits 0 - 7: OS version |
** |
*/ |
|
INT32 |
version_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int comm_version; |
int message_version; |
int config_version; |
int debug_core_version; |
char tip_version[12]; |
char tip_date[12]; |
int os_version; /* eighth word of config message */ |
INT32 junk; |
char prtbuf[256]; |
INT32 retval; |
|
if ((strcmp(token[0], "ver") != 0) || |
(token_count != 1)) |
return (EMSYNTAX); |
|
/* byte count is 40 because 4 bytes for target version |
4 bytes for os version |
12 bytes for tip version |
12 bytes for tip date |
4 for msgbuf size |
4 for max bkpts */ |
if ((retval = Mini_read_req ((INT32) VERSION_SPACE, |
(ADDR32) 0, |
(INT32) 1, |
(INT16) 40, |
(INT32 *) &junk, |
(BYTE *) &(versions_etc.version), |
TRUE)) != SUCCESS) |
return (FAILURE); |
|
comm_version = (int) ((versions_etc.version >> 24) & 0x00ff); |
message_version = (int) ((versions_etc.version >> 16) & 0x00ff); |
config_version = (int) ((versions_etc.version >> 8) & 0x00ff); |
debug_core_version = (int) ((versions_etc.version) & 0x00ff); |
strcpy(tip_version,versions_etc.tip_version); |
strcpy(tip_date,versions_etc.tip_date); |
os_version = (int) ((versions_etc.os_version ) & 0x00ff); |
|
|
sprintf(&prtbuf[0], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], " MiniMON29K R3.0\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], " Copyright 1993 Advanced Micro Devices, Inc.\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
|
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "\t Host code:\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Version %s\n", |
host_config.version); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Date: %s\n", |
host_config.date); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
sprintf(&prtbuf[0], "\t Tip code:\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Version %s\n", |
tip_version); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Date: %s\n", |
tip_date); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
sprintf(&prtbuf[0], "\t Target code:\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Debug core version: %d.%d\n", |
((debug_core_version >> 4) & 0x0f), |
(debug_core_version & 0x0f)); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Configuration version: %d.%d\n", |
((config_version >> 4) & 0x0f), |
(config_version & 0x0f)); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Message system version: %d.%d\n", |
((message_version >> 4) & 0x0f), |
(message_version & 0x0f)); |
sprintf(&prtbuf[strlen(prtbuf)], "\t\t Communication driver version: %d.%d\n", |
((comm_version >> 4) & 0x0f), |
(comm_version & 0x0f)); |
|
sprintf(&prtbuf[strlen(prtbuf)], "\t\t OS system version: %d.%d\n", |
((os_version >> 4) & 0x0f), |
(os_version & 0x0f)); |
|
|
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
fprintf(stderr, "Maximum message buffer size on target: 0x%lx\n",versions_etc.max_msg_size); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Maximum message buffer size on target: 0x%lx\n",versions_etc.max_msg_size); |
fprintf(stderr, "Maximum number of breakpoints on target: %ld\n", versions_etc.max_bkpts); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Maximum message buffer size on target: 0x%lx\n",versions_etc.max_msg_size); |
return (SUCCESS); |
|
} /* end version_cmd() */ |
|
|
|
/Makefile.in
0,0 → 1,116
# |
# Makefile for utils/amd-udi/mondfe |
# Copyright (C) 1993 Free Software Foundation |
# |
# This file 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 of the License, or |
# (at your option) any later version. |
# |
# This program 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 this program; if not, write to the Free Software |
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
# |
# $Id: Makefile.in,v 1.1.1.1 2001-05-18 11:27:35 markom Exp $ |
# |
# Written by Jeffrey Wheat (cassidy@cygnus.com) |
# |
|
#### Start of system configuration section. #### |
|
srcdir = @srcdir@ |
VPATH = @srcdir@ |
|
CC = @CC@ |
|
INSTALL = @INSTALL@ |
INSTALL_PROGRAM = @INSTALL_PROGRAM@ |
INSTALL_DATA = @INSTALL_DATA@ |
|
DEFS = @DEFS@ |
LIBS = @LIBS@ |
RANLIB = @RANLIB@ |
|
AR = ar |
AR_FLAGS = cq |
|
CFLAGS = -g |
|
LD = ld |
LDFLAGS = -g |
|
MV = mv |
RM = rm |
|
prefix = /usr/local |
exec_prefix = $(prefix) |
|
bindir = $(exec_prefix)/bin |
libdir = $(exec_prefix)/lib |
|
mandir = $(prefix)/man |
man1dir = $(mandir)/man1 |
man2dir = $(mandir)/man2 |
man3dir = $(mandir)/man3 |
man4dir = $(mandir)/man4 |
man5dir = $(mandir)/man5 |
man6dir = $(mandir)/man6 |
man7dir = $(mandir)/man7 |
man8dir = $(mandir)/man8 |
|
SHELL = /bin/sh |
|
INSTALL = install -c |
INSTALL_DATA = $(INSTALL) |
INSTALL_PROGRAM = $(INSTALL) |
|
#### End of system configuration section. #### |
|
OBJS = main.o monitor.o error.o help.o commands.o asm.o \ |
opcodes.o regs.o bkpt.o dasm.o fill.o move.o \ |
set.o xcmd.o yank.o dump.o getdata.o io.o icmd.o mini2udi.o |
|
LIBDFE = ../udi/libdfe.a |
|
INCLUDE = -I$(srcdir)/../udi -I$(srcdir)/../include |
|
.c.o: |
$(CC) $(INCLUDE) $(DEFS) $(CFLAGS) -c $< |
|
all: mondfe |
|
mondfe: $(LIBUDIDFE) $(OBJS) |
$(CC) $(LDFLAGS) -o $@ $(OBJS) $(LIBDFE) $(LIBIBERTY) |
|
install: all |
|
mostlyclean clean: |
$(RM) -f *.o mondfe |
|
distclean maintainer-clean realclean: clean |
$(RM) -f Makefile config.status |
|
.PHONY: check installcheck info install-info clean-info dvi |
|
check installcheck: |
|
info install-info clean-info dvi: |
|
# with the gnu make, this is done automatically. |
|
Makefile: Makefile.in |
$(SHELL) ./config.status |
|
config.status: configure |
$(srcdir)/configure --no-create |
|
configure: configure.in |
autoconf |
|
# Prevent GNU make v3 from overflowing arg limit on SysV. |
.NOEXPORT: |
/yank.c
0,0 → 1,548
static char _[] = "@(#)yank.c 5.20 93/07/30 16:39:05, Srini, AMD. "; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This module is used to "yank" or load a COFF file |
** Into target memory. |
***************************************************************************** |
*/ |
|
|
#include <stdio.h> |
#include <memory.h> |
#include <ctype.h> |
#include "coff.h" |
#include "memspcs.h" |
#include "main.h" |
#include "miniint.h" |
#include "macros.h" |
#include "error.h" |
|
#ifdef MSDOS |
#include <string.h> |
#include <stdlib.h> |
#else |
#include <string.h> |
#endif |
|
/* Definitions */ |
|
#define FILE_BUFFER_SIZE 1024 |
|
#ifdef MSDOS |
#define FILE_OPEN_FLAG "rb" |
#else |
#define FILE_OPEN_FLAG "r" |
#endif |
|
#define FROM_BEGINNING 0 |
|
/* Function declarations */ |
INT32 Mini_load_coff PARAMS((char *fname, |
INT32 space, |
INT32 sym, |
INT32 sects, |
int msg)); |
INT32 Mini_init_info_ptr PARAMS((INIT_INFO *init)); |
INT32 Mini_send_init_info PARAMS((INIT_INFO *init)); |
INT32 Mini_load_file PARAMS((char *fname, |
INT32 mspace, |
int fargc, |
char *fargs, |
INT32 sym, |
INT32 sects, |
int msg)); |
void convert32 PARAMS((BYTE *)); |
void convert16 PARAMS((BYTE *)); |
int SetSections PARAMS((char *)); |
void print_ld_msg PARAMS((INT32, int, ADDR32, INT32)); |
void print_ign_msg PARAMS((int, ADDR32, INT32)); |
void print_end_msg PARAMS((INT32, int, ADDR32, INT32)); |
|
/* GLobal */ |
|
GLOBAL INIT_INFO init_info; |
|
static BYTE buffer[FILE_BUFFER_SIZE]; |
extern char CoffFileName[]; |
static INT32 Symbols=0; /* No symbols support yet */ |
static INT32 Sections=STYP_ABS | STYP_TEXT | STYP_DATA | STYP_LIT | STYP_BSS; |
static INT32 MSpace=I_MEM; |
static int FileArgc; |
static char ArgString[1024]; |
static FILE *coff_in; |
static int InitializeProgram=1; |
|
|
/* |
** This is the function called by the main program to load |
** a COFF file. It also modifies the global data structure |
** init. The data structure is then sent via an INIT message |
** to the target. In addition, the "argv" parameter string |
** is sent to the target with WRITE messages. |
** |
*/ |
|
INT32 |
yank_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int i; |
int j; |
int SectionsGiven=0; |
int IPFlag=0; |
|
for (j=1; j < token_count; j++) { /* parse command */ |
switch (token[j][0]) { |
case '-': |
if (token[j][1] == '\0') |
return (EMSYNTAX); |
if (strcmp(token[j],"-ms")==0) {/*mem stack opt */ |
if (++j >= token_count) |
return (EMSYNTAX); |
if (sscanf(token[j],"%lx",&(init_info.mem_stack_size)) != 1) |
return (EMSYNTAX); |
} else if (strcmp(token[j],"-rs")==0) {/*r stack*/ |
if (++j >= token_count) |
return (EMSYNTAX); |
if (sscanf(token[j],"%lx",&(init_info.reg_stack_size)) != 1) |
return (EMSYNTAX); |
} else if (strcmp(token[j],"-noi")==0) {/*no init */ |
InitializeProgram = 0; |
IPFlag = 1; |
} else if (strcmp(token[j],"-i")==0) {/*init*/ |
InitializeProgram = 1; |
IPFlag = 1; |
} else { |
if (SetSections(token[j]) == (int) -1) |
return (EMSYNTAX); |
else |
SectionsGiven=1; |
} |
break; |
default: /* filename etc. */ |
if (!SectionsGiven) { |
Sections = STYP_ABS|STYP_TEXT|STYP_DATA|STYP_LIT|STYP_BSS; |
SectionsGiven=0; |
} |
if (!IPFlag) { |
InitializeProgram = 1; |
IPFlag=0; |
} |
(void) strcpy (&CoffFileName[0], token[j]); |
FileArgc = token_count - j; |
(void) strcpy(ArgString, token[j]); |
for (i = 1; i < FileArgc; i++) { |
strcat(ArgString, " "); |
strcat(ArgString, token[j+i]); |
}; |
j = token_count; /* break out of for loop */ |
break; |
}; |
} |
if (strcmp(CoffFileName,"") == 0) /* No COFF file given */ |
return (EMSYNTAX); |
|
if (Mini_load_file(&CoffFileName[0], MSpace, |
FileArgc, ArgString, |
Symbols, Sections, |
QuietMode) != SUCCESS) { |
return(FAILURE); |
} else |
return(SUCCESS); |
}; |
|
|
INT32 |
Mini_load_file(filename, mspace, fileargc, fileargs, sym, sects, quietmode) |
char *filename; |
INT32 mspace; |
int fileargc; |
char *fileargs; |
INT32 sym; |
INT32 sects; |
int quietmode; |
{ |
|
if (Mini_init_info_ptr(&init_info) != SUCCESS) |
return(FAILURE); |
|
if (Mini_load_coff(filename, mspace, sym, sects, quietmode) != SUCCESS) |
return(FAILURE); |
|
init_info.argstring = fileargs; /* complete argv string */ |
|
if (InitializeProgram) { |
if (Mini_send_init_info(&init_info) != SUCCESS) |
return(FAILURE); |
} else { |
warning(EMNOINITP); |
} |
|
return(SUCCESS); |
}; |
|
INT32 |
Mini_init_info_ptr(init_ptr) |
INIT_INFO *init_ptr; |
{ |
|
/* Re-initialize INIT message */ |
init_ptr->text_start = 0xffffffff; |
init_ptr->text_end = 0; |
init_ptr->data_start = 0xffffffff; |
init_ptr->data_end = 0; |
init_ptr->entry_point = 0; |
if (init_ptr->mem_stack_size == (UINT32) -1) |
init_ptr->mem_stack_size = MEM_STACK_SIZE; |
if (init_ptr->reg_stack_size == (UINT32) -1) |
init_ptr->reg_stack_size = REG_STACK_SIZE; |
init_ptr->argstring = (char *) 0; |
return(SUCCESS); |
}; |
|
|
INT32 |
Mini_send_init_info(info_ptr) |
INIT_INFO *info_ptr; |
{ |
INT32 retval; |
|
/* Align INIT values to word boundaries */ |
info_ptr->text_start = ALIGN32(info_ptr->text_start); |
info_ptr->text_end = ALIGN32(info_ptr->text_end); |
info_ptr->data_start = ALIGN32(info_ptr->data_start); |
info_ptr->data_end = ALIGN32(info_ptr->data_end); |
info_ptr->mem_stack_size = ALIGN32(info_ptr->mem_stack_size); |
info_ptr->reg_stack_size = ALIGN32(info_ptr->reg_stack_size); |
|
/* Send INIT message */ |
|
if ((retval = Mini_init (info_ptr->text_start, |
info_ptr->text_end, |
info_ptr->data_start, |
info_ptr->data_end, |
info_ptr->entry_point, |
info_ptr->mem_stack_size, |
info_ptr->reg_stack_size, |
info_ptr->argstring)) != SUCCESS) { |
warning(EMINIT); |
return(FAILURE); |
}; |
return (SUCCESS); |
|
} /* Mini_send_init_info */ |
|
|
|
/* |
** This function is used to load a COFF file. Depending on |
** the global variable "target_interface", data will be loaded |
** by either EB29K shared memory, PCEB shared memory, EB030 |
** shared memory or serially. |
** |
** In addition, the global data structure "init" is updated. |
** This data structure maintains the entry point and various |
** other target initialization parameters. |
*/ |
|
INT32 |
Mini_load_coff(filename, mspace, sym, Section, quietmode) |
char *filename; |
int quietmode; |
INT32 sym; |
INT32 Section; |
INT32 mspace; |
{ |
unsigned short COFF_sections; |
INT32 flags; |
INT32 memory_space; |
INT32 address; |
INT32 byte_count; |
INT32 temp_byte_count; |
INT32 bytes_ret; |
|
struct filehdr COFF_header; |
struct aouthdr COFF_aout_header; |
struct scnhdr COFF_section_header; |
|
if (!quietmode) { |
fprintf(stderr, "loading %s\n", filename); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "loading %s\n", filename); |
} |
|
/* Open the COFF input file (if we can) */ |
if ((coff_in = fopen(filename, FILE_OPEN_FLAG)) == NULL) { |
warning (EMOPEN); return(FAILURE); |
}; |
|
/* Read in COFF header information */ |
if (fread((char *)&COFF_header, sizeof(struct filehdr), 1, coff_in) != 1) { |
fclose(coff_in); warning(EMHDR); return (FAILURE); |
}; |
|
|
/* Is it an Am29000 COFF File? */ |
if ((COFF_header.f_magic != 0x17a) && (COFF_header.f_magic != 0x7a01) && |
(COFF_header.f_magic != 0x17b) && (COFF_header.f_magic != 0x7b01)) { |
fclose(coff_in); warning (EMMAGIC); return (FAILURE); |
} |
|
/* Get number of COFF sections */ |
if ((COFF_header.f_magic != 0x17a) && (COFF_header.f_magic != 0x017b)) |
convert16((BYTE *) &COFF_header.f_nscns); |
COFF_sections = (unsigned short) COFF_header.f_nscns; |
|
/* Read in COFF a.out header information (if we can) */ |
if (COFF_header.f_opthdr > 0) { |
if (fread((char *)&COFF_aout_header, sizeof(struct aouthdr), |
1, coff_in) != 1) { |
fclose(coff_in); warning (EMAOUT); return (FAILURE); |
}; |
/* Set entry point in INIT message */ |
init_info.entry_point = COFF_aout_header.entry; |
if ((COFF_header.f_magic != 0x17a) && (COFF_header.f_magic != 0x017b)) { |
convert16((BYTE *) &COFF_header.f_opthdr); |
convert32((BYTE *) &init_info.entry_point); |
} |
} |
|
|
/* |
** Process COFF section headers |
*/ |
|
/* Process all sections */ |
while ((int) COFF_sections--) { |
|
fseek (coff_in, (long) (FILHSZ+(int)COFF_header.f_opthdr+ |
SCNHSZ*(COFF_header.f_nscns-COFF_sections-1)), |
FROM_BEGINNING); |
|
if (fread(&COFF_section_header, 1, SCNHSZ, coff_in) != SCNHSZ) { |
fclose(coff_in); warning (EMSCNHDR); return (FAILURE); |
} |
|
if ((COFF_header.f_magic != 0x17a) && (COFF_header.f_magic != 0x017b)) { |
convert32((BYTE *) &(COFF_section_header.s_paddr)); |
convert32((BYTE *) &(COFF_section_header.s_scnptr)); |
convert32((BYTE *) &(COFF_section_header.s_size)); |
convert32((BYTE *) &(COFF_section_header.s_flags)); |
} |
|
address = COFF_section_header.s_paddr; |
byte_count = COFF_section_header.s_size; |
flags = COFF_section_header.s_flags; |
|
/* Print downloading messages (if necessary) */ |
if ((flags == (INT32) STYP_TEXT) || (flags == (INT32) (STYP_TEXT | STYP_ABS))) { |
memory_space = I_MEM; |
init_info.text_start = MIN((ADDR32) address, |
(ADDR32) init_info.text_start); |
init_info.text_end = MAX((ADDR32) (address + byte_count), |
(ADDR32) init_info.text_end); |
} else if ((flags == (INT32) STYP_DATA) || (flags == (INT32) (STYP_DATA | STYP_ABS)) || |
(flags == (INT32) STYP_LIT) || (flags == (INT32) (STYP_LIT | STYP_ABS)) || |
(flags == (INT32) STYP_BSS) || (flags == (INT32) (STYP_BSS | STYP_ABS))) { |
memory_space = D_MEM; |
init_info.data_start = MIN((ADDR32) address, |
(ADDR32) init_info.data_start); |
init_info.data_end = MAX((ADDR32) (address + byte_count), |
(ADDR32) init_info.data_end); |
} else { |
print_ign_msg(quietmode, address, byte_count); |
flags = (INT32) 0; |
} |
|
if ((flags == (INT32) STYP_BSS) || (flags == (INT32) (STYP_BSS | STYP_ABS))) { |
/* Clear BSS section */ |
if (flags & Section) { |
print_ld_msg(flags,quietmode,address,byte_count); |
if (Mini_fill ((INT32) D_MEM, |
(ADDR32) address, |
(INT32) (byte_count+3)/4, |
4 /* fill zeroes */, |
"\0\0\0") != SUCCESS) { |
(void) fclose(coff_in); warning(EMFILL); return(FAILURE); |
}; |
print_end_msg(flags,quietmode,address,byte_count); |
} |
} else if (flags & Section) { /* not a BSS or COmment */ |
if (flags == (INT32) (flags & Section)) { |
fseek (coff_in, COFF_section_header.s_scnptr, FROM_BEGINNING); |
while (byte_count > 0) { |
temp_byte_count = MIN((INT32) byte_count, (INT32) sizeof(buffer)); |
if (fread((char *) buffer, (int) temp_byte_count, 1, coff_in) != 1) { |
fclose(coff_in); warning (EMSCN); return (FAILURE); |
}; |
print_ld_msg(flags, quietmode,address, temp_byte_count); |
/* Write to 29K memory*/ |
if (Mini_write_req ((INT32) memory_space, |
(ADDR32) address, |
(INT32) (temp_byte_count+3)/4, |
(INT16) 4, /* size */ |
&bytes_ret, |
(BYTE *) buffer, |
(INT32) FALSE) != SUCCESS) { |
warning(EMWRITE); |
return(FAILURE); |
} |
address = address + temp_byte_count; |
byte_count = byte_count - temp_byte_count; |
}; |
print_end_msg(flags, quietmode, COFF_section_header.s_paddr, |
COFF_section_header.s_size); |
}; |
} |
} /* end while */ |
|
(void) fclose(coff_in); |
return (SUCCESS); |
|
} /* end Mini_loadcoff() */ |
|
|
int |
SetSections(string) |
char *string; |
{ |
int i; |
|
if (string[0] != '-') |
return (-1); /* not section options */ |
|
Sections = STYP_ABS; |
for (i=1; string[i] != '\0'; i++) { |
switch (string[i]) { |
case 't': |
case 'T': |
Sections = Sections | STYP_TEXT; |
break; |
case 'd': |
case 'D': |
Sections = Sections | STYP_DATA; |
break; |
case 'b': |
case 'B': |
Sections = Sections | STYP_BSS; |
break; |
case 'l': |
case 'L': |
Sections = Sections | STYP_LIT; |
break; |
default: |
return (EMSYNTAX); |
} |
} |
return (0); |
} |
|
void |
print_ld_msg(flags, mode, address, byte_count) |
INT32 flags; |
int mode; |
ADDR32 address; |
INT32 byte_count; |
{ |
if (!mode) { |
if (flags & (INT32) STYP_BSS) |
fprintf(stderr, "Clearing "); |
else |
fprintf(stderr, "Loading "); |
|
if ((flags == (INT32) STYP_TEXT) || (flags == (INT32) (STYP_TEXT|STYP_ABS))) |
fprintf(stderr, "TEXT "); |
else if (flags & (INT32) STYP_DATA) |
fprintf(stderr, "DATA "); |
else if (flags & (INT32) STYP_LIT) |
fprintf(stderr, "LIT "); |
else if (flags & (INT32) STYP_BSS) |
fprintf(stderr, "BSS "); |
fprintf(stderr, "section from 0x%08lx to 0x%08lx\r", |
address, (ADDR32) (address+byte_count)); |
} |
} |
|
void |
print_ign_msg(mode, address, byte_count) |
int mode; |
ADDR32 address; |
INT32 byte_count; |
{ |
if (!mode) |
fprintf(stderr, "Ignoring COMMENT section (%ld bytes) ...\n", byte_count); |
} |
|
void |
print_end_msg(flags, mode,address,size) |
INT32 flags; |
int mode; |
ADDR32 address; |
INT32 size; |
{ |
if (!mode) { |
if (flags & (INT32) STYP_BSS) |
fprintf(stderr, "Cleared "); |
else |
fprintf(stderr, "Loaded "); |
if (io_config.echo_mode == (INT32) TRUE) { |
if (flags & (INT32) STYP_BSS) |
fprintf(io_config.echo_file, "Cleared "); |
else |
fprintf(io_config.echo_file, "Loaded "); |
} |
|
if ((flags == (INT32) STYP_TEXT) || |
(flags == (INT32) (STYP_TEXT|STYP_ABS))) |
fprintf(stderr, "TEXT "); |
else if (flags & (INT32) STYP_DATA) |
fprintf(stderr, "DATA "); |
else if (flags & (INT32) STYP_LIT) |
fprintf(stderr, "LIT "); |
else if (flags & (INT32) STYP_BSS) |
fprintf(stderr, "BSS "); |
|
fprintf(stderr, "section from 0x%08lx to 0x%08lx\n", |
address, (ADDR32) (address+size)); |
if (io_config.echo_mode == (INT32) TRUE) { |
if ((flags == (INT32) STYP_TEXT) || |
(flags == (INT32) (STYP_TEXT|STYP_ABS))) |
fprintf(io_config.echo_file, "TEXT "); |
else if (flags & (INT32) STYP_DATA) |
fprintf(io_config.echo_file, "DATA "); |
else if (flags & (INT32) STYP_LIT) |
fprintf(io_config.echo_file, "LIT "); |
else if (flags & (INT32) STYP_BSS) |
fprintf(io_config.echo_file, "BSS "); |
|
fprintf(io_config.echo_file, "section from 0x%08lx to 0x%08lx\n", |
address, (ADDR32) (address+size)); |
} |
} |
} |
/dump.c
0,0 → 1,1482
static char _[] = " @(#)dump.c 5.20 93/07/30 16:38:27, Srini, AMD "; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** |
** This code provides dump routines to output data in |
** hex / ASCII formats. |
** |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <ctype.h> |
#include <memory.h> |
#include "main.h" |
#include "macros.h" |
#include "monitor.h" |
#include "miniint.h" |
#include "memspcs.h" |
#include "error.h" |
|
|
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
#else |
#include <string.h> |
#endif |
|
int get_addr_29k PARAMS((char *, struct addr_29k_t *)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
int print_addr_29k PARAMS((INT32, ADDR32)); |
|
int dump_mem_word PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_reg_word PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_mem_half PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_reg_half PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_mem_byte PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_reg_byte PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_mem_float PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_reg_float PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_mem_double PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
int dump_reg_double PARAMS((INT32 mspace, ADDR32 addr, INT32 bytes, BYTE *buf)); |
|
int get_data PARAMS((BYTE *, BYTE *, int)); |
int dump_ASCII PARAMS((char *, int, BYTE *, int)); |
|
|
/* |
** The function below is used in dumping data. This function is |
** called in the main command loop parser of the monitor. The |
** parameters passed to this function are: |
** |
** token - This is an array of pointers to strings. Each string |
** referenced by this array is a "token" of the user's |
** input, translated to lower case. |
** |
** token_count - This is the number of tokens in "token". |
** |
** This function reduces the tokens to three parameters: |
** memory_space, address and byte_count. The address parameter is |
** aligned as follows: |
** |
** - All register accesses are byte aligned. The address, |
** however, accesses 32 bit words. The valued in these |
** registers are displayed in formats determined by the |
** first token. |
** |
** - Memory addresses are aligned and displayed according |
** to the dump format as specified in the first token. |
** |
** |
*/ |
|
|
INT32 |
dump_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
static INT32 memory_space=D_MEM; |
static ADDR32 address=0; |
INT32 byte_count=64; |
int result; |
struct addr_29k_t addr_29k_start; |
struct addr_29k_t addr_29k_end; |
int dump_format; |
int object_size; |
ADDR32 align_mask; |
|
INT32 retval; |
INT32 hostendian; |
INT32 bytes_returned; |
BYTE *read_buffer; |
|
/* |
** What is the dump format? |
*/ |
|
if ((strcmp(token[0], "d") == 0) || |
(strcmp(token[0], "dw") == 0)) { |
dump_format = WORD_FORMAT; |
object_size = sizeof(INT32); |
align_mask = 0xfffffffc; |
} |
else |
if (strcmp(token[0], "dh") == 0) { |
dump_format = HALF_FORMAT; |
object_size = sizeof(INT16); |
align_mask = 0xfffffffe; |
} |
else |
if (strcmp(token[0], "db") == 0) { |
dump_format = BYTE_FORMAT; |
object_size = sizeof(BYTE); |
align_mask = 0xffffffff; |
} |
else |
if (strcmp(token[0], "df") == 0) { |
dump_format = FLOAT_FORMAT; |
object_size = sizeof(float); |
align_mask = 0xfffffffc; |
} |
else |
if (strcmp(token[0], "dd") == 0) { |
dump_format = DOUBLE_FORMAT; |
object_size = sizeof(double); |
align_mask = 0xfffffff8; |
} |
else |
return(EMSYNTAX); |
|
/* |
** Get start address and byte count |
*/ |
|
if (token_count == 1) { |
if (ISREG(memory_space)) |
address = address + (byte_count/4); |
else |
if (ISMEM(memory_space)) |
address = address + byte_count; |
else |
return(EMBADADDR); |
/* Check the start address */ |
addr_29k_start.address = address; |
addr_29k_start.memory_space = memory_space; |
result = addr_29k_ok(&addr_29k_start); |
if (result != 0) |
return (result); |
} |
else |
if (token_count == 2) { |
result = get_addr_29k(token[1], &addr_29k_start); |
if (result != 0) |
return (EMSYNTAX); |
/* Check the start address */ |
result = addr_29k_ok(&addr_29k_start); |
if (result != 0) |
return (result); |
|
memory_space = addr_29k_start.memory_space; |
/* Make sure we have an even multiple of object_size */ |
if (ISREG(memory_space)) { |
address = addr_29k_start.address; |
byte_count = (byte_count + (object_size - 1)) & 0xfffffffc; |
} |
else |
if (ISMEM(memory_space)) { |
address = addr_29k_start.address & align_mask; |
byte_count = (byte_count + (object_size - 1)) & align_mask; |
} |
else |
return(EMBADADDR); |
} |
else |
if (token_count == 3) { |
result = get_addr_29k(token[1], &addr_29k_start); |
if (result != 0) |
return (EMSYNTAX); |
/* Only check the start address */ |
result = addr_29k_ok(&addr_29k_start); |
if (result != 0) |
return (result); |
result = get_addr_29k(token[2], &addr_29k_end); |
if (result != 0) |
return (EMSYNTAX); |
|
if (addr_29k_start.memory_space != addr_29k_end.memory_space) |
return (EMBADADDR); |
if (addr_29k_start.address > addr_29k_end.address) |
return (EMBADADDR); |
|
memory_space = addr_29k_start.memory_space; |
if (ISREG(memory_space)) { |
address = addr_29k_start.address; |
byte_count = (addr_29k_end.address - |
addr_29k_start.address + 1) * 4; |
} |
else |
if (ISMEM(memory_space)) { |
address = addr_29k_start.address & align_mask; |
byte_count = ((addr_29k_end.address & align_mask) - |
(addr_29k_start.address & align_mask) + |
object_size); |
} |
else |
return(EMBADADDR); |
|
} |
else |
/* Too many args */ |
return (EMSYNTAX); |
|
|
/* |
** Get data |
*/ |
|
/* Will the data overflow the message buffer? Done by TIP ??*/ |
if ((read_buffer = (BYTE *) malloc((unsigned int) byte_count)) == NULL) { |
warning(EMALLOC); |
return(FAILURE); |
}; |
|
hostendian = FALSE; |
if ((retval = Mini_read_req(memory_space, |
address, |
byte_count / object_size, |
(INT16) object_size, |
&bytes_returned, |
read_buffer, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
}; |
|
bytes_returned = bytes_returned * object_size; |
|
/* Continue if SUCCESSful */ |
|
/* |
** Call data format routines |
*/ |
|
if ISMEM(memory_space) { |
if (dump_format == WORD_FORMAT) |
result = dump_mem_word(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == HALF_FORMAT) |
result = dump_mem_half(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == BYTE_FORMAT) |
result = dump_mem_byte(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == FLOAT_FORMAT) |
result = dump_mem_float(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == DOUBLE_FORMAT) |
result = dump_mem_double(memory_space, |
address, |
bytes_returned, |
read_buffer); |
} |
else |
if ISREG(memory_space) { |
if (dump_format == WORD_FORMAT) |
result = dump_reg_word(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == HALF_FORMAT) |
result = dump_reg_half(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == BYTE_FORMAT) |
result = dump_reg_byte(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == FLOAT_FORMAT) |
result = dump_reg_float(memory_space, |
address, |
bytes_returned, |
read_buffer); |
else |
if (dump_format == DOUBLE_FORMAT) |
result = dump_reg_double(memory_space, |
address, |
bytes_returned, |
read_buffer); |
} |
else |
return(EMBADADDR); |
|
(void) free ((char *) read_buffer); |
return (result); |
|
} /* end dump_cmd() */ |
|
|
|
/* |
** Functions used by dump_cmd() |
*/ |
|
|
/* |
** This function is used to dump 32 bit words of data. |
** the address is printed, followed by the data, grouped |
** into 8 character long strings, each representing one |
** 32 bit word. Space for four 32-bit words is reserved |
** on each line. Following the hex data, an ASCII |
** representation of the data is printed. |
*/ |
|
int |
dump_mem_word(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
INT32 data_word; |
struct addr_29k_t addr_29k; |
int ASCII_index; |
char ASCII_buffer[20]; |
|
byte_count = 0; |
ASCII_index = 0; |
ASCII_buffer[0] = '\0'; |
|
address_mask = 0xfffffff0; |
start_address = read_address; |
end_address = read_address + bytes_returned; |
last_print_address = (end_address + 0xf) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
fprintf(stderr, "\n\n"); |
return (0); |
} |
|
/* Print out ASCII data */ |
if ((address & address_mask) == address) { |
fprintf(stderr, " %s\n", ASCII_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " %s\n", ASCII_buffer); |
ASCII_index = 0; |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
result = dump_ASCII(ASCII_buffer, ASCII_index, |
(BYTE *) NULL, sizeof(INT32)); |
ASCII_index = ASCII_index + sizeof(INT32); |
address = address + sizeof(INT32); |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_word, |
&read_buffer[byte_count], |
sizeof(INT32)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%08lx ", data_word); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%08lx ", data_word); |
|
/* Build ASCII srting */ |
result = dump_ASCII(ASCII_buffer, |
ASCII_index, |
&read_buffer[byte_count], |
sizeof(INT32)); |
ASCII_index = ASCII_index + sizeof(INT32); |
|
address = address + sizeof(INT32); |
|
byte_count = byte_count + sizeof(INT32); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
|
} /* end dump_mem_word() */ |
|
|
int |
dump_reg_word(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
INT32 data_word; |
struct addr_29k_t addr_29k; |
int ASCII_index; |
char ASCII_buffer[20]; |
|
byte_count = 0; |
ASCII_index = 0; |
ASCII_buffer[0] = '\0'; |
|
address_mask = 0xfffffffc; |
start_address = read_address; |
end_address = read_address + (bytes_returned / 4); |
last_print_address = (end_address + 0x3) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print out ASCII data */ |
if ((address & address_mask) == address) { |
fprintf(stderr, " %s\n", ASCII_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " %s\n", ASCII_buffer); |
ASCII_index = 0; |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
result = dump_ASCII(ASCII_buffer, ASCII_index, |
(BYTE *) NULL, sizeof(INT32)); |
ASCII_index = ASCII_index + sizeof(INT32); |
address = address + 1; |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_word, |
&read_buffer[byte_count], |
sizeof(INT32)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%08lx ", data_word); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%08lx ", data_word); |
|
/* Build ASCII srting */ |
result = dump_ASCII(ASCII_buffer, |
ASCII_index, |
&read_buffer[byte_count], |
sizeof(INT32)); |
ASCII_index = ASCII_index + sizeof(INT32); |
|
address = address + 1; |
|
byte_count = byte_count + sizeof(INT32); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
|
} /* end dump_reg_word() */ |
|
|
|
/* |
** This function is used to dump memory as half words. |
*/ |
|
int |
dump_mem_half(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
INT16 data_half; |
INT32 data_word; |
struct addr_29k_t addr_29k; |
int ASCII_index; |
char ASCII_buffer[20]; |
|
byte_count = 0; |
ASCII_index = 0; |
ASCII_buffer[0] = '\0'; |
|
address_mask = 0xfffffff0; |
start_address = read_address; |
end_address = read_address + bytes_returned; |
last_print_address = (end_address + 0xf) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print out ASCII data */ |
if ((address & address_mask) == address) { |
fprintf(stderr, " %s\n", ASCII_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " %s\n", ASCII_buffer); |
ASCII_index = 0; |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
result = dump_ASCII(ASCII_buffer, ASCII_index, |
(BYTE *) NULL, sizeof(INT16)); |
ASCII_index = ASCII_index + sizeof(INT16); |
address = address + sizeof(INT16); |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_half, |
&read_buffer[byte_count], |
sizeof(INT16)); |
if (result != 0) |
return (EMBADADDR); |
|
/* We have to cast to INT32 to print out a hex halfword */ |
/* (the Sun libraries sign extend to 32 bits) */ |
data_word = (INT32) data_half; |
data_word = (data_word & 0x0000ffff); |
fprintf(stderr, "%04x ", data_word); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%04x ", data_word); |
|
/* Build ASCII srting */ |
result = dump_ASCII(ASCII_buffer, |
ASCII_index, |
&read_buffer[byte_count], |
sizeof(INT16)); |
ASCII_index = ASCII_index + sizeof(INT16); |
|
address = address + sizeof(INT16); |
|
byte_count = byte_count + sizeof(INT16); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_mem_half() */ |
|
|
|
/* |
** This function is used to dump registers as half words. |
*/ |
|
int |
dump_reg_half(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
INT32 data_word; |
struct addr_29k_t addr_29k; |
int ASCII_index; |
char ASCII_buffer[20]; |
|
byte_count = 0; |
ASCII_index = 0; |
ASCII_buffer[0] = '\0'; |
|
address_mask = 0xfffffffc; |
start_address = read_address; |
end_address = read_address + (bytes_returned / 4); |
last_print_address = (end_address + 0x3) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print out ASCII data */ |
if ((address & address_mask) == address) { |
fprintf(stderr, " %s\n", ASCII_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " %s\n", ASCII_buffer); |
ASCII_index = 0; |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
result = dump_ASCII(ASCII_buffer, ASCII_index, |
(BYTE *) NULL, sizeof(INT16)); |
ASCII_index = ASCII_index + sizeof(INT16); |
|
address = address + 1; |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_word, |
&read_buffer[byte_count], |
sizeof(INT32)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%04lx %04lx ", |
((data_word >> 16) & 0xffff), |
(data_word & 0xffff)); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%04lx %04lx ", |
((data_word >> 16) & 0xffff), |
(data_word & 0xffff)); |
|
/* Build ASCII srting */ |
result = dump_ASCII(ASCII_buffer, |
ASCII_index, |
&read_buffer[byte_count], |
sizeof(INT32)); |
ASCII_index = ASCII_index + sizeof(INT32); |
|
address = address + 1; |
|
byte_count = byte_count + sizeof(INT32); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_reg_half() */ |
|
|
|
/* |
** This function is used to dump memory as bytes. |
*/ |
|
int |
dump_mem_byte(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
BYTE data_byte; |
struct addr_29k_t addr_29k; |
int ASCII_index; |
char ASCII_buffer[20]; |
|
byte_count = 0; |
ASCII_index = 0; |
ASCII_buffer[0] = '\0'; |
|
address_mask = 0xfffffff0; |
start_address = read_address; |
end_address = read_address + bytes_returned; |
last_print_address = (end_address + 0xf) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print out ASCII data */ |
if ((address & address_mask) == address) { |
fprintf(stderr, " %s\n", ASCII_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " %s\n", ASCII_buffer); |
ASCII_index = 0; |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
result = dump_ASCII(ASCII_buffer, ASCII_index, |
(BYTE *) NULL, sizeof(BYTE)); |
ASCII_index = ASCII_index + sizeof(BYTE); |
address = address + sizeof(BYTE); |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_byte, |
&read_buffer[byte_count], |
sizeof(BYTE)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%02x ", data_byte); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%02x ", data_byte); |
|
/* Build ASCII srting */ |
result = dump_ASCII(ASCII_buffer, |
ASCII_index, |
&read_buffer[byte_count], |
sizeof(BYTE)); |
ASCII_index = ASCII_index + sizeof(BYTE); |
|
address = address + sizeof(BYTE); |
|
byte_count = byte_count + sizeof(BYTE); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_mem_byte() */ |
|
|
|
/* |
** This function is used to dump registers as bytes. |
*/ |
|
int |
dump_reg_byte(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
INT32 data_word; |
struct addr_29k_t addr_29k; |
int ASCII_index; |
char ASCII_buffer[20]; |
|
byte_count = 0; |
ASCII_index = 0; |
ASCII_buffer[0] = '\0'; |
|
address_mask = 0xfffffffc; |
start_address = read_address; |
end_address = read_address + (bytes_returned / 4); |
last_print_address = (end_address + 0x3) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print out ASCII data */ |
if ((address & address_mask) == address) { |
fprintf(stderr, " %s\n", ASCII_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " %s\n", ASCII_buffer); |
ASCII_index = 0; |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
result = dump_ASCII(ASCII_buffer, ASCII_index, |
(BYTE *) NULL, sizeof(INT32)); |
ASCII_index = ASCII_index + sizeof(INT32); |
|
address = address + 1; |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_word, |
&read_buffer[byte_count], |
sizeof(INT32)); |
if (result != 0) |
return (EMBADADDR); |
|
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%02lx %02lx %02lx %02lx ", |
((data_word >> 24) & 0xff), |
((data_word >> 16) & 0xff), |
((data_word >> 8) & 0xff), |
(data_word & 0xff)); |
fprintf(stderr, "%02lx %02lx %02lx %02lx ", |
((data_word >> 24) & 0xff), |
((data_word >> 16) & 0xff), |
((data_word >> 8) & 0xff), |
(data_word & 0xff)); |
|
/* Build ASCII srting */ |
result = dump_ASCII(ASCII_buffer, |
ASCII_index, |
&read_buffer[byte_count], |
sizeof(INT32)); |
ASCII_index = ASCII_index + sizeof(INT32); |
|
address = address + 1; |
|
byte_count = byte_count + sizeof(INT32); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_reg_byte() */ |
|
|
|
/* |
** This function is used to dump memory as floats. |
*/ |
|
int |
dump_mem_float(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
float data_float; |
struct addr_29k_t addr_29k; |
|
byte_count = 0; |
|
address_mask = 0xfffffff0; |
start_address = read_address; |
end_address = read_address + bytes_returned; |
last_print_address = (end_address + 0xf) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
address = address + sizeof(float); |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_float, |
&read_buffer[byte_count], |
sizeof(float)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%+1.6e ", (double) data_float); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%+1.6e ", (double) data_float); |
|
address = address + sizeof(float); |
|
byte_count = byte_count + sizeof(float); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_mem_float() */ |
|
|
|
|
/* |
** This function is used to dump registers as floats. |
*/ |
|
int |
dump_reg_float(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
float data_float; |
struct addr_29k_t addr_29k; |
|
byte_count = 0; |
|
address_mask = 0xfffffffc; |
start_address = read_address; |
end_address = read_address + (bytes_returned / 4); |
last_print_address = (end_address + 0x3) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
address = address + 1; |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_float, |
&read_buffer[byte_count], |
sizeof(float)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%+1.6e ", (double) data_float); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%+1.6e ", (double) data_float); |
|
address = address + 1; |
|
byte_count = byte_count + sizeof(float); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_reg_float() */ |
|
|
|
|
/* |
** This function is used to dump memory as doubles. |
*/ |
|
int |
dump_mem_double(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
double data_double; |
struct addr_29k_t addr_29k; |
|
byte_count = 0; |
|
address_mask = 0xfffffff0; |
start_address = read_address; |
end_address = read_address + bytes_returned; |
last_print_address = (end_address + 0xf) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
address = address + sizeof(double); |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_double, |
&read_buffer[byte_count], |
sizeof(double)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%+1.15e ", data_double); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%+1.15e ", data_double); |
|
address = address + sizeof(double); |
|
byte_count = byte_count + sizeof(double); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_mem_double() */ |
|
|
|
|
/* |
** This function is used to dump registers as doubles. |
*/ |
|
int |
dump_reg_double(memory_space, read_address, bytes_returned, read_buffer) |
INT32 memory_space; |
ADDR32 read_address; |
INT32 bytes_returned; |
BYTE *read_buffer; |
{ |
int result; |
ADDR32 address; |
ADDR32 start_address; |
ADDR32 end_address; |
ADDR32 last_print_address; |
ADDR32 address_mask; |
INT32 byte_count; |
double data_double; |
struct addr_29k_t addr_29k; |
|
byte_count = 0; |
|
address_mask = 0xfffffffc; |
start_address = read_address; |
end_address = read_address + (bytes_returned / 4); |
last_print_address = (end_address + 0x3) & address_mask; |
address = start_address & address_mask; |
|
/* |
** Loop while data available |
*/ |
|
while (address <= last_print_address) { |
|
/* Exit if address not valid */ |
addr_29k.memory_space = memory_space; |
addr_29k.address = address; |
result = addr_29k_ok(&addr_29k); |
if (result != 0) { |
fprintf(stderr, "\n\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n\n"); |
return (0); |
} |
|
/* Print address in margin */ |
if (((address & address_mask) == address) && |
(address != last_print_address)) { |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
result = print_addr_29k(memory_space, address); |
if (result != 0) |
return (EMBADADDR); |
} |
|
/* Do leading and trailing spaces (if necessary) */ |
if ((address < start_address) || |
(address >= end_address)) { |
fprintf(stderr, " "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " "); |
address = address + 2; |
} |
|
/* Print out hex data */ |
if ((address >= start_address) && |
(address < end_address)) { |
|
result = get_data((BYTE *)&data_double, |
&read_buffer[byte_count], |
sizeof(double)); |
if (result != 0) |
return (EMBADADDR); |
|
fprintf(stderr, "%+1.15e ", data_double); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%+1.15e ", data_double); |
|
address = address + (sizeof(double) / sizeof(INT32)); |
|
byte_count = byte_count + sizeof(double); |
|
} /* end if */ |
|
} /* end while */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
return (0); |
} /* end dump_reg_double() */ |
|
/* |
** This function fills in a buffer with a character |
** representation of the dumped data. |
*/ |
|
int |
dump_ASCII(buffer, index, data, size) |
char *buffer; |
int index; |
BYTE *data; |
int size; |
{ |
INT32 i; |
|
/* Do ASCII dump */ |
for (i=0; i<size; i=i+1) |
if (data == NULL) |
buffer[index+i] = ' '; |
else |
if (isprint(data[i])) |
buffer[index+i] = data[i]; |
else |
buffer[index+i] = '.'; |
|
buffer[index+i] = '\0'; /* Null terminate */ |
|
return (0); |
|
} /* end dump_ASCII() */ |
|
/move.c
0,0 → 1,170
static char _[] = "@(#)move.c 5.20 93/07/30 16:38:55, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This code provides "move" routines to copy blocks of memory. |
** Data may be moved as words (32 bit), half-words (16 bit), |
** bytes (8 bit), float (32 bit floating point) or double |
** (64 bit floating point). |
** |
** Registers moves are not permitted. |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <ctype.h> |
#include <memory.h> |
#include "main.h" |
#include "memspcs.h" |
#include "miniint.h" |
#include "macros.h" |
#include "error.h" |
|
|
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
#else |
#include <string.h> |
|
#endif |
|
|
int get_addr_29k PARAMS((char *, struct addr_29k_t *)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
|
int get_word PARAMS((char *, INT32 *)); |
|
int set_data PARAMS((BYTE *, BYTE *, int)); |
|
/* |
** The function below is used in moving data. This function is |
** called in the main command loop parser of the monitor. The |
** parameters passed to this function are: |
** |
** token - This is an array of pointers to strings. Each string |
** referenced by this array is a "token" of the user's |
** input, translated to lower case. |
** |
** token_count - This is the number of items in the token array. |
** |
** This function reduces the tokens to three parameters: |
** the start address and the end address of the move and the |
** target address of the move. |
** |
*/ |
|
|
INT32 |
move_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int result; |
INT32 byte_count; |
struct addr_29k_t addr_29k_start; |
struct addr_29k_t addr_29k_end; |
struct addr_29k_t addr_29k_dest; |
struct addr_29k_t temp_addr_29k; |
|
INT32 retval; |
INT32 direction; |
|
if ((strcmp(token[0], "m") != 0) || |
(token_count != 4)) |
return (EMSYNTAX); |
|
/* |
** Get addresses |
*/ |
|
result = get_addr_29k(token[1], &addr_29k_start); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k_start); |
if (result != 0) |
return (result); |
|
result = get_addr_29k(token[2], &addr_29k_end); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k_end); |
if (result != 0) |
return (result); |
|
result = get_addr_29k(token[3], &addr_29k_dest); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k_dest); |
if (result != 0) |
return (result); |
|
/* End address must be not be less than start address */ |
if (addr_29k_start.address > addr_29k_end.address) |
return (EMSYNTAX); |
|
byte_count = (addr_29k_end.address - addr_29k_start.address) + 1; |
|
/* Dest range must be in valid memory */ |
temp_addr_29k.memory_space = addr_29k_dest.memory_space; |
/* For memory to register, divide byte count by 4 */ |
if ((ISMEM(addr_29k_start.memory_space)) && |
(ISREG(addr_29k_dest.memory_space))) |
temp_addr_29k.address = addr_29k_dest.address + (byte_count / 4); |
else |
/* For register to memory, multiply byte count by 4 */ |
if ((ISREG(addr_29k_start.memory_space)) && |
(ISMEM(addr_29k_dest.memory_space))) |
temp_addr_29k.address = addr_29k_dest.address + (byte_count * 4); |
else |
temp_addr_29k.address = addr_29k_dest.address + byte_count; |
result = addr_29k_ok(&temp_addr_29k); |
if (result != 0) |
return (EMCOPY); |
|
/* Registers are four bytes */ |
if (ISREG(addr_29k_start.memory_space)) |
byte_count = (byte_count * 4); |
|
/* Do copy */ |
|
direction = TRUE; /* SRINI front to back or back to front */ |
if ((retval = Mini_copy (addr_29k_start.memory_space, |
addr_29k_start.address, |
addr_29k_dest.memory_space, |
addr_29k_dest.address, |
byte_count, |
(INT16) 1, /* size */ |
direction)) != SUCCESS) { |
return(FAILURE); |
} else |
return(SUCCESS); |
|
} /* end move_cmd() */ |
|
|
|
/io.c
0,0 → 1,163
static char _[] = "@(#)io.c 5.22 93/10/26 14:50:43, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
* This file contains the I/O related routines. |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <string.h> |
#ifdef MSDOS |
#include <conio.h> |
#else |
#include <sys/ioctl.h> |
#endif |
#include "main.h" |
#include "miniint.h" |
#include "error.h" |
#include "monio.h" |
|
/* Function declarations */ |
|
INT32 Mini_io_setup PARAMS((void)); |
INT32 Mini_io_reset PARAMS((void)); |
int getkey PARAMS((void)); |
INT32 Mini_poll_kbd PARAMS((char *cmd_buffer, int size, int mode)); |
int cmd_io PARAMS ((char *cmd_buffer, char c)); |
int channel0_io PARAMS ((char c)); |
|
INT32 |
Mini_io_setup() |
{ |
setbuf(stdout, 0); /* stdout unbuffered */ |
return(SUCCESS); |
} |
|
INT32 |
Mini_io_reset() |
{ |
/* Nothing special for now */ |
return(SUCCESS); |
} |
|
/* |
** This function is used to perform all host I/O. It |
** calls the functions cmd_io() or hif_io() as appropriate |
** Note that there are eight pobible I/O "modes". These |
** are all possible combination of: |
** |
** - Host / Target I/O |
** - HIF / non-HIF I/O |
** - Command file / keyboard I/O |
** |
*/ |
|
INT32 |
Mini_poll_kbd(cmd_buffer, size, blockmode) |
char *cmd_buffer; |
int size; |
int blockmode; |
{ |
#ifdef MSDOS |
char ch; |
static int indx=0; |
|
io_config.cmd_ready = FALSE; |
if (blockmode) { /* BLOCK until a command is typed (line buffered) */ |
while (gets(cmd_buffer) == NULL); /* no characters in stdin */ |
io_config.cmd_ready = TRUE; |
} else { /* NONBLOCk return immediately if there is no command pending */ |
if (kbhit()) { |
ch = (unsigned char) getche(); |
*(cmd_buffer+indx) = ch; |
indx=indx+1; |
if (ch == (unsigned char) 13) { /* \r, insert \n */ |
putchar(10); /* line feed */ |
*(cmd_buffer+indx) = '\0'; |
io_config.cmd_ready = TRUE; |
indx=0; |
} else if (ch == (unsigned char) 8) { /* backspace */ |
indx=indx-1; |
} else if (ch == (unsigned char) 127) { /* delete */ |
indx=indx-1; |
} |
}; |
} |
return(SUCCESS); |
|
#else |
int c; |
int result; |
char *temp_ptr; |
int tries; |
int i; |
|
result = 0; |
io_config.cmd_ready = FALSE; |
|
if (blockmode) { /* block mode read */ |
i = 0; |
#ifdef __hpux |
ioctl(fileno(stdin), FIOSNBIO, &i); /* set blocking read */ |
#else |
ioctl(fileno(stdin), FIONBIO, &i); /* set blocking read */ |
#endif |
} else { /* nonblocking read */ |
/* for now only read from stdin */ |
i = 1; |
#ifdef __hpux |
ioctl(fileno(stdin), FIOSNBIO, &i); /* set non blocking read */ |
#else |
ioctl(fileno(stdin), FIONBIO, &i); /* set non blocking read */ |
#endif |
} |
|
/* Now read from stdin. */ |
result = read( 0, cmd_buffer, BUFSIZ ); |
|
if (result < 0) |
{ |
} else { |
cmd_buffer[result] = '\0'; |
io_config.cmd_ready = TRUE; |
} |
|
if (blockmode) { |
} else { |
i = 0; |
#ifdef __hpux |
ioctl(fileno(stdin), FIOSNBIO, &i); /* clear non-blocking read */ |
#else |
ioctl(fileno(stdin), FIONBIO, &i); /* clear non-blocking read */ |
#endif |
} |
|
return(SUCCESS); |
#endif |
} |
|
/getdata.c
0,0 → 1,807
static char _[] = "@(#)getdata.c 5.21 93/07/30 16:38:33, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** |
** This file contains functions used to parse strings into |
** various data structures. |
** |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <ctype.h> |
#include "memspcs.h" |
#include "main.h" |
#include "opcodes.h" |
#include "macros.h" |
#include "error.h" |
|
#ifdef MSDOS |
#include <string.h> |
#else |
#include <string.h> |
#endif |
|
/* Function declarations */ |
int get_data PARAMS(( BYTE *out_data, BYTE *in_data, int size)); |
int set_data PARAMS((BYTE *out_data, BYTE *in_data, int size)); |
int get_word_decimal PARAMS((char *buffer, INT32 *data_word)); |
int get_double PARAMS((char *buffer, double *data_double)); |
int get_float PARAMS((char *buffer, float *data_float)); |
int get_byte PARAMS((char *buffer, BYTE *data_byte)); |
int get_half PARAMS((char *buffer, INT16 *data_half)); |
int get_word PARAMS((char *buffer, INT32 *data_word)); |
int get_alias_29k PARAMS((char *reg_str, struct addr_29k_t *addr_29k)); |
int get_register_29k PARAMS((char *reg_str,struct addr_29k_t *addr_29k)); |
int get_memory_29k PARAMS((char *memory_str, struct addr_29k_t *addr_29k, INT32 default_space)); |
int print_addr_29k PARAMS((INT32 memory_space, ADDR32 address)); |
int addr_29k_ok PARAMS((struct addr_29k_t *addr_29k)); |
int get_addr_29k PARAMS((char *addr_str, struct addr_29k_t *addr_29k)); |
int get_addr_29k_m PARAMS((char *addr_str, struct addr_29k_t *addr_29k, INT32 default_space)); |
void convert16 PARAMS(( BYTE *byte)); |
void convert32 PARAMS(( BYTE *byte)); |
|
|
/* |
** This function is used to parse a string into the |
** memory space / address pair used by the Am29000. |
** the memory spaces supported are in the "memspcs.h" |
** file. |
** |
** The strings parsed are: |
** |
** lr0 to gr127 (Local registers) |
** gr0 to gr127 (Global registers) |
** sr0 to sr127 (Special registers) |
** tr0 to tr127 (TLB registers) |
** xr0 to xr32 (Coprocessor registers) |
** and |
** <hex_addr>{i|r|d} |
** |
** If successful, the Am29000 memory space / address pair |
** pointed to by addr_29k is filled in and zero is returned. |
** If unsuccessful, a -1 is returned and the values in |
** addr_29k are undefined. |
** |
** Note: This function expects an unpadded, lower case |
** ASCII string. |
*/ |
|
|
int |
get_addr_29k(addr_str, addr_29k) |
char *addr_str; |
struct addr_29k_t *addr_29k; |
{ |
/* defaults memory addresses to D_MEM */ |
return(get_addr_29k_m(addr_str, addr_29k, D_MEM)); |
} |
|
|
int |
get_addr_29k_m(addr_str, addr_29k, default_space) |
char *addr_str; |
struct addr_29k_t *addr_29k; |
INT32 default_space; /* for default if no space given in string */ |
{ |
int result; |
|
result = get_memory_29k(addr_str, addr_29k, default_space); |
|
if (result != 0) |
result = get_register_29k(addr_str, addr_29k); |
|
if (result != 0) |
result = get_alias_29k(addr_str, addr_29k); |
|
return (result); |
} /* end get_addr_29k() */ |
|
|
/* |
** This function is used to verify that an Am29000 |
** memory space / address pair contains a valid address. |
** The memory spaces supported are those defined in the |
** "memspcs.h" header file. |
** |
** The global structure "target_config" is also used to |
** do range checking. |
** |
** If successful, a 0 is returned, otherwise -1 is |
** returned. |
*/ |
|
|
int |
addr_29k_ok(addr_29k) |
struct addr_29k_t *addr_29k; |
{ |
int return_code; |
ADDR32 start_addr; |
ADDR32 end_addr; |
|
return_code = 0; |
|
if (addr_29k->memory_space == LOCAL_REG) { |
if (addr_29k->address > 127) |
return_code = EMBADREG; |
} |
else |
if (addr_29k->memory_space == ABSOLUTE_REG) { |
if ((addr_29k->address >= 0) && (addr_29k->address <= 255)) |
return (0); |
else |
return (EMBADREG); |
} |
else |
if (addr_29k->memory_space == GLOBAL_REG) { |
if (PROCESSOR(target_config.processor_id) == PROC_AM29050) { |
if ( ((addr_29k->address > 3) && |
(addr_29k->address < 64)) || |
|
(addr_29k->address > 127)) |
return_code = EMBADREG; |
} else { |
if ( ((addr_29k->address > 1) && |
(addr_29k->address < 64)) || |
|
(addr_29k->address > 127)) |
return_code = EMBADREG; |
} |
} else /* Note: Am29xxx procesors have different SPECIAL_REGs */ |
if ((addr_29k->memory_space == SPECIAL_REG) || |
(addr_29k->memory_space == A_SPCL_REG)) { |
|
if ((PROCESSOR(target_config.processor_id) == PROC_AM29030) || |
(PROCESSOR(target_config.processor_id) == PROC_AM29240) || |
(PROCESSOR(target_config.processor_id) == PROC_AM29035)) { |
|
if (((addr_29k->address > 14) && |
(addr_29k->address < 29)) || |
|
((addr_29k->address > 30) && |
(addr_29k->address < 128)) || |
|
((addr_29k->address > 135) && |
(addr_29k->address < 160)) || |
|
((addr_29k->address > 162) && |
(addr_29k->address < 164)) || |
|
(addr_29k->address > 164)) |
return_code = EMBADREG; |
} |
else |
if (PROCESSOR(target_config.processor_id) == PROC_AM29050) { |
|
if (((addr_29k->address > 26) && |
(addr_29k->address < 128)) || |
|
((addr_29k->address > 135) && |
(addr_29k->address < 160)) || |
|
(addr_29k->address > 164)) |
return_code = EMBADREG; |
} |
else /* default */ |
if (((addr_29k->address > 14) && |
(addr_29k->address < 128)) || |
|
((addr_29k->address > 135) && |
(addr_29k->address < 160)) || |
|
((addr_29k->address > 162) && |
(addr_29k->address < 164)) || |
|
(addr_29k->address > 164)) |
return_code = EMBADREG; |
} /* end if (SPECIAL_REG) */ |
else |
if (addr_29k->memory_space == TLB_REG) { |
if (addr_29k->address > 127) |
return_code = EMBADREG; |
} |
else |
if (addr_29k->memory_space == COPROC_REG) { |
if (target_config.coprocessor != 0) |
return_code = EMBADREG; |
if (addr_29k->address > 32) |
return_code = EMBADREG; |
} |
else |
if (addr_29k->memory_space == PC_SPACE) { |
return (0); |
} |
else |
if (addr_29k->memory_space == GENERIC_SPACE) { |
return (0); |
} |
else |
if (addr_29k->memory_space == I_MEM) { |
start_addr = target_config.I_mem_start; |
end_addr = start_addr + (ADDR32) target_config.I_mem_size; |
if ((addr_29k->address < start_addr) || |
(addr_29k->address > end_addr)) |
return_code = EMBADADDR; |
} |
else |
if (addr_29k->memory_space == D_MEM) { |
start_addr = target_config.D_mem_start; |
end_addr = start_addr + (ADDR32) target_config.D_mem_size; |
if ((addr_29k->address < start_addr) || |
(addr_29k->address > end_addr)) |
return_code = EMBADADDR; |
} |
else |
if (addr_29k->memory_space == I_ROM) { |
start_addr = target_config.ROM_start; |
end_addr = start_addr + (ADDR32) target_config.ROM_size; |
if ((addr_29k->address < start_addr) || |
(addr_29k->address > end_addr)) |
return_code = EMBADADDR; |
} |
else |
if (addr_29k->memory_space == D_ROM) { |
return_code = EMBADADDR; /* We don't use this memory space */ |
} |
else |
if (addr_29k->memory_space == I_O) { |
return (0); /* No checking on I/O space */ |
} |
else |
return_code = EMBADADDR; /* Unknown memory space */ |
|
return (return_code); |
|
} /* end addr_29k_ok() */ |
|
|
|
|
|
/* |
** This function is used to print out an address. The |
** parameters are a memory_space and an address. This |
** function returns a 0 if the command was successful and |
** a -1 on failure. |
** |
** The strings printed are: |
** |
** lr0 to gr127 (Local registers) |
** gr0 to gr127 (Global registers) |
** sr0 to sr127 (Special registers) |
** tr0 to tr127 (TLB registers) |
** xr0 to xr32 (Coprocessor registers) |
** <hex_addr> (Data memory) |
** <hex_addr>i (instruction memory) |
** and |
** <hex_addr>r (ROM memory) |
** |
*/ |
|
|
int |
print_addr_29k(memory_space, address) |
INT32 memory_space; |
ADDR32 address; |
{ |
char buf[80]; |
|
if (memory_space == LOCAL_REG) |
sprintf(&buf[0], "lr%03ld ", address); |
else |
if (memory_space == ABSOLUTE_REG) |
sprintf(&buf[0], "ar%03ld ", address); |
else |
if (memory_space == GLOBAL_REG) |
sprintf(&buf[0], "gr%03ld ", address); |
else |
if ((memory_space == SPECIAL_REG) || (memory_space == A_SPCL_REG)) |
sprintf(&buf[0], "sr%03ld ", address); |
else |
if (memory_space == PC_SPACE) |
sprintf(&buf[0], "pc%03ld ", address); |
else |
if (memory_space == TLB_REG) |
sprintf(&buf[0], "tr%03ld ", address); |
else |
if (memory_space == COPROC_REG) |
sprintf(&buf[0], "xr%03ld ", address); |
else |
if (memory_space == I_MEM) |
sprintf(&buf[0], "%08lxi ", address); |
else |
if (memory_space == D_MEM) |
sprintf(&buf[0], "%08lx ", address); |
else |
if (memory_space == GENERIC_SPACE) |
sprintf(&buf[0], "%08lx ", address); |
else |
if (memory_space == I_ROM) |
sprintf(&buf[0], "%08lxr ", address); |
else |
if (memory_space == D_ROM) |
sprintf(&buf[0], "%08ldr ", address); |
else |
if (memory_space == I_O) |
sprintf(&buf[0], "%08lx(i/o)", address); |
else |
return (-1); |
|
fprintf (stderr, "%s", &buf[0]); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &buf[0]); |
return (0); |
} /* end print_addr_29k() */ |
|
|
|
/* |
** This function is used to convert a string denoting a |
** 29k address into an addr_29k_t memory space / address pair. |
** This function recognizes the registers described in |
** get_addr_29k() above. |
*/ |
|
int |
get_memory_29k(memory_str, addr_29k, default_space) |
char *memory_str; |
struct addr_29k_t *addr_29k; |
INT32 default_space; |
{ |
int i; |
int fields; |
int string_length; |
ADDR32 addr; |
char i_r; |
char error; |
|
addr_29k->memory_space = -1; |
addr_29k->address = -1; |
|
addr = 0; |
i_r = '\0'; |
error = '\0'; |
|
/* Get rid of leading "0x" */ |
if ((strlen(memory_str) > 2) && |
(strncmp(memory_str, "0x", 2) == 0)) |
memory_str = &(memory_str[2]); |
|
string_length = strlen(memory_str); |
|
if ((string_length > 10) || (string_length < 1)) |
return (EMBADADDR); |
|
if (memory_str[0] == '.') {/* relative offset */ |
fields = sscanf(&memory_str[1], "%lx%c%c", &addr, &i_r, &error); |
addr_29k->memory_space = PC_RELATIVE; |
addr_29k->address = addr; |
return (0); |
} |
|
for (i=1; i<(string_length-1); i=i+1) |
if (isxdigit(memory_str[i]) == 0) |
return (EMBADADDR); |
|
if ((isxdigit(memory_str[(string_length-1)]) == 0) && |
(memory_str[(string_length-1)] != 'i') && |
(memory_str[(string_length-1)] != 'm') && |
(memory_str[(string_length-1)] != 'u') && |
(memory_str[(string_length-1)] != 'p') && |
(memory_str[(string_length-1)] != 'r')) |
return (EMBADADDR); |
|
fields = sscanf(memory_str, "%lx%c%c", &addr, &i_r, &error); |
|
addr_29k->address = addr; |
|
if (fields == 1) { |
addr_29k->memory_space = default_space; |
} |
else |
if (fields == 2) { |
if ((i_r == '\0') || (i_r == 'm')) |
addr_29k->memory_space = D_MEM; |
else |
if (i_r == 'r') |
addr_29k->memory_space = I_ROM; |
else |
if (i_r == 'i') |
addr_29k->memory_space = I_MEM; |
else |
if (i_r == 'p') |
if ((target_config.processor_id & 0xf1) >= 0x50) |
addr_29k->memory_space = GENERIC_SPACE; |
else |
addr_29k->memory_space = I_O; |
else |
if (i_r == 'u') |
addr_29k->memory_space = GENERIC_SPACE; |
else |
return (EMBADADDR); |
} |
else |
return (EMBADADDR); |
|
return (0); |
} /* end get_memory_29k() */ |
|
|
|
/* |
** This function is used to convert a string denoting an |
** 29k register into an addr_29k_t memory space / address pair. |
*/ |
|
int |
get_register_29k(reg_str, addr_29k) |
char *reg_str; |
struct addr_29k_t *addr_29k; |
{ |
int fields; |
ADDR32 reg_number; |
char error; |
|
addr_29k->memory_space = -1; |
addr_29k->address = -1; |
|
reg_number = 0; |
error = '\0'; |
|
if (strlen(reg_str) > 8) |
return (EMBADREG); |
|
if (strncmp(reg_str, "lr", 2) == 0) |
addr_29k->memory_space = LOCAL_REG; |
else |
if (strncmp(reg_str, "ar", 2) == 0) |
addr_29k->memory_space = ABSOLUTE_REG; |
else |
if (strncmp(reg_str, "gr", 2) == 0) |
addr_29k->memory_space = GLOBAL_REG; |
else |
if (strncmp(reg_str, "sr", 2) == 0) |
addr_29k->memory_space = A_SPCL_REG; |
else |
if (strncmp(reg_str, "tr", 2) == 0) |
addr_29k->memory_space = TLB_REG; |
else |
if (strncmp(reg_str, "xr", 2) == 0) |
addr_29k->memory_space = COPROC_REG; |
|
/* Get register number */ |
if (addr_29k->memory_space != -1) { |
fields = sscanf(&(reg_str[2]), "%ld%c", ®_number, &error); |
if ((fields == 1) && |
(error == '\0')) |
addr_29k->address = reg_number; |
else |
addr_29k->memory_space = -1; |
} |
|
if (addr_29k->memory_space == -1) |
return (EMBADREG); |
else |
return (0); |
} /* end get_register_29k() */ |
|
|
|
|
/* |
** This function is used to get the special register aliases |
** ("cps", "vab", "ops", etc ...) in addition to the registers |
** described in get_addr_29k() above. |
*/ |
|
int |
get_alias_29k(reg_str, addr_29k) |
char *reg_str; |
struct addr_29k_t *addr_29k; |
{ |
int i; |
int result; |
int found; |
|
addr_29k->memory_space = -1; |
addr_29k->address = -1; |
|
if (strlen(reg_str) > 8) |
return (EMBADREG); |
|
/* Check for logical PC */ |
if ((strcmp("pc", reg_str) == 0) || |
(strcmp("PC", reg_str) == 0)) { |
addr_29k->memory_space = PC_SPACE; |
addr_29k->address = (ADDR32) 0; |
return (0); |
} |
/* Search for a special register alias */ |
i=0; |
found = FALSE; |
while ((i<256) && (found != TRUE)) { |
result = strcmp(spreg[i], reg_str); |
if (result == 0) { |
found = TRUE; |
addr_29k->memory_space = A_SPCL_REG; |
addr_29k->address = (ADDR32) i; |
} |
i = i + 1; |
} /* end while */ |
|
if (found == TRUE) |
return (0); |
else |
return (EMBADREG); |
|
} /* end get_alias_29k() */ |
|
|
|
|
|
/* |
** This function is used to read in a 32 bit hex word. |
** This word is input as an ASCII string and converted |
** into an INT32 data_word. If the conversion is successful, |
** a zero is returned, otherwise a -1 is returned. |
*/ |
|
int |
get_word(buffer, data_word) |
char *buffer; |
INT32 *data_word; |
{ |
int fields; |
char error; |
|
/* No more than eight (hex) characters */ |
if (strlen(buffer) > 8) |
return (EMSYNTAX); |
|
fields = sscanf(buffer, "%lx%c", data_word, &error); |
|
if (fields != 1) |
return (EMSYNTAX); |
|
return (0); |
|
} /* end get_word() */ |
|
|
|
int |
get_half(buffer, data_half) |
char *buffer; |
INT16 *data_half; |
{ |
int fields; |
char error; |
INT16 temp_int; |
|
/* No more than four (hex) characters */ |
if (strlen(buffer) > 4) |
return (EMSYNTAX); |
|
fields = sscanf(buffer, "%hx%c", &temp_int, &error); |
|
if (fields != 1) |
return (EMSYNTAX); |
|
*data_half = (INT16) temp_int; |
|
return (0); |
|
} /* end get_half() */ |
|
|
int |
get_byte(buffer, data_byte) |
char *buffer; |
BYTE *data_byte; |
{ |
int fields; |
char error; |
int temp_int; |
|
/* No more than two (hex) characters */ |
if (strlen(buffer) > 2) |
return (EMSYNTAX); |
|
fields = sscanf(buffer, "%x%c", &temp_int, &error); |
|
if (fields != 1) |
return (EMSYNTAX); |
|
*data_byte = (BYTE) temp_int; |
|
return (0); |
|
} /* end get_byte() */ |
|
|
int |
get_float(buffer, data_float) |
char *buffer; |
float *data_float; |
{ |
int fields; |
char error; |
|
fields = sscanf(buffer, "%f%c", data_float, &error); |
|
if (fields != 1) |
return (EMSYNTAX); |
|
return (0); |
|
} /* end get_float() */ |
|
|
int |
get_double(buffer, data_double) |
char *buffer; |
double *data_double; |
{ |
int fields; |
char error; |
|
fields = sscanf(buffer, "%lf%c", data_double, &error); |
|
if (fields != 1) |
return (EMSYNTAX); |
|
return (0); |
|
|
} /* end get_double() */ |
|
|
|
|
/* |
** This function is used to read in a 32 bit decimal word. |
** This word is input as an ASCII string and converted |
** into an INT32 data_word. If the conversion is successful, |
** a zero is returned, otherwise a -1 is returned. |
** This function is very similar to get_word(). |
*/ |
|
int |
get_word_decimal(buffer, data_word) |
char *buffer; |
INT32 *data_word; |
{ |
int fields; |
char error; |
|
/* No more than eight (hex) characters */ |
if (strlen(buffer) > 8) |
return (EMSYNTAX); |
|
fields = sscanf(buffer, "%ld%c", data_word, &error); |
|
if (fields != 1) |
return (EMSYNTAX); |
|
return (0); |
|
} /* end get_word_decimal() */ |
|
|
/* |
** This function is used to copy data from into and out |
** of the message buffers. If necessary, endian |
** conversion is performed. |
*/ |
|
int |
set_data(out_data, in_data, size) |
BYTE *out_data; |
BYTE *in_data; |
int size; |
{ |
int i; |
|
if (host_config.host_endian == host_config.target_endian) |
for (i=0; i<size; i=i+1) |
out_data[i] = in_data[i]; |
else |
for (i=0; i<size; i=i+1) |
out_data[i] = in_data[((size-1)-i)]; |
|
return (0); |
} /* end set_data() */ |
|
|
|
|
/* |
** This function is used to get data. |
** If necessary, endian conversion is performed. |
*/ |
|
int |
get_data(out_data, in_data, size) |
BYTE *out_data; |
BYTE *in_data; |
int size; |
{ |
int i; |
|
if (host_config.host_endian == host_config.target_endian) |
for (i=0; i<size; i=i+1) |
out_data[i] = in_data[i]; |
else |
for (i=0; i<size; i=i+1) |
out_data[i] = in_data[((size-1)-i)]; |
|
return (0); |
} /* end get_data() */ |
|
|
|
/* |
** This function is used to swap the bytes in a 32 bit |
** word. This will convert "little endian" (IBM-PC / Intel) |
** words to "big endian" (Sun / Motorola) words. |
*/ |
|
void |
convert32(byte) |
BYTE *byte; |
{ |
BYTE temp; |
|
temp = byte[0]; /* Swap bytes 0 and 3 */ |
byte[0] = byte[3]; |
byte[3] = temp; |
temp = byte[1]; /* Swap bytes 1 and 2 */ |
byte[1] = byte[2]; |
byte[2] = temp; |
} /* end convert32() */ |
|
|
/* |
** This function is used to swap the bytes in a 16 bit |
** word. This will convert "little endian" (IBM-PC / Intel) |
** half words to "big endian" (Sun / Motorola) half words. |
*/ |
|
void |
convert16(byte) |
BYTE *byte; |
{ |
BYTE temp; |
|
temp = byte[0]; /* Swap bytes 0 and 1 */ |
byte[0] = byte[1]; |
byte[1] = temp; |
|
} /* end convert16() */ |
/icmd.c
0,0 → 1,499
static char _[] = "@(#)icmd.c 5.20 93/07/30 16:38:37, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This code implements a subset of the MON29K-like "i" |
** commands. Access the 2903x cashe, ix, ia, il |
***************************************************************************** |
*/ |
|
|
#include <stdio.h> |
#include <ctype.h> |
#include <memory.h> |
#include "main.h" |
#include "macros.h" |
#include "miniint.h" |
#include "memspcs.h" |
#include "error.h" |
|
|
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
#else |
#include <string.h> |
#endif |
|
INT32 i_cmd PARAMS((char **, int)); |
INT32 ix_cmd PARAMS((char **, int)); |
INT32 il_cmd PARAMS((char **, int)); |
|
int get_addr_29k PARAMS((char *, struct addr_29k_t *)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
int print_addr_29k PARAMS((INT32, ADDR32)); |
int get_word PARAMS((char *buffer, INT32 *data_word)); |
void convert32 PARAMS(( BYTE *byte)); |
|
void dasm_instr PARAMS((ADDR32, struct instr_t *)); |
|
/* Variable definitions */ |
struct xp_cmd_t { |
INT32 vtb; |
INT32 ops; |
INT32 cps; |
INT32 cfg; |
INT32 cha; |
INT32 chd; |
INT32 chc; |
INT32 rbp; |
INT32 tmc; |
INT32 tmr; |
INT32 pc0; |
INT32 pc1; |
INT32 pc2; |
INT32 mmuc; |
INT32 lru; |
}; |
#define XP_CMD_SZ 15 * sizeof (INT32) |
/* #define XP_CMD_SZ sizeof(struct xp_cmd_t) */ |
|
|
INT32 |
i_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
INT32 result; |
|
if (strcmp(token[0], "ix") == 0) |
result = ix_cmd(token, token_count); |
else |
if (strcmp(token[0], "il") == 0) |
result = il_cmd(token, token_count); |
else |
result = EMSYNTAX; |
|
return (result); |
} /* end xcmd() */ |
|
|
|
/* |
** The function below is used to implement the MON29K-like |
** "i" commands. the function below, i_cmd() is called |
** in the main command loop parser of the monitor. The |
** parameters passed to this function are: |
** |
** token - This is an array of pointers to strings. Each string |
** referenced by this array is a "token" of the user's |
** input, translated to lower case. |
** |
** token_count - This is the number of tokens in "token". |
** |
** This function then calls the specific "i" commands, |
** such as "ix", "il" or "ia". |
*/ |
|
/* |
** il |
** This command will dissasseble the contents of the cache |
** This command is used to examine the contents of the cache |
** in the Am29030. First set 0 is printed, starting with the |
** This command will dissasseble the contents of the cache |
** tag, followed by a disassembly of four instructions in |
** the set. Set 1 for the line follows similarly. |
** |
** The data comes in from the READ_ACK message in the following |
** order: |
** |
** tag (data[0-3] (set 0) |
** instr1 (data[4-7] |
** instr1 (data[8-11] |
** instr1 (data[12-15] |
** instr1 (data[16-19] |
** |
** tag (data[20-23] (set 1) |
** instr1 (data[24-27] |
** instr1 (data[28-31] |
** instr1 (data[32-35] |
** instr1 (data[36-39] |
*/ |
|
INT32 |
il_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
static INT32 memory_space=I_CACHE; |
static ADDR32 cache_line=0; |
static INT32 byte_count=(10*sizeof(INST32)); |
static INT32 count=1; |
ADDR32 address; |
INT32 i; |
int j; |
int set; |
int index; |
int result; |
struct instr_t instr; |
INT32 cache_line_start; |
INT32 cache_line_end; |
|
INT32 retval; |
INT32 bytes_ret; |
INT32 host_endian; |
BYTE read_buffer[10*sizeof(INST32)]; |
char prtbuf[256]; |
|
|
/* Is it an 'il' command? */ |
if (strcmp(token[0], "il") != 0) |
return (EMSYNTAX); |
|
/* |
** Parse parameters |
*/ |
|
if (token_count == 1) { |
cache_line = cache_line + count; |
} |
else |
if (token_count == 2) { |
result = get_word(token[1], &cache_line_start); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_start < 0) || |
(cache_line_start >255)) |
return (EMBADADDR); |
cache_line = cache_line_start; |
} |
else |
if (token_count == 3) { |
/* Get first cache line to be dumped */ |
result = get_word(token[1], &cache_line_start); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_start < 0) || |
(cache_line_start > 255)) |
return (EMBADADDR); |
/* Get last cache line to be dumped */ |
result = get_word(token[2], &cache_line_end); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_end < 0) || |
(cache_line_end > 255)) |
return (EMBADADDR); |
if (cache_line_start > cache_line_end) |
return (EMBADADDR); |
cache_line = cache_line_start; |
count = (cache_line_end - cache_line_start) + 1; |
} |
else |
/* Too many args */ |
return (EMSYNTAX); |
|
i = 0; |
while (i < count) { |
|
host_endian = FALSE; |
if ((retval = Mini_read_req(memory_space, |
(cache_line + i), |
byte_count/4, |
(INT16) 4, /* size */ |
&bytes_ret, |
read_buffer, |
host_endian)) != SUCCESS) { |
return(FAILURE); |
}; |
/* The following is executed if SUCCESSful */ |
|
for (set=0; set<2; set++) { |
|
/* Print out formatted address tag and status information */ |
index = (set * 20); |
sprintf(&prtbuf[0], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "Cache line 0x%lx, set %d.\n", (int) (cache_line+i), set); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "IATAG V P US\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "%02x%02x%1x %1x %1x %1x\n", |
read_buffer[index], |
read_buffer[index + 1], |
((read_buffer[index + 2] >> 4) & 0x0f), |
((read_buffer[index + 3] >> 2) & 0x01), |
((read_buffer[index + 3] >> 1) & 0x01), |
(read_buffer[index + 3] & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Address = IATAG + line_number + <16 byte adddress> */ |
address = ((read_buffer[index] << 24) | |
(read_buffer[index + 1] << 16) | |
(read_buffer[index + 2] << 8) | |
((cache_line+i) << 4)); |
|
/* Disassemble four words */ |
for (j=0; j<4; j=j+1) { |
index = (set * 20) + ((j+1) * sizeof(INT32)); |
instr.op = read_buffer[index]; |
instr.c = read_buffer[index + 1]; |
instr.a = read_buffer[index + 2]; |
instr.b = read_buffer[index + 3]; |
|
/* Print address of instruction (in hex) */ |
address = (address & 0xfffffff0); /* Clear low four bits */ |
address = (address | (j << 2)); |
fprintf(stderr, "%08lx ", address); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%08lx ", address); |
|
/* Print instruction (in hex) */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
fprintf(stderr, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
|
/* Disassemble instruction */ |
dasm_instr(address, &instr); |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
} /* end for(j) */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
} /* end for(set) */ |
|
i = i + 1; |
|
} /* end while loop */ |
|
return (0); |
|
} /* end il_cmd() */ |
|
|
|
/* |
** ix |
** This command will dump the contents of the cache in hex |
** This command is used to examine the contents of the cache |
** in the Am29030. |
** First set 0 is printed, starting with the |
** tag, followed by a disassembly of four instructions in |
** the set. Set 1 for the line follows similarly. |
** |
** The data comes in from the READ_ACK message in the following |
** order: |
** |
** tag (data[0-3] (set 0) |
** instr1 (data[4-7] |
** instr1 (data[8-11] |
** instr1 (data[12-15] |
** instr1 (data[16-19] |
** |
** tag (data[20-23] (set 1) |
** instr1 (data[24-27] |
** instr1 (data[28-31] |
** instr1 (data[32-35] |
** instr1 (data[36-39] |
*/ |
|
INT32 |
ix_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
static INT32 memory_space=I_CACHE; |
static ADDR32 cache_line=0; |
static INT32 byte_count=(10*sizeof(INST32)); |
static INT32 count=1; |
ADDR32 address; |
INT32 i; |
int j; |
int set; |
int index; |
int result; |
struct instr_t instr; |
INT32 cache_line_start; |
INT32 cache_line_end; |
|
INT32 retval; |
INT32 bytes_ret; |
INT32 host_endian; |
BYTE read_buffer[10*sizeof(INST32)]; |
char prtbuf[256]; |
|
|
/* Is it an 'ix' command? */ |
if (strcmp(token[0], "ix") != 0) |
return (EMSYNTAX); |
|
/* |
** Parse parameters |
*/ |
if (token_count == 1) { |
cache_line = cache_line + count; |
} |
else |
if (token_count == 2) { |
result = get_word(token[1], &cache_line_start); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_start < 0) || |
(cache_line_start >255)) |
return (EMBADADDR); |
cache_line = cache_line_start; |
} |
else |
if (token_count == 3) { |
/* Get first cache line to be dumped */ |
result = get_word(token[1], &cache_line_start); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_start < 0) || |
(cache_line_start > 255)) |
return (EMBADADDR); |
/* Get last cache line to be dumped */ |
result = get_word(token[2], &cache_line_end); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_end < 0) || |
(cache_line_end > 255)) |
return (EMBADADDR); |
if (cache_line_start > cache_line_end) |
return (EMBADADDR); |
cache_line = cache_line_start; |
count = (cache_line_end - cache_line_start) + 1; |
} |
else |
/* Too many args */ |
return (EMSYNTAX); |
|
i = 0; |
while (i < count) { |
|
host_endian = FALSE; |
if ((retval = Mini_read_req(memory_space, |
(cache_line + i), |
byte_count/4, |
(INT16) 4, /* size */ |
&bytes_ret, |
read_buffer, |
host_endian)) != SUCCESS) { |
return(FAILURE); |
}; |
/* The following is executed if SUCCESSful */ |
|
for (set=0; set<2; set++) { |
|
/* Print out formatted address tag and status information */ |
index = (set * 20); |
sprintf(&prtbuf[0], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "Cache line 0x%lx, set %d.\n", (int) (cache_line+i), set); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "IATAG V P US\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "%02x%02x%1x %1x %1x %1x\n", |
read_buffer[index], |
read_buffer[index + 1], |
((read_buffer[index + 2] >> 4) & 0x0f), |
((read_buffer[index + 3] >> 2) & 0x01), |
((read_buffer[index + 3] >> 1) & 0x01), |
(read_buffer[index + 3] & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Address = IATAG + line_number + <16 byte adddress> */ |
address = ((read_buffer[index] << 24) | |
(read_buffer[index + 1] << 16) | |
(read_buffer[index + 2] << 8) | |
((cache_line+i) << 4)); |
|
/* Disassemble four words */ |
for (j=0; j<4; j=j+1) { |
index = (set * 20) + ((j+1) * sizeof(INT32)); |
instr.op = read_buffer[index]; |
instr.c = read_buffer[index + 1]; |
instr.a = read_buffer[index + 2]; |
instr.b = read_buffer[index + 3]; |
|
/* Print address of instruction (in hex) */ |
address = (address & 0xfffffff0); /* Clear low four bits */ |
address = (address | (j << 2)); |
fprintf(stderr, "%08lx ", address); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%08lx ", address); |
|
/* Print instruction (in hex) */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
fprintf(stderr, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
|
/* Disassemble instruction */ |
dasm_instr(address, &instr); |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
} /* end for(j) */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
} /* end for(set) */ |
|
i = i + 1; |
|
} /* end while loop */ |
|
return (0); |
|
} /* end ix_cmd() */ |
|
|
/mini2udi.c
0,0 → 1,1326
static char _[] = "@(#)mini2udi.c 5.23 93/08/18 13:48:08, Srini, AMD. "; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
* Definitions of the functions that define Minimon's Interface |
* to the UDI |
* interface The minimon functions are declared in miniint.h The UDI |
* functions are declared in udi/udiproc.h |
***************************************************************************** |
*/ |
|
|
#include <stdio.h> |
#ifdef MSDOS |
#include <io.h> |
#endif |
#include <string.h> |
#include "main.h" |
#include "memspcs.h" |
#include "macros.h" |
#include "miniint.h" |
#include "udiproc.h" |
#include "udiids.h" |
#include "udiext.h" |
#include "versions.h" |
|
|
/* Define BreakIdType here to avoid having to change at many places |
* every time it changes. |
*/ |
typedef unsigned int BreakIdType; |
|
/* ABOUT UDI calls: |
* There are three types of return values: |
* < 0: means a TIP failure. |
* = 0: means success. |
* > 0: means a "local" failure. |
*/ |
|
|
|
static UDISessionId SessionID; |
static char MONErrorMsg[MONErrorMsgSize]; |
static int GoForever=0; |
|
static char *udi_errmsg[] = { |
/* |
#define UDINoError 0 |
*/ "UDIERR: No Error", |
/* |
#define UDIErrorNoSuchConfiguration 1 |
*/ "UDIERR: No Such Configuration in Config File.", |
/* |
#define UDIErrorCantHappen 2 |
*/ "UDIERR: Cannot Happen With Current Environment Setup.", |
/* |
#define UDIErrorCantConnect 3 |
*/ "UDIERR: Cannot Connect to TIP Specified.", |
/* |
#define UDIErrorNoSuchConnection 4 |
*/ "UDIERR: No Such Connection Found.", |
/* |
#define UDIErrorNoConnection 5 |
*/ "UDIERR: No Connection Occurred.", |
/* |
#define UDIErrorCantOpenConfigFile 6 |
*/ "UDIERR: Cannot Open UDI Config File.", |
/* |
#define UDIErrorCantStartTIP 7 |
*/ "UDIERR: Cannot Start TIP In Current Environment Setup.", |
/* |
#define UDIErrorConnectionUnavailable 8 |
*/ "UDIERR: Requested Connection Unavailable.", |
/* |
#define UDIErrorTryAnotherTIP 9 |
*/ "UDIERR: Try Another TIP For Connection.", |
/* |
#define UDIErrorExecutableNotTIP 10 |
*/ "UDIERR: TIP Specified in Config File Not An Executable.", |
/* |
#define UDIErrorInvalidTIPOption 11 |
*/ "UDIERR: Connection Failed Due To Invalid TIP Options in Config File.", |
/* |
#define UDIErrorCantDisconnect 12 |
*/ "UDIERR: Cannot Disconnect TIP", |
/* |
#define UDIErrorUnknownError 13 |
*/ "UDIERR: Unknown Error Number Specified.", |
/* |
#define UDIErrorCantCreateProcess 14 |
*/ "UDIERR: TIP Cannot Create a New Process.", |
/* |
#define UDIErrorNoSuchProcess 15 |
*/ "UDIERR: No Such Process in the Current TIP.", |
/* |
#define UDIErrorUnknownResourceSpace 16 |
*/ "UDIERR: Unknown Resource Space Encountered By TIP.", |
/* |
#define UDIErrorInvalidResource 17 |
*/ "UDIERR: Invalid Resource Specified To TIP.", |
/* |
#define UDIErrorUnsupportedStepType 18 |
*/ "UDIERR: Unsupported Step Type For This TIP Specified.", |
/* |
#define UDIErrorCantSetBreakpoint 19 |
*/ "UDIERR: Could Not Set The Breakpoint.", |
/* |
#define UDIErrorTooManyBreakpoints 20 |
*/ "UDIERR: Too Many Breakpoints Already In Use.", |
/* |
#define UDIErrorInvalidBreakId 21 |
*/ "UDIERR: Breakpoint Does Not Exist For This BreakId.", |
/* |
#define UDIErrorNoMoreBreakIds 22 |
*/ "UDIERR: No More Breakpoints. BreakId Too High.", |
/* |
#define UDIErrorUnsupportedService 23 |
*/ "UDIERR: TIP Does Not Support The Requested Service.", |
/* |
#define UDIErrorTryAgain 24 |
*/ "UDIERR: Error Occurred. Trying Again.", |
/* |
#define UDIErrorIPCLimitation 25 |
*/ "UDIERR: IPC Limitation Exceeded.", |
/* |
#define UDIErrorIncomplete 26 |
*/ "UDIERR: Service Incomplete.More Data Available.", |
/* |
#define UDIErrorAborted 27 |
*/ "UDIERR: Aborted Requested Service.", |
/* |
#define UDIErrorTransDone 28 |
*/ "UDIERR: Transaction Completed.", |
/* |
#define UDIErrorCantAccept 29 |
*/ "UDIERR: Cannot Accept.", |
/* |
#define UDIErrorTransInputNeeded 30 |
*/ "UDIERR: Transaction Input Needed.", |
/* |
#define UDIErrorTransModeX 31 |
*/ "UDIERR: Transaction ModeX", |
/* |
#define UDIErrorInvalidSize 32 |
*/ "UDIERR: Invalid Object Size Specified.", |
/* |
#define UDIErrorBadConfigFileEntry 33 |
*/ "UDIERR: Bad Entry In UDI Config File Found.", |
/* |
#define UDIErrorIPCInternal 34 |
*/ "UDIERR: Internal Error Occurred In IPC Layer." |
}; |
|
static UDIPId CurrentPID=(UDIPId) UDIProcessProcessor; |
static void PrintErrorMessage PARAMS((UDIError num)); |
static void udi_warning PARAMS((int num)); |
static CPUSpace xlate_mspace_mon2udi PARAMS((INT32 mspace)); |
static INT32 xlate_mspace_udi2mon PARAMS((CPUSpace mspace)); |
static UDIError FillString PARAMS(( UDIResource from, |
UDIHostMemPtr pattern, |
UDISizeT pattern_count, |
UDICount fill_count)); |
static UDIError FillWords PARAMS(( UDIResource from, |
UDIHostMemPtr pattern, |
UDISizeT pattern_count, |
UDICount fill_count)); |
|
|
INT32 |
/*********************************************Mini_TIP_init */ |
Mini_TIP_init(connect_string, mon_session_id) |
char *connect_string; |
int *mon_session_id; |
{ |
UDIError UDIretval; |
UDISessionId session; |
|
/* First connect the target */ |
if ((UDIretval = UDIConnect(connect_string, |
&session)) <= TIPFAILURE) { |
SessionID = session; |
*mon_session_id = (int) session; |
PrintErrorMessage (UDIretval); |
return ((INT32) UDIretval); |
} else if (UDIretval == SUCCESS) { |
SessionID = session; |
*mon_session_id = (int) session; |
return (SUCCESS); |
} else { |
SessionID = session; |
*mon_session_id = (int) session; |
udi_warning(UDIretval); |
return((INT32) UDIretval); |
}; |
} |
|
INT32 |
Mini_TIP_Capabilities() |
{ |
UDIError UDIretval; |
UDIUInt32 TIPId; /* Out */ |
UDIUInt32 TargetId; /* Out */ |
UDIUInt32 DFEId; /* In */ |
UDIUInt32 DFE; /* In */ |
UDIUInt32 TIP; /* Out */ |
UDIUInt32 DFEIPCId; /* Out */ |
UDIUInt32 TIPIPCId; /* Out */ |
char TIPString[80]; /* Out */ |
|
(void) strcpy (TIPString,""); |
DFEId = (UDIUInt32) UDIID (UDIProductCode_Mondfe, MONDFERev, MONDFESubRev, MONDFESubSubRev); |
DFE = (UDIUInt32) MONDFEUDIVers; |
if ((UDIretval = UDICapabilities ( &TIPId, |
&TargetId, |
DFEId, |
DFE, |
&TIP, |
&DFEIPCId, |
&TIPIPCId, |
&TIPString[0])) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
if (!QuietMode) { |
if (io_config.echo_mode == (INT32) TRUE) { |
fprintf(io_config.echo_file, "MiniMON29K Release 3.0\n"); |
fprintf(io_config.echo_file, ">AMD MONDFE Version: %d.%d.%d", |
(int) ((DFEId & 0x00000F00) >> 8), |
(int) ((DFEId & 0x000000F0) >> 4), |
(int) ((DFEId & 0x0000000F) >> 0)); |
fprintf(io_config.echo_file, "\tIPC Version: %d.%d.%d UDI Rev. %d.%d.%d <\n", |
(int) ((DFEIPCId & 0x00000F00) >> 8), |
(int) ((DFEIPCId & 0x000000F0) >> 4), |
(int) ((DFEIPCId & 0x0000000F) >> 0), |
(int) ((DFE & 0x00000F00) >> 8), |
(int) ((DFE & 0x000000F0) >> 4), |
(int) ((DFE & 0x0000000F) >> 0)); |
fprintf(io_config.echo_file, "%s\n", TIPString); |
fprintf(io_config.echo_file, ">TIP Version: %d.%d.%d", |
(int) ((TIPId & 0x00000F00) >> 8), |
(int) ((TIPId & 0x000000F0) >> 4), |
(int) ((TIPId & 0x0000000F) >> 0)); |
fprintf(io_config.echo_file, "\tIPC Version: %d.%d.%d UDI Rev. %d.%d.%d<\n", |
(int) ((TIPIPCId & 0x00000F00) >> 8), |
(int) ((TIPIPCId & 0x000000F0) >> 4), |
(int) ((TIPIPCId & 0x0000000F) >> 0), |
(int) ((TIP & 0x00000F00) >> 8), |
(int) ((TIP & 0x000000F0) >> 4), |
(int) ((TIP & 0x0000000F) >> 0)); |
} |
fprintf(stderr, "MiniMON29K Release 3.0\n"); |
fprintf(stderr, ">AMD MONDFE Version: %d.%d.%d", |
(int) ((DFEId & 0x00000F00) >> 8), |
(int) ((DFEId & 0x000000F0) >> 4), |
(int) ((DFEId & 0x0000000F) >> 0)); |
fprintf(stderr, "\tIPC Version: %d.%d.%d UDI Rev. %d.%d.%d <\n", |
(int) ((DFEIPCId & 0x00000F00) >> 8), |
(int) ((DFEIPCId & 0x000000F0) >> 4), |
(int) ((DFEIPCId & 0x0000000F) >> 0), |
(int) ((DFE & 0x00000F00) >> 8), |
(int) ((DFE & 0x000000F0) >> 4), |
(int) ((DFE & 0x0000000F) >> 0)); |
fprintf(stderr, "%s\n", TIPString); |
fprintf(stderr, ">TIP Version: %d.%d.%d", |
(int) ((TIPId & 0x00000F00) >> 8), |
(int) ((TIPId & 0x000000F0) >> 4), |
(int) ((TIPId & 0x0000000F) >> 0)); |
fprintf(stderr, "\tIPC Version: %d.%d.%d UDI Rev. %d.%d.%d<\n", |
(int) ((TIPIPCId & 0x00000F00) >> 8), |
(int) ((TIPIPCId & 0x000000F0) >> 4), |
(int) ((TIPIPCId & 0x0000000F) >> 0), |
(int) ((TIP & 0x00000F00) >> 8), |
(int) ((TIP & 0x000000F0) >> 4), |
(int) ((TIP & 0x0000000F) >> 0)); |
} |
if ( (int) ((TIPId & 0x00000F00) >> 8) < |
(int) ((DFEId & 0x00000F00) >> 8) ) { |
fprintf(stderr, "!!!!! WARNING: MONTIP's major version number is older than that of MONDFE's !!!!!\n"); |
fprintf(stderr, "!!!!! Please verify the versions and call AMD 29K Technical Support for assistance. !!!!!\n"); |
} |
if ((TIP == (UDIUInt32) 0) || ((TIP & 0xFFF) > (DFE & 0xFFF))) { |
fprintf(stderr, "UDI WARNING: UDI Versions NOT Compatible.\n"); |
} |
if (TIP == (UDIUInt32) 0) |
return (FAILURE); |
return (SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
INT32 |
Mini_TIP_CreateProc() |
{ |
UDIError UDIretval; |
UDIPId pid; |
|
if ((UDIretval = UDICreateProcess(&pid)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
CurrentPID = pid; |
return (SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
INT32 |
Mini_TIP_disc() |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIDisconnect(SessionID, |
UDIContinueSession)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
INT32 |
Mini_TIP_SetCurrSession(sid) |
int sid; |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDISetCurrentConnection((UDISessionId) sid)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
SessionID = (UDISessionId) sid; |
return (SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
INT32 |
Mini_TIP_SetPID(pid) |
int pid; |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDISetCurrentProcess((UDIPId) pid)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return (SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
INT32 |
Mini_TIP_DestroyProc() |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIDestroyProcess(CurrentPID)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return (SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
INT32 |
Mini_TIP_exit() |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIDisconnect(SessionID, |
UDITerminateSession)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
/* Breakpoint routines */ |
|
/* Remove breakpoint */ |
INT32 |
/*******************************************Mini_bkpt_rm */ |
Mini_bkpt_rm(break_id) |
int break_id; |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIClearBreakpoint ((BreakIdType) break_id)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
/* Set Breakpoints */ |
|
INT32 |
/**********************************************Mini_bkpt_set */ |
Mini_bkpt_set(m_space, address, pass_count, type, break_id) |
INT32 m_space; |
ADDR32 address; |
INT32 pass_count; |
INT32 type; |
int *break_id; |
{ |
UDIResource addr; |
UDIError UDIretval; |
|
|
addr.Space = xlate_mspace_mon2udi(m_space); |
addr.Offset = address; |
|
if (type == BKPT_29000) |
type = (UDIBreakType) UDIBreakFlagExecute; |
else if (type == BKPT_29050) |
type = (UDIBreakType) (MONBreakFlagHardware | UDIBreakFlagExecute); |
else if (type == BKPT_29050_BTE_0) |
type = (UDIBreakType) (MONBreakFlagHardware | UDIBreakFlagExecute); |
else if (type == BKPT_29050_BTE_1) |
type = (UDIBreakType) (MONBreakTranslationEnabled | MONBreakFlagHardware | UDIBreakFlagExecute); |
|
if ((UDIretval = UDISetBreakpoint(addr, |
(UDIInt32) pass_count, |
(UDIBreakType) type, |
(BreakIdType *) break_id)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
/* Query (get status) Breakpoints */ |
|
INT32 |
/**********************************************Mini_bkpt_stat */ |
Mini_bkpt_stat(break_id, address, m_space, pass_count, |
bkpt_type, current_cnt) |
int break_id; |
INT32 *m_space; |
ADDR32 *address; |
INT32 *pass_count; |
INT32 *bkpt_type; |
INT32 *current_cnt; |
{ |
UDIError UDIretval; |
UDIResource addr; |
|
if ((UDIretval = UDIQueryBreakpoint ((BreakIdType) break_id, |
&addr, |
(UDIInt32 *)pass_count, |
(UDIBreakType *) bkpt_type, |
(UDIInt32 *) current_cnt)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
*address = addr.Offset; |
*m_space = xlate_mspace_udi2mon(addr.Space); |
if (*bkpt_type & MONBreakFlagHardware) |
*bkpt_type = BKPT_29050; |
return(SUCCESS); |
} else { |
if (UDIretval == UDIErrorNoMoreBreakIds) |
return ((INT32) MONBreakNoMore); |
else if (UDIretval == UDIErrorInvalidBreakId) |
return ((INT32) MONBreakInvalid); |
else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
}; |
} |
|
/* Kill Target */ |
|
INT32 |
/**********************************************Mini_break */ |
Mini_break() |
{ |
|
UDIStop(); |
return (SUCCESS); |
} |
|
/* Obtain Target configuration and resynchronize with target */ |
|
UDIInt32 |
/**********************************************Mini_config_req */ |
Mini_config_req(target_config, versions) |
TARGET_CONFIG *target_config; |
VERSIONS_ETC *versions; |
{ |
UDIError UDIretval; |
UDIMemoryRange DFEMemRange[MONMaxMemRanges]; |
UDIUInt32 ChipVersions[MONMaxChips]; |
UDIInt NumRanges, NumChips; |
UDIInt i; |
|
NumRanges = (UDIInt) MONMaxMemRanges; |
NumChips = (UDIInt) MONMaxChips; |
|
if ((UDIretval = UDIGetTargetConfig( |
(UDIMemoryRange *) &DFEMemRange[0], |
(UDIInt *) &NumRanges, /* 3 -> I, D, R */ |
(UDIUInt32 *) &ChipVersions[0], |
(UDIInt *) &NumChips)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return(FAILURE); |
} else if ((UDIretval == SUCCESS) || (UDIretval == UDIErrorIncomplete)) { |
if (UDIretval == UDIErrorIncomplete) { |
fprintf(stderr, "Ignoring: "); |
if (io_config.echo_mode == (INT32) TRUE) { |
fprintf(io_config.echo_file, "Ignoring: "); |
fflush (io_config.echo_file); |
} |
udi_warning(UDIretval); |
}; |
i = (UDIInt) 0; |
while ((i < (UDIInt) MONMaxMemRanges) && (i < NumRanges)) { |
switch ((int) DFEMemRange[i].Space) { |
case UDI29KDRAMSpace: |
target_config->D_mem_start = (ADDR32) DFEMemRange[i].Offset; |
target_config->D_mem_size = (INT32) DFEMemRange[i].Size; |
break; |
case UDI29KIROMSpace: |
target_config->ROM_start = (ADDR32) DFEMemRange[i].Offset; |
target_config->ROM_size = (INT32) DFEMemRange[i].Size; |
break; |
case UDI29KIRAMSpace: |
target_config->I_mem_start = (ADDR32) DFEMemRange[i].Offset; |
target_config->I_mem_size = (INT32) DFEMemRange[i].Size; |
break; |
default: /* don't care, so ignore it */ |
break; |
}; |
i = i + (UDIInt) 1; |
} /* end while */ |
i = (UDIInt) 0; |
while ((i < (UDIInt) MONMaxChips) && (i < NumChips)) { |
switch (i) { |
case 0: /* cpu */ |
target_config->processor_id = (UINT32) ChipVersions[i]; |
break; |
case 1: /* coprocessor */ |
target_config->coprocessor = (UINT32) ChipVersions[i]; |
if (target_config->coprocessor == (UINT32) UDI29KChipNotPresent) |
target_config->coprocessor = (UINT32) -1; /* MONDFE's */ |
break; |
default: /* ignore */ |
break; |
}; |
i = i + (UDIInt) 1; |
} /* end while */ |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
|
/* Copy memory and registers */ |
|
|
INT32 |
/**********************************************Mini_copy */ |
Mini_copy(src_space, src_addr, dst_space, dst_addr, byte_count, size, dir) |
INT32 src_space, |
dst_space; |
ADDR32 src_addr, |
dst_addr; |
INT32 byte_count; |
INT16 size; |
INT32 dir; |
{ |
UDIError UDIretval; |
UDIResource from, to; |
UDICount count_done; |
|
from.Space = xlate_mspace_mon2udi(src_space); |
from.Offset = src_addr; |
to.Space = xlate_mspace_mon2udi(dst_space); |
to.Offset = dst_addr; |
|
if ((UDIretval = UDICopy (from, |
to, |
(UDICount) byte_count, |
(UDISizeT) size, |
&count_done, |
(UDIBool) dir)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
/* Fill memory and registers */ |
|
|
/* fill_count if greater than 4 should be a multiple of 4 */ |
INT32 |
/**********************************************Mini_fill */ |
Mini_fill(m_space, start, fill_count, pattern_count, pattern) |
INT32 m_space; |
ADDR32 start; |
INT32 fill_count, |
pattern_count; |
BYTE *pattern; |
{ |
UDIBool host_endian; |
UDIResource from; |
UDICount count_done; |
UDIError UDIretval; |
|
host_endian = FALSE; |
|
from.Offset = start; |
from.Space = xlate_mspace_mon2udi (m_space); |
|
if (fill_count == (INT32) 1) { /* takes only one write */ |
if ((UDIretval = UDIWrite((UDIHostMemPtr) pattern, |
from, |
(UDICount) fill_count, |
(UDISizeT) pattern_count, /* a byte at a time */ |
(UDICount *) &count_done, |
host_endian)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} else { |
/* Handle arbitrary length strings to Data memory separately */ |
if ((pattern_count > (INT32) 4) && |
((int) (pattern_count % 4) != (int) 0)){ |
if (from.Space != UDI29KDRAMSpace) |
return (FAILURE); |
return((INT32) FillString(from, (UDIHostMemPtr) pattern, |
(UDISizeT) pattern_count, (UDICount) fill_count)); |
} else { |
return((INT32) FillWords(from, (UDIHostMemPtr) pattern, |
(UDISizeT) pattern_count, (UDICount) fill_count)); |
} |
}; |
} |
|
/* Initiate a wait and get target status */ |
|
INT32 |
/**********************************************Mini_get_target_stats */ |
Mini_get_target_stats(maxtime, target_status) |
INT32 maxtime; |
INT32 *target_status; |
{ |
UDIPId pid; |
UDIError UDIretval; |
UDIInt32 udiwait_code; |
|
if (maxtime == (INT32) -1) { |
udiwait_code = (UDIInt32) UDIWaitForever; |
} else { |
udiwait_code = (UDIInt32) maxtime; |
}; |
if ((UDIretval = UDIWait ((UDIInt32) udiwait_code, |
&pid, |
(UDIUInt32 *) target_status)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (SUCCESS); /* considered non-fatal */ |
} else if (UDIretval == SUCCESS) { |
CurrentPID = (UDIPId) pid; /* useful when reconnecting */ |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
|
INT32 |
/**********************************************Mini_go */ |
Mini_go() |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIExecute()) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
INT32 |
/**********************************************Mini_init */ |
Mini_init(txt_start, txt_end, dat_start, dat_end, |
entry_point, m_stack, r_stack, |
arg_string) |
ADDR32 txt_start, |
txt_end, |
dat_start, |
dat_end; |
ADDR32 entry_point; |
INT32 m_stack, |
r_stack; |
char *arg_string; |
{ |
UDIMemoryRange ProcessMemory[MONMaxProcessMemRanges]; |
UDIInt NumRanges; |
UDIResource Entry; |
CPUSizeT StackSizes[MONMaxStacks]; |
UDIInt NumStacks; |
UDIError UDIretval; |
|
NumRanges = (UDIInt) MONMaxProcessMemRanges; |
NumStacks = (UDIInt) MONMaxStacks; |
ProcessMemory[0].Space = (CPUSpace) UDI29KIRAMSpace; |
ProcessMemory[0].Offset = (CPUOffset) txt_start; |
ProcessMemory[0].Size = (CPUSizeT) (txt_end - txt_start); |
ProcessMemory[1].Space = (CPUSpace) UDI29KDRAMSpace; |
ProcessMemory[1].Offset = (CPUOffset) dat_start; |
ProcessMemory[1].Size = (CPUSizeT) (dat_end - dat_start); |
Entry.Offset = entry_point; |
Entry.Space = xlate_mspace_mon2udi((INT32) I_MEM); |
StackSizes[0] = (CPUSizeT) r_stack; |
StackSizes[1] = (CPUSizeT) m_stack; |
|
if ((UDIretval = UDIInitializeProcess (&ProcessMemory[0], |
(UDIInt) NumRanges, |
Entry, |
&StackSizes[0], |
(UDIInt) NumStacks, |
arg_string)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
|
/* Read memory or registers from target */ |
INT32 |
/**********************************************Mini_read_req */ |
Mini_read_req(m_space, address, byte_count, size, count_done, |
buffer, host_endian) |
INT32 m_space; |
ADDR32 address; |
INT32 byte_count; |
INT16 size; |
INT32 host_endian; |
INT32 *count_done; |
BYTE *buffer; |
{ |
UDIError UDIretval; |
UDIResource from; |
|
from.Space = xlate_mspace_mon2udi(m_space); |
from.Offset = address; |
|
if ((UDIretval = UDIRead (from, |
(UDIHostMemPtr) buffer, |
(UDICount) byte_count, |
(UDISizeT) size, |
(UDICount *) count_done, |
(UDIBool) host_endian)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return(FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
/* |
* Reset target processor |
*/ |
INT32 |
/**********************************************Mini_reset_processor */ |
Mini_reset_processor() |
{ |
UDIMemoryRange ProcessMemory[MONMaxProcessMemRanges]; |
UDIInt NumRanges; |
UDIResource Entry; |
CPUSizeT StackSizes[MONMaxStacks]; |
UDIInt NumStacks; |
UDIError UDIretval; |
UDIPId CurrentPID; |
UDIUInt32 StopReason; |
|
|
NumRanges = (UDIInt) MONMaxProcessMemRanges; |
NumStacks = (UDIInt) MONMaxStacks; |
ProcessMemory[0].Space = (CPUSpace) UDI29KIRAMSpace; |
ProcessMemory[0].Offset = (CPUOffset) 0; |
ProcessMemory[0].Size = (CPUSizeT) 0; |
ProcessMemory[0].Space = (CPUSpace) UDI29KIRAMSpace; |
ProcessMemory[0].Offset = (CPUOffset) 0; |
ProcessMemory[0].Size = (CPUSizeT) 0; |
Entry.Offset = 0; |
Entry.Space = xlate_mspace_mon2udi((INT32) I_MEM); |
StackSizes[0] = (CPUSizeT) 0; |
StackSizes[1] = (CPUSizeT) 0; |
|
if ((UDIretval = UDIWait((UDIInt32) 0, &CurrentPID, &StopReason)) |
<= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return(FAILURE); |
} else if (UDIretval != SUCCESS) { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
/* set PID to ProcProcessor */ |
if (( UDIretval = UDISetCurrentProcess((UDIPId) UDIProcessProcessor)) |
<= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return(FAILURE); |
} else if (UDIretval != SUCCESS) { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
/* Successful */ |
/* call InitializeProcess. Paramters ignored. */ |
if ((UDIretval = UDIInitializeProcess (&ProcessMemory[0], |
(UDIInt) NumRanges, |
Entry, |
&StackSizes[0], |
(UDIInt) NumStacks, |
(char *) 0)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return(FAILURE); |
} else if (UDIretval != SUCCESS) { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
/* Successful */ |
if (( UDIretval = UDISetCurrentProcess((UDIPId) CurrentPID)) |
<= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return(FAILURE); |
} else if (UDIretval != SUCCESS) { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
return (SUCCESS); |
} |
|
/* Write memory or registers to target */ |
INT32 |
/**********************************************Mini_write_req */ |
Mini_write_req(m_space, address, byte_count, size, count_done, |
buffer, host_endian) |
INT32 m_space; |
ADDR32 address; |
INT32 byte_count; |
INT16 size; |
INT32 *count_done; |
BYTE *buffer; |
INT32 host_endian; |
{ |
UDIError UDIretval; |
UDIResource to; |
|
to.Space = xlate_mspace_mon2udi(m_space); |
to.Offset = address; |
|
if ((UDIretval = UDIWrite((UDIHostMemPtr) buffer, |
to, |
(UDICount) byte_count, |
(UDISizeT) size, |
(UDICount *) count_done, |
(UDIBool) host_endian)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return(FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
INT32 |
Mini_stdin_mode_x(mode) |
INT32 *mode; |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIStdinMode ((UDIMode *) mode)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
INT32 |
/**********************************************Mini_put_stdin */ |
Mini_put_stdin(buffer, bufsize, count) |
char *buffer; |
INT32 bufsize; |
INT32 *count; |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIPutStdin ((UDIHostMemPtr) buffer, |
(UDISizeT) bufsize, |
(UDISizeT *) count)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
/* Put characters to stdout */ |
|
|
INT32 |
/**********************************************Mini_get_stdout */ |
Mini_get_stdout(buffer, bufsize, count_done) |
char *buffer; |
INT32 *count_done; |
INT32 bufsize; |
{ |
UDIError UDIretval; |
|
if ((UDIretval = UDIGetStdout ((UDIHostMemPtr) buffer, |
(UDISizeT) bufsize, |
(UDISizeT *) count_done)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
INT32 |
/**********************************************Mini_get_stderr */ |
Mini_get_stderr(buffer, bufsize, count_done) |
char *buffer; |
INT32 *count_done; |
INT32 bufsize; |
{ |
UDIError UDIretval; |
if ((UDIretval = UDIGetStderr ((UDIHostMemPtr) buffer, |
(UDISizeT) bufsize, |
(UDISizeT *) count_done)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
} |
|
/* Step instructions */ |
|
|
INT32 |
/**********************************************Mini_step */ |
Mini_step(count) |
INT32 count; |
{ |
UDIError UDIretval; |
UDIRange dummy_range; |
UDIStepType step_type; |
|
dummy_range.Low = 0; |
dummy_range.High = 0xffffffff; |
|
step_type = UDIStepNatural; |
|
if ((UDIretval = UDIStep((UDIUInt32) count, |
step_type, |
dummy_range)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
INT32 |
/***************************************************** Mini_put_trans */ |
Mini_put_trans(buffer) |
char *buffer; |
{ |
UDIError UDIretval; |
UDISizeT count; |
UDISizeT *count_done; |
|
count = (UDISizeT) (strlen (buffer) + 1); |
if ((UDIretval = UDIPutTrans((UDIHostMemPtr) buffer, |
(UDISizeT) count, |
(UDISizeT *) count_done)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
|
} |
|
|
static CPUSpace |
xlate_mspace_mon2udi(m_space) |
INT32 m_space; |
{ |
switch(m_space) { |
case LOCAL_REG: |
return((CPUSpace) UDI29KLocalRegs); |
case ABSOLUTE_REG: |
return((CPUSpace) UDI29KGlobalRegs); |
case GLOBAL_REG: |
return((CPUSpace) UDI29KGlobalRegs); |
case SPECIAL_REG: |
return((CPUSpace) UDI29KSpecialRegs); |
case TLB_REG: |
return((CPUSpace) UDI29KTLBRegs); |
case COPROC_REG: |
return((CPUSpace) UDI29KAm29027Regs); |
case I_MEM: |
return((CPUSpace) UDI29KIRAMSpace); |
case D_MEM: |
return((CPUSpace) UDI29KDRAMSpace); |
case I_ROM: |
return((CPUSpace) UDI29KIROMSpace); |
case D_ROM: |
return((CPUSpace) UDI29KDRAMSpace); |
case I_O: |
return((CPUSpace) UDI29KIOSpace); |
case I_CACHE: |
return((CPUSpace) UDI29KICacheSpace); |
case D_CACHE: |
return((CPUSpace) UDI29KDCacheSpace); |
case PC_SPACE: |
return((CPUSpace) UDI29KPC); |
case A_SPCL_REG: |
return((CPUSpace) UDI29KSpecialRegs); |
case GENERIC_SPACE: |
return ((CPUSpace) UDI29KDRAMSpace); |
case VERSION_SPACE: |
return ((CPUSpace) VERSION_SPACE); |
default: |
return((CPUSpace) FAILURE); |
}; |
} |
|
static INT32 |
xlate_mspace_udi2mon(mspace) |
CPUSpace mspace; |
{ |
switch(mspace) { |
case UDI29KDRAMSpace: |
return((INT32) D_MEM); |
case UDI29KIOSpace: |
return((INT32) I_O); |
case UDI29KCPSpace0: |
return((INT32) FAILURE); |
case UDI29KCPSpace1: |
return((INT32) FAILURE); |
case UDI29KIROMSpace: |
return((INT32) I_ROM); |
case UDI29KIRAMSpace: |
return((INT32) I_MEM); |
case UDI29KLocalRegs: |
return((INT32) LOCAL_REG); |
case UDI29KGlobalRegs: |
return((INT32) GLOBAL_REG); |
case UDI29KRealRegs: |
return((INT32) GLOBAL_REG); |
case UDI29KSpecialRegs: |
return((INT32) SPECIAL_REG); |
case UDI29KTLBRegs: |
return((INT32) TLB_REG); |
case UDI29KACCRegs: |
return((INT32) FAILURE); |
case UDI29KICacheSpace: |
return((INT32) I_CACHE); |
case UDI29KAm29027Regs: |
return((INT32) COPROC_REG); |
case UDI29KPC: |
return((INT32) PC_SPACE); |
case UDI29KDCacheSpace: |
return((INT32) D_CACHE); |
default: |
return(FAILURE); |
}; |
} |
|
static |
void udi_warning(num) |
int num; |
{ |
fprintf(stderr, "UDIERROR: %d : %s\n", num, udi_errmsg[num]); |
fflush(stderr); |
if (io_config.echo_mode == (INT32) TRUE) { |
fprintf(io_config.echo_file, "UDIERROR: %d :%s\n", num, udi_errmsg[num]); |
fflush (io_config.echo_file); |
} |
} |
|
static void |
PrintErrorMessage(UDIretval) |
UDIError UDIretval; |
{ |
UDISizeT ErrorMsgCnt; |
|
fprintf(stderr, "TIPERROR: %d :", UDIretval); |
fflush(stderr); |
if (io_config.echo_mode == (INT32) TRUE) { |
fprintf(io_config.echo_file, "TIPERROR: %d :", UDIretval); |
fflush(io_config.echo_file); |
} |
|
ErrorMsgCnt = (UDISizeT) 0; |
do { |
if (UDIGetErrorMsg(UDIretval, |
(UDISizeT) MONErrorMsgSize, |
MONErrorMsg, &ErrorMsgCnt) != UDINoError) { |
fprintf(stderr, "TIPERROR: Could not get TIP error message.\n"); |
fflush(stderr); |
return; |
} |
write (fileno(stderr), &MONErrorMsg[0], (int) ErrorMsgCnt); |
if (io_config.echo_mode == (INT32) TRUE) |
write (fileno(io_config.echo_file), &MONErrorMsg[0], (int) ErrorMsgCnt); |
} while (ErrorMsgCnt == (UDISizeT) MONErrorMsgSize); |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) { |
fprintf(io_config.echo_file, "\n"); |
fflush(io_config.echo_file); |
} |
return; |
} |
|
static UDIError |
FillWords(from, pattern, pattern_count, fill_count) |
UDIResource from; |
UDIHostMemPtr pattern; |
UDISizeT pattern_count; |
UDICount fill_count; |
{ |
UDICount count_done; |
UDIBool host_endian, direction; |
UDIError UDIretval; |
UDIResource to; |
|
INT32 isregspace = ISREG(xlate_mspace_udi2mon(from.Space)); |
|
host_endian = FALSE; |
|
if ((UDIretval = UDIWrite((UDIHostMemPtr) pattern, |
from, |
(UDICount) 1, |
(UDISizeT) pattern_count, |
(UDICount *) &count_done, |
host_endian)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { /* do copy */ |
fill_count = fill_count - 1; /* one less */ |
if (fill_count > (INT32) 0) { /* do copy */ |
if (isregspace) |
to.Offset = from.Offset + (pattern_count/4); |
else |
to.Offset = from.Offset + pattern_count; |
to.Space = from.Space; /* already translated */ |
direction = TRUE; /* front to back */ |
if (pattern_count > (INT32) 4) { /* is a multiple of 4 also */ |
fill_count = (INT32) (fill_count * (pattern_count/4)); |
pattern_count = (INT32) 4; |
}; |
if ((UDIretval = UDICopy (from, |
to, |
fill_count, |
(UDISizeT) pattern_count, |
(UDICount *) &count_done, |
direction)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
}; |
/* return if no more to copy */ |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
|
static UDIError |
FillString(from, pattern, pattern_count, fill_count) |
UDIResource from; |
UDIHostMemPtr pattern; |
UDISizeT pattern_count; |
UDICount fill_count; |
{ |
UDICount count_done; |
UDIBool host_endian, direction; |
UDIError UDIretval; |
UDIResource to; |
|
host_endian = FALSE; |
|
if ((UDIretval = UDIWrite((UDIHostMemPtr) pattern, |
from, |
(UDICount) pattern_count, |
(UDISizeT) 1, |
(UDICount *) &count_done, |
host_endian)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { /* do copy */ |
fill_count = fill_count - 1; /* one less */ |
if (fill_count > (INT32) 0) { /* do copy */ |
to.Offset = from.Offset + pattern_count; |
to.Space = from.Space; |
direction = TRUE; /* front to back */ |
if ((UDIretval = UDICopy (from, |
to, |
(UDICount) (fill_count*pattern_count), |
(UDISizeT) 1, |
(UDICount *) &count_done, |
direction)) <= TIPFAILURE) { |
PrintErrorMessage (UDIretval); |
return (FAILURE); |
} else if (UDIretval == SUCCESS) { |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
} |
}; |
/* return if no more to copy */ |
return(SUCCESS); |
} else { |
udi_warning(UDIretval); |
return(FAILURE); |
}; |
} |
/asm.c
0,0 → 1,1769
static char _[] = " @(#)asm.c 5.23 93/10/26 10:17:03, Srini, AMD"; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
* This module supports the assemble command to assemble 29K instructions |
* in memory. |
***************************************************************************** |
*/ |
|
|
#include <stdio.h> |
#include "opcodes.h" |
#include "memspcs.h" |
#include "main.h" |
#include "monitor.h" |
#include "macros.h" |
#include "miniint.h" |
#include "error.h" |
|
#ifdef MSDOS |
#include <string.h> |
#define strcasecmp stricmp |
#else |
#include <string.h> |
#endif |
|
|
/* |
** There are approximately 23 different instruction formats for the |
** Am29000. Instructions are assembled using one of these formats. |
** |
** Note: Opcodes in the "switch" statement are sorted in numerical |
** order. |
** |
*/ |
|
|
int get_addr_29k_m PARAMS((char *, struct addr_29k_t *, INT32)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
void convert32 PARAMS((BYTE *)); |
int set_data PARAMS((BYTE *, BYTE *, int)); |
|
int asm_instr PARAMS((struct instr_t *, char **, int)); |
|
int asm_arith_logic PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_load_store PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_vector PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_no_parms PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_one_parms PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_float PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_call_jmp PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_calli_jmpi PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_class PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_clz PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_const PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_consth PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_convert PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_div0 PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_exhws PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_jmp PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_jmpi PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_mfsr PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_mtsr PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_mtsrim PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_mftlb PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_mttlb PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_sqrt PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
int asm_emulate PARAMS((struct instr_t *, struct addr_29k_t *, int)); |
|
extern void Mini_poll_kbd PARAMS((char *cmd_buffer, int size, int mode)); |
extern int Mini_cmdfile_input PARAMS((char *cmd_buffer, int size)); |
extern int tokenize_cmd PARAMS((char *, char **)); |
extern void lcase_tokens PARAMS((char **, int)); |
extern INT32 do_assemble PARAMS(( struct addr_29k_t addr_29k, |
char *token[], |
int token_count)); |
#ifndef XRAY |
|
extern char cmd_buffer[]; |
|
#define MAX_ASM_TOKENS 15 |
static char *asm_token[MAX_ASM_TOKENS]; |
static int asm_token_count; |
|
/* |
** This function is used to assemble an instruction. The command |
** takes as parameters an array of strings (*token[]) and a |
** count (token_count) which gives the number of tokens in the |
** array. These tokens should have the following values: |
** |
** token[0] - 'a' (the assemble command) |
** token[1] - <address> (the address to assemble instruction at) |
** token[2] - <opcode> (the 29K opcode nmemonic) |
** token[3] to token[n] - parameters to the assembly instruction. |
** |
*/ |
|
INT32 |
asm_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
INT32 result; |
struct addr_29k_t addr_29k; |
int asm_done; |
|
/* |
** Parse parameters |
*/ |
|
if ((token_count < 2) || (token_count > 9)) { |
return (EMSYNTAX); |
} else if (token_count == 2) { |
/* Get address of assembly */ |
result = get_addr_29k_m(token[1], &addr_29k, I_MEM); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k); |
if (result != 0) |
return (result); |
asm_done = 0; |
fprintf(stderr, "0x%08lx:\t", addr_29k.address); |
do { |
if (io_config.cmd_file_io == TRUE) { |
if (Mini_cmdfile_input(cmd_buffer, BUFFER_SIZE) == SUCCESS) { |
fprintf(stderr, "%s", cmd_buffer); |
} else { |
Mini_poll_kbd(cmd_buffer, BUFFER_SIZE, BLOCK); /* block */ |
} |
} else { |
Mini_poll_kbd(cmd_buffer, BUFFER_SIZE, BLOCK); /* block */ |
} |
if (io_config.log_file) /* make a log file */ |
#ifdef MSDOS |
fprintf(io_config.log_file, "%s\n", cmd_buffer); |
#else |
fprintf(io_config.log_file, "%s", cmd_buffer); |
#endif |
if (io_config.echo_mode == (INT32) TRUE) |
#ifdef MSDOS |
fprintf(io_config.echo_file, "%s\n", cmd_buffer); |
#else |
fprintf(io_config.echo_file, "%s", cmd_buffer); |
#endif |
asm_token_count = tokenize_cmd(cmd_buffer, asm_token); |
lcase_tokens(asm_token, asm_token_count); |
if (strcmp(token[0], ".") == 0) |
asm_done = 1; |
else { |
result= do_assemble(addr_29k, &asm_token[0], asm_token_count); |
if (result != SUCCESS) |
warning (result); |
else |
addr_29k.address = addr_29k.address + 4; |
fprintf(stderr, "0x%08lx:\t", addr_29k.address); |
} |
} while (asm_done != 1); |
} else { |
/* Get address of assembly */ |
result = get_addr_29k_m(token[1], &addr_29k, I_MEM); |
if (result != 0) |
return (result); |
result = addr_29k_ok(&addr_29k); |
if (result != 0) |
return (result); |
return (do_assemble(addr_29k, &token[2], (token_count-2))); |
} |
return (SUCCESS); |
} |
|
|
INT32 |
do_assemble(addr_29k, token, token_count) |
struct addr_29k_t addr_29k; |
char *token[]; |
int token_count; |
{ |
INT32 result; |
struct instr_t instr; |
|
INT32 retval; |
BYTE *write_data; |
INT32 bytes_ret; |
INT32 hostendian; /* for UDI conformant */ |
|
/* Initialize instr */ |
instr.op = 0; |
instr.c = 0; |
instr.a = 0; |
instr.b = 0; |
|
/* Assemble instruction */ |
result = asm_instr(&instr, &(token[0]), token_count); |
|
if (result != 0) |
return (EMSYNTAX); |
|
/* Will the data overflow the message buffer? done in TIP */ |
write_data = (BYTE *) &instr; |
|
hostendian = FALSE; |
if ((retval = Mini_write_req (addr_29k.memory_space, |
addr_29k.address, |
1, /* count */ |
(INT16) sizeof(INST32), /* size */ |
&bytes_ret, |
write_data, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
}; |
return (SUCCESS); |
} |
#endif |
|
/* |
** This function is used to assemble a single Am29000 instruction. |
** The token[] array contains the lower-case tokens for a single |
** assembler instruction. The token_count contains the number of |
** tokens in the array. This number should be at least 1 (as in the |
** cases of instructions like IRET) and at most 5 (for instructions |
** like LOAD). |
*/ |
|
#ifdef XRAY |
extern struct t_inst_table { |
char *inst_mnem; |
unsigned char oprn_fmt; |
} inst_table[]; |
#endif |
|
int |
asm_instr(instr, token, token_count) |
struct instr_t *instr; |
char *token[]; |
int token_count; |
{ |
int i; |
int result; |
struct addr_29k_t parm[10]; |
char temp_opcode[20]; |
char *temp_ptr; |
int opcode_found; |
static char *str_0x40="0x40"; |
static char *str_gr1="gr1"; |
|
|
/* Is token_count valid, and is the first token a string? */ |
if ((token_count < 1) || |
(token_count > 7) || |
(strcmp(token[0], "") == 0)) |
return (EMSYNTAX); |
|
/* Get opcode */ |
|
/* |
** Note: Since the opcode_name[] string used in the disassembler |
** uses padded strings, we cannot do a strcmp(). We canot do a |
** strncmp() of the length of token[0] either, since "and" will |
** match up (for instance) with "andn". So we copy the string, |
** null terminate at the first pad character (space), and then |
** compare. This is inefficient, but necessary. |
*/ |
|
i=0; |
opcode_found = FALSE; |
while ((i<256) && (opcode_found != TRUE)) { |
#ifdef XRAY |
result = strcasecmp(token[0], inst_table[i].inst_mnem); |
#else |
temp_ptr = strcpy(temp_opcode, opcode_name[i]); |
|
if (strcmp(temp_ptr, "") != 0) |
temp_ptr = strtok(temp_opcode, " "); |
result = strcmp(token[0], temp_ptr); |
#endif |
|
if (result == 0) { |
opcode_found = TRUE; |
instr->op = (BYTE) i; |
} |
i = i + 1; |
} /* end while */ |
|
/* Check for a NOP */ |
if ((opcode_found == FALSE) && |
(strcasecmp(token[0], "nop") == 0)) { |
opcode_found = TRUE; |
instr->op = ASEQ0; |
/* Fake up tokens to give "aseq 0x40,gr1,gr1" */ |
token_count = 4; |
token[1] = str_0x40; |
token[2] = str_gr1; |
token[3] = str_gr1; |
} |
|
if (opcode_found == FALSE) |
return (EMSYNTAX); |
|
if ((strcasecmp(token[0], "iretinv") == 0) || |
(strcasecmp(token[0], "inv") == 0) ) { |
/* iretinv and inv instructions */ |
for (i=1; i<token_count; i=i+1) { |
result = get_addr_29k_m(token[i], &(parm[i-1]), GENERIC_SPACE); |
if (result != 0) |
return (result); |
} |
} else { |
/* Make the other tokens into addr_29k */ |
for (i=1; i<token_count; i=i+1) { |
result = get_addr_29k_m(token[i], &(parm[i-1]), I_MEM); |
if (result != 0) |
return (result); |
/* Check if register values are legal */ |
if (ISREG(parm[i-1].memory_space)) { |
result = addr_29k_ok(&(parm[i-1])); |
if (result != 0) |
return (EMBADREG); |
} |
/* Set bit 7 if a LOCAL_REG */ |
if (parm[i-1].memory_space == LOCAL_REG) |
parm[i-1].address = (parm[i-1].address | 0x80); |
} |
} |
|
|
switch (instr->op) { |
|
/* Opcodes 0x00 to 0x0F */ |
case ILLEGAL_00: result = EMSYNTAX; |
break; |
case CONSTN: result = asm_const(instr, parm, 2); |
break; |
case CONSTH: result = asm_consth(instr, parm, 2); |
break; |
case CONST: result = asm_const(instr, parm, 2); |
break; |
case MTSRIM: result = asm_mtsrim(instr, parm, 2); |
break; |
case CONSTHZ: result = asm_const(instr, parm, 2); |
break; |
case LOADL0: result = asm_load_store(instr, parm, 4); |
break; |
case LOADL1: result = asm_load_store(instr, parm, 4); |
break; |
case CLZ0: result = asm_clz(instr, parm, 2); |
break; |
case CLZ1: result = asm_clz(instr, parm, 2); |
break; |
case EXBYTE0: result = asm_arith_logic(instr, parm, 3); |
break; |
case EXBYTE1: result = asm_arith_logic(instr, parm, 3); |
break; |
case INBYTE0: result = asm_arith_logic(instr, parm, 3); |
break; |
case INBYTE1: result = asm_arith_logic(instr, parm, 3); |
break; |
case STOREL0: result = asm_load_store(instr, parm, 4); |
break; |
case STOREL1: result = asm_load_store(instr, parm, 4); |
break; |
|
/* Opcodes 0x10 to 0x1F */ |
case ADDS0: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDS1: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADD0: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADD1: result = asm_arith_logic(instr, parm, 3); |
break; |
case LOAD0: result = asm_load_store(instr, parm, 4); |
break; |
case LOAD1: result = asm_load_store(instr, parm, 4); |
break; |
case ADDCS0: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDCS1: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDCU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDCU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDC0: result = asm_arith_logic(instr, parm, 3); |
break; |
case ADDC1: result = asm_arith_logic(instr, parm, 3); |
break; |
case STORE0: result = asm_load_store(instr, parm, 4); |
break; |
case STORE1: result = asm_load_store(instr, parm, 4); |
break; |
|
/* Opcodes 0x20 to 0x2F */ |
case SUBS0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBS1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUB0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUB1: result = asm_arith_logic(instr, parm, 3); |
break; |
case LOADSET0: result = asm_load_store(instr, parm, 4); |
break; |
case LOADSET1: result = asm_load_store(instr, parm, 4); |
break; |
case SUBCS0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBCS1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBCU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBCU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBC0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBC1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPBYTE0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPBYTE1: result = asm_arith_logic(instr, parm, 3); |
break; |
|
|
/* Opcodes 0x30 to 0x3F */ |
case SUBRS0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRS1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBR0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBR1: result = asm_arith_logic(instr, parm, 3); |
break; |
case LOADM0: result = asm_load_store(instr, parm, 4); |
break; |
case LOADM1: result = asm_load_store(instr, parm, 4); |
break; |
case SUBRCS0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRCS1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRCU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRCU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRC0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SUBRC1: result = asm_arith_logic(instr, parm, 3); |
break; |
case STOREM0: result = asm_load_store(instr, parm, 4); |
break; |
case STOREM1: result = asm_load_store(instr, parm, 4); |
break; |
|
/* Opcodes 0x40 to 0x4F */ |
case CPLT0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPLT1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPLTU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPLTU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPLE0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPLE1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPLEU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPLEU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGT0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGT1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGTU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGTU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGE0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGE1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGEU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPGEU1: result = asm_arith_logic(instr, parm, 3); |
break; |
|
/* Opcodes 0x50 to 0x5F */ |
case ASLT0: result = asm_vector(instr, parm, 3); |
break; |
case ASLT1: result = asm_vector(instr, parm, 3); |
break; |
case ASLTU0: result = asm_vector(instr, parm, 3); |
break; |
case ASLTU1: result = asm_vector(instr, parm, 3); |
break; |
case ASLE0: result = asm_vector(instr, parm, 3); |
break; |
case ASLE1: result = asm_vector(instr, parm, 3); |
break; |
case ASLEU0: result = asm_vector(instr, parm, 3); |
break; |
case ASLEU1: result = asm_vector(instr, parm, 3); |
break; |
case ASGT0: result = asm_vector(instr, parm, 3); |
break; |
case ASGT1: result = asm_vector(instr, parm, 3); |
break; |
case ASGTU0: result = asm_vector(instr, parm, 3); |
break; |
case ASGTU1: result = asm_vector(instr, parm, 3); |
break; |
case ASGE0: result = asm_vector(instr, parm, 3); |
break; |
case ASGE1: result = asm_vector(instr, parm, 3); |
break; |
case ASGEU0: result = asm_vector(instr, parm, 3); |
break; |
case ASGEU1: result = asm_vector(instr, parm, 3); |
break; |
|
/* Opcodes 0x60 to 0x6F */ |
case CPEQ0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPEQ1: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPNEQ0: result = asm_arith_logic(instr, parm, 3); |
break; |
case CPNEQ1: result = asm_arith_logic(instr, parm, 3); |
break; |
case MUL0: result = asm_arith_logic(instr, parm, 3); |
break; |
case MUL1: result = asm_arith_logic(instr, parm, 3); |
break; |
case MULL0: result = asm_arith_logic(instr, parm, 3); |
break; |
case MULL1: result = asm_arith_logic(instr, parm, 3); |
break; |
case DIV0_OP0: result = asm_div0(instr, parm, 2); |
break; |
case DIV0_OP1: result = asm_div0(instr, parm, 2); |
break; |
case DIV_OP0: result = asm_arith_logic(instr, parm, 3); |
break; |
case DIV_OP1: result = asm_arith_logic(instr, parm, 3); |
break; |
case DIVL0: result = asm_arith_logic(instr, parm, 3); |
break; |
case DIVL1: result = asm_arith_logic(instr, parm, 3); |
break; |
case DIVREM0: result = asm_arith_logic(instr, parm, 3); |
break; |
case DIVREM1: result = asm_arith_logic(instr, parm, 3); |
break; |
|
/* Opcodes 0x70 to 0x7F */ |
case ASEQ0: result = asm_vector(instr, parm, 3); |
break; |
case ASEQ1: result = asm_vector(instr, parm, 3); |
break; |
case ASNEQ0: result = asm_vector(instr, parm, 3); |
break; |
case ASNEQ1: result = asm_vector(instr, parm, 3); |
break; |
case MULU0: result = asm_arith_logic(instr, parm, 3); |
break; |
case MULU1: result = asm_arith_logic(instr, parm, 3); |
break; |
case ILLEGAL_76: result = EMSYNTAX; |
break; |
case ILLEGAL_77: result = EMSYNTAX; |
break; |
case INHW0: result = asm_arith_logic(instr, parm, 3); |
break; |
case INHW1: result = asm_arith_logic(instr, parm, 3); |
break; |
case EXTRACT0: result = asm_arith_logic(instr, parm, 3); |
break; |
case EXTRACT1: result = asm_arith_logic(instr, parm, 3); |
break; |
case EXHW0: result = asm_arith_logic(instr, parm, 3); |
break; |
case EXHW1: result = asm_arith_logic(instr, parm, 3); |
break; |
case EXHWS: result = asm_exhws(instr, parm, 2); |
break; |
case ILLEGAL_7F: result = EMSYNTAX; |
break; |
|
/* Opcodes 0x80 to 0x8F */ |
case SLL0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SLL1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SRL0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SRL1: result = asm_arith_logic(instr, parm, 3); |
break; |
case ILLEGAL_84: result = EMSYNTAX; |
break; |
case ILLEGAL_85: result = EMSYNTAX; |
break; |
case SRA0: result = asm_arith_logic(instr, parm, 3); |
break; |
case SRA1: result = asm_arith_logic(instr, parm, 3); |
break; |
case IRET: |
result = asm_no_parms(instr, parm, 0); |
break; |
case HALT_OP: result = asm_no_parms(instr, parm, 0); |
break; |
case ILLEGAL_8A: result = EMSYNTAX; |
break; |
case ILLEGAL_8B: result = EMSYNTAX; |
break; |
case IRETINV: |
if (token_count > 1) |
result = asm_one_parms(instr, parm, 1); |
else |
result = asm_no_parms(instr, parm, 0); |
break; |
case ILLEGAL_8D: result = EMSYNTAX; |
break; |
case ILLEGAL_8E: result = EMSYNTAX; |
break; |
case ILLEGAL_8F: result = EMSYNTAX; |
break; |
|
/* Opcodes 0x90 to 0x9F */ |
case AND_OP0: result = asm_arith_logic(instr, parm, 3); |
break; |
case AND_OP1: result = asm_arith_logic(instr, parm, 3); |
break; |
case OR_OP0: result = asm_arith_logic(instr, parm, 3); |
break; |
case OR_OP1: result = asm_arith_logic(instr, parm, 3); |
break; |
case XOR_OP0: result = asm_arith_logic(instr, parm, 3); |
break; |
case XOR_OP1: result = asm_arith_logic(instr, parm, 3); |
break; |
case XNOR0: result = asm_arith_logic(instr, parm, 3); |
break; |
case XNOR1: result = asm_arith_logic(instr, parm, 3); |
break; |
case NOR0: result = asm_arith_logic(instr, parm, 3); |
break; |
case NOR1: result = asm_arith_logic(instr, parm, 3); |
break; |
case NAND0: result = asm_arith_logic(instr, parm, 3); |
break; |
case NAND1: result = asm_arith_logic(instr, parm, 3); |
break; |
case ANDN0: result = asm_arith_logic(instr, parm, 3); |
break; |
case ANDN1: result = asm_arith_logic(instr, parm, 3); |
break; |
case SETIP: result = asm_float(instr, parm, 3); |
break; |
case INV: |
if (token_count > 1) |
result = asm_one_parms(instr, parm, 1); |
else |
result = asm_no_parms(instr, parm, 0); |
break; |
|
/* Opcodes 0xA0 to 0xAF */ |
case JMP0: result = asm_jmp(instr, parm, 1); |
break; |
case JMP1: result = asm_jmp(instr, parm, 1); |
break; |
case ILLEGAL_A2: result = EMSYNTAX; |
break; |
case ILLEGAL_A3: result = EMSYNTAX; |
break; |
case JMPF0: result = asm_call_jmp(instr, parm, 2); |
break; |
case JMPF1: result = asm_call_jmp(instr, parm, 2); |
break; |
case ILLEGAL_A6: result = EMSYNTAX; |
break; |
case ILLEGAL_A7: result = EMSYNTAX; |
break; |
case CALL0: result = asm_call_jmp(instr, parm, 2); |
break; |
case CALL1: result = asm_call_jmp(instr, parm, 2); |
break; |
case ORN_OP0: result = EMSYNTAX; |
break; |
case ORN_OP1: result = EMSYNTAX; |
break; |
case JMPT0: result = asm_call_jmp(instr, parm, 2); |
break; |
case JMPT1: result = asm_call_jmp(instr, parm, 2); |
break; |
case ILLEGAL_AE: result = EMSYNTAX; |
break; |
case ILLEGAL_AF: result = EMSYNTAX; |
break; |
|
/* Opcodes 0xB0 to 0xBF */ |
case ILLEGAL_B0: result = EMSYNTAX; |
break; |
case ILLEGAL_B1: result = EMSYNTAX; |
break; |
case ILLEGAL_B2: result = EMSYNTAX; |
break; |
case ILLEGAL_B3: result = EMSYNTAX; |
break; |
case JMPFDEC0: result = asm_call_jmp(instr, parm, 2); |
break; |
case JMPFDEC1: result = asm_call_jmp(instr, parm, 2); |
break; |
case MFTLB: result = asm_mftlb(instr, parm, 2); |
break; |
case ILLEGAL_B7: result = EMSYNTAX; |
break; |
case ILLEGAL_B8: result = EMSYNTAX; |
break; |
case ILLEGAL_B9: result = EMSYNTAX; |
break; |
case ILLEGAL_BA: result = EMSYNTAX; |
break; |
case ILLEGAL_BB: result = EMSYNTAX; |
break; |
case ILLEGAL_BC: result = EMSYNTAX; |
break; |
case ILLEGAL_BD: result = EMSYNTAX; |
break; |
case MTTLB: result = asm_mttlb(instr, parm, 2); |
break; |
case ILLEGAL_BF: result = EMSYNTAX; |
break; |
|
/* Opcodes 0xC0 to 0xCF */ |
case JMPI: result = asm_jmpi(instr, parm, 1); |
break; |
case ILLEGAL_C1: result = EMSYNTAX; |
break; |
case ILLEGAL_C2: result = EMSYNTAX; |
break; |
case ILLEGAL_C3: result = EMSYNTAX; |
break; |
case JMPFI: result = asm_calli_jmpi(instr, parm, 2); |
break; |
case ILLEGAL_C5: result = EMSYNTAX; |
break; |
case MFSR: result = asm_mfsr(instr, parm, 2); |
break; |
case ILLEGAL_C7: result = EMSYNTAX; |
break; |
case CALLI: result = asm_calli_jmpi(instr, parm, 2); |
break; |
case ILLEGAL_C9: result = EMSYNTAX; |
break; |
case ILLEGAL_CA: result = EMSYNTAX; |
break; |
case ILLEGAL_CB: result = EMSYNTAX; |
break; |
case JMPTI: result = asm_calli_jmpi(instr, parm, 2); |
break; |
case ILLEGAL_CD: result = EMSYNTAX; |
break; |
case MTSR: result = asm_mtsr(instr, parm, 2); |
break; |
case ILLEGAL_CF: result = EMSYNTAX; |
break; |
|
/* Opcodes 0xD0 to 0xDF */ |
case ILLEGAL_D0: result = EMSYNTAX; |
break; |
case ILLEGAL_D1: result = EMSYNTAX; |
break; |
case ILLEGAL_D2: result = EMSYNTAX; |
break; |
case ILLEGAL_D3: result = EMSYNTAX; |
break; |
case ILLEGAL_D4: result = EMSYNTAX; |
break; |
case ILLEGAL_D5: result = EMSYNTAX; |
break; |
case ILLEGAL_D6: result = EMSYNTAX; |
break; |
case EMULATE: result = asm_emulate(instr, parm, 3); |
break; |
case ILLEGAL_D8: result = EMSYNTAX; |
break; |
case ILLEGAL_D9: result = EMSYNTAX; |
break; |
case ILLEGAL_DA: result = EMSYNTAX; |
break; |
case ILLEGAL_DB: result = EMSYNTAX; |
break; |
case ILLEGAL_DC: result = EMSYNTAX; |
break; |
case ILLEGAL_DD: result = EMSYNTAX; |
break; |
case MULTM: result = asm_float(instr, parm, 3); |
break; |
case MULTMU: result = asm_float(instr, parm, 3); |
break; |
|
/* Opcodes 0xE0 to 0xEF */ |
case MULTIPLY: result = asm_float(instr, parm, 3); |
break; |
case DIVIDE: result = asm_float(instr, parm, 3); |
break; |
case MULTIPLU: result = asm_float(instr, parm, 3); |
break; |
case DIVIDU: result = asm_float(instr, parm, 3); |
break; |
case CONVERT: result = asm_convert(instr, parm, 6); |
break; |
case SQRT: result = asm_sqrt(instr, parm, 3); |
break; |
case CLASS: result = asm_class(instr, parm, 3); |
break; |
case ILLEGAL_E7: result = EMSYNTAX; |
break; |
case ILLEGAL_E8: result = EMSYNTAX; |
break; |
case ILLEGAL_E9: result = EMSYNTAX; |
break; |
case FEQ: result = asm_float(instr, parm, 3); |
break; |
case DEQ: result = asm_float(instr, parm, 3); |
break; |
case FGT: result = asm_float(instr, parm, 3); |
break; |
case DGT: result = asm_float(instr, parm, 3); |
break; |
case FGE: result = asm_float(instr, parm, 3); |
break; |
case DGE: result = asm_float(instr, parm, 3); |
break; |
|
/* Opcodes 0xF0 to 0xFF */ |
case FADD: result = asm_float(instr, parm, 3); |
break; |
case DADD: result = asm_float(instr, parm, 3); |
break; |
case FSUB: result = asm_float(instr, parm, 3); |
break; |
case DSUB: result = asm_float(instr, parm, 3); |
break; |
case FMUL: result = asm_float(instr, parm, 3); |
break; |
case DMUL: result = asm_float(instr, parm, 3); |
break; |
case FDIV: result = asm_float(instr, parm, 3); |
break; |
case DDIV: result = asm_float(instr, parm, 3); |
break; |
case ILLEGAL_F8: result = EMSYNTAX; |
break; |
case FDMUL: result = asm_float(instr, parm, 3); |
break; |
case ILLEGAL_FA: result = EMSYNTAX; |
break; |
case ILLEGAL_FB: result = EMSYNTAX; |
break; |
case ILLEGAL_FC: result = EMSYNTAX; |
break; |
case ILLEGAL_FD: result = EMSYNTAX; |
break; |
case ILLEGAL_FE: result = EMSYNTAX; |
break; |
case ILLEGAL_FF: result = EMSYNTAX; |
break; |
} /* end switch */ |
|
return (result); |
|
} /* End asm_instr() */ |
|
|
|
|
/* |
** The following functions are used to convert instruction |
** parameters as an arrays of addr_29k_t memory space / address |
** pairs into a 32 bit Am29000 binary instruction. |
** All of the Am29000 instruction formats are supported below. |
*/ |
|
|
/* |
** Formats: <nmemonic>, RC, RA, (RB or I) |
** Examples: ADD, OR, SLL, all arithmetic and |
** logic instructions |
** |
*/ |
|
int |
asm_arith_logic(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 3) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISGENERAL(parm[2].memory_space)) { |
/* Make sure M flag is cleared */ |
instr->op = (BYTE) (instr->op & 0xfe); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0xff); |
} |
else |
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISMEM(parm[2].memory_space)) { |
/* Make sure M flag is set */ |
instr->op = (BYTE) (instr->op | 0x01); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_arith_logic() */ |
|
|
|
/* |
** Formats: <nmemonic>, VN, RA, (RB or I) |
** Examples: ASSEQ, ASLE, ASLT, all trap assertion |
** instructions |
** |
*/ |
|
int |
asm_vector(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 3) |
return (EMSYNTAX); |
|
if (ISMEM(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISGENERAL(parm[2].memory_space)) { |
/* Make sure M flag is cleared */ |
instr->op = (BYTE) (instr->op & 0xfe); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0xff); |
} |
else |
if (ISMEM(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISMEM(parm[2].memory_space)) { |
/* Make sure M flag is set */ |
instr->op = (BYTE) (instr->op | 0x01); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_vector() */ |
|
|
|
/* |
** Formats: <nmemonic>, CE, CNTL, RA, (RB or I) |
** Examples: LOAD, LOADM, STORE, all load and store |
** instructions |
** |
*/ |
|
int |
asm_load_store(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
int ce; |
int cntl; |
|
if (parm_count != 4) |
return (EMSYNTAX); |
|
if (ISMEM(parm[0].memory_space) && |
ISMEM(parm[1].memory_space) && |
ISGENERAL(parm[2].memory_space) && |
ISGENERAL(parm[3].memory_space)) { |
/* Make sure M flag is cleared */ |
instr->op = (BYTE) (instr->op & 0xfe); |
if (parm[0].address > 1) |
return (EMSYNTAX); |
if (parm[1].address > 0x7f) |
return (EMSYNTAX); |
ce = (int) ((parm[0].address << 7) & 0x80); |
cntl = (int) (parm[1].address & 0x7f); |
instr->c = (BYTE) (ce | cntl); |
instr->a = (BYTE) (parm[2].address & 0xff); |
instr->b = (BYTE) (parm[3].address & 0xff); |
} |
else |
if (ISMEM(parm[0].memory_space) && |
ISMEM(parm[1].memory_space) && |
ISGENERAL(parm[2].memory_space) && |
ISMEM(parm[3].memory_space)) { |
/* Make sure M flag is set */ |
instr->op = (BYTE) (instr->op | 0x01); |
if (parm[0].address > 1) |
return (EMSYNTAX); |
if (parm[1].address > 0x7f) |
return (EMSYNTAX); |
if (parm[3].address > 0xff) |
return (EMSYNTAX); |
ce = (int) ((parm[0].address << 7) & 0x80); |
cntl = (int) (parm[1].address & 0x7f); |
instr->c = (BYTE) (ce | cntl); |
instr->a = (BYTE) (parm[2].address & 0xff); |
instr->b = (BYTE) (parm[3].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_load_store() */ |
|
|
|
/* |
** Formats: <nmemonic> |
** Examples: HALT, INV, IRET |
*/ |
/*ARGSUSED*/ |
|
int |
asm_no_parms(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 0) |
return (EMSYNTAX); |
|
/* Put zeros in the "reserved" fields */ |
instr->c = 0; |
instr->a = 0; |
instr->b = 0; |
|
return (0); |
} /* end asm_no_parms() */ |
|
|
int |
asm_one_parms(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 1) |
return (EMSYNTAX); |
|
instr->c = (BYTE) (parm[0].address & 0x3); |
|
/* Put zeros in the "reserved" fields */ |
instr->a = 0; |
instr->b = 0; |
|
return (0); |
} /* end asm_one_parms */ |
|
|
/* |
** Formats: <nmemonic>, RC, RA, RB |
** Examples: DADD, FADD, all floating point |
** instructions |
** |
*/ |
|
int |
asm_float(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 3) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISGENERAL(parm[2].memory_space)) { |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_float() */ |
|
|
|
/* |
** Formats: <nmemonic> RA, <target> |
** Examples: CALL, JMPF, JMPFDEC, JMPT |
** |
** Note: This function is used only with the CALL, |
** JMPF, JMPFDEC and JMPT operations. |
*/ |
|
int |
asm_call_jmp(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISMEM(parm[1].memory_space)) { |
/* Make sure M flag is set */ |
if (parm[1].memory_space != PC_RELATIVE) |
instr->op = (BYTE) (instr->op | 0x01); |
else |
instr->op = (BYTE) instr->op ; |
instr->c = (BYTE) ((parm[1].address >> 10) & 0xff); |
instr->a = (BYTE) (parm[0].address & 0xff); |
instr->b = (BYTE) ((parm[1].address >> 2) & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_call_jmp() */ |
|
|
|
|
/* |
** Formats: <nmemonic> RA, RB |
** Examples: CALLI, JMPFI, JMPTI |
** |
** Note: This function is used only with the CALLI, |
** JMPFI and JMPTI (but not JMPI) operations. |
*/ |
|
int |
asm_calli_jmpi(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISREG(parm[1].memory_space)) { |
instr->c = 0; |
instr->a = (BYTE) (parm[0].address & 0xff); |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_calli_jmpi() */ |
|
|
|
/* |
** Formats: <nmemonic> RC, RB, FS |
** Examples: CLASS |
** |
** Note: This function is used only with the CLASS |
** operation. |
*/ |
|
int |
asm_class(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 3) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISMEM(parm[2].memory_space)) { |
if (parm[2].address > 0x03) |
return (EMSYNTAX); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0x03); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_class() */ |
|
|
/* |
** Formats: <nmemonic> RC, (RB or I) |
** Examples: CLZ |
** |
** Note: This function is used only with the CLZ |
** operation. |
*/ |
|
int |
asm_clz(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space)) { |
/* Make sure M flag is cleared */ |
instr->op = (BYTE) (instr->op & 0xfe); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = 0; |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
if (ISGENERAL(parm[0].memory_space) && |
ISMEM(parm[1].memory_space)) { |
/* Check param1 */ |
if ((parm[1].address) > 0xff) |
return(EMSYNTAX); |
/* Make sure M flag is set */ |
instr->op = (BYTE) (instr->op | 0x01); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = 0; |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_clz() */ |
|
|
|
/* |
** Formats: <nmemonic> RA, <const16> |
** Examples: CONST, CONSTN |
** |
*/ |
|
int |
asm_const(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISMEM(parm[1].memory_space)) { |
instr->c = (BYTE) ((parm[1].address >> 8) & 0xff); |
instr->a = (BYTE) (parm[0].address & 0xff); |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_const() */ |
|
|
|
/* |
** Formats: <nmemonic> RA, <const16> |
** Examples: CONSTH |
** |
*/ |
|
int |
asm_consth(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISMEM(parm[1].memory_space)) { |
instr->c = (BYTE) ((parm[1].address >> 24) & 0xff); |
instr->a = (BYTE) (parm[0].address & 0xff); |
instr->b = (BYTE) ((parm[1].address >> 16) & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_consth() */ |
|
|
|
/* |
** Formats: <nmemonic> RC, RA, UI, RND, FD, FS |
** Examples: CONVERT |
** |
** Note: This function is used only with the CONVERT |
** operation. |
** |
** Note: Some assembler examples show this operation with |
** only five parameters. It should have six. |
*/ |
|
int |
asm_convert(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
BYTE ui; |
BYTE rnd; |
BYTE fd; |
BYTE fs; |
|
if (parm_count != 6) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISMEM(parm[2].memory_space) && |
ISMEM(parm[3].memory_space) && |
ISMEM(parm[4].memory_space) && |
ISMEM(parm[5].memory_space)) { |
if (parm[2].address > 1) |
return (EMSYNTAX); |
if (parm[3].address > 0x07) |
return (EMSYNTAX); |
if (parm[4].address > 0x03) |
return (EMSYNTAX); |
if (parm[5].address > 0x03) |
return (EMSYNTAX); |
ui = (BYTE) ((parm[2].address << 7) & 0x80); |
rnd = (BYTE) ((parm[3].address << 4) & 0x70); |
fd = (BYTE) ((parm[4].address << 2) & 0x0c); |
fs = (BYTE) (parm[5].address & 0x03); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (ui | rnd | fd | fs); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_convert() */ |
|
|
|
/* |
** Formats: <nmemonic> RC, RA |
** Examples: DIV0 |
** |
** Note: This function is used only with the DIV0 |
** operation. |
*/ |
|
int |
asm_div0(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space)) { |
/* Make sure M flag is cleared */ |
instr->op = (BYTE) (instr->op & 0xfe); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = 0; |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
if (ISGENERAL(parm[0].memory_space) && |
ISMEM(parm[1].memory_space)) { |
/* Check immediate value */ |
if (parm[1].address > 0xff) |
return (EMSYNTAX); |
/* Make sure M flag is set */ |
instr->op = (BYTE) (instr->op | 0x01); |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = 0; |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_div0() */ |
|
|
/* |
** Formats: <nmemonic> RC, RA |
** Examples: EXHWS |
** |
** Note: This function is used only with the EXHWS |
** operation. |
*/ |
|
int |
asm_exhws(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space)){ |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = 0; |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_exhws() */ |
|
|
|
|
/* |
** Formats: <nmemonic> <target> |
** Examples: JMP |
** |
** Note: This function is used only with the JMP |
** operation. |
** |
** Note: This function will only do absolute jumps. |
*/ |
|
int |
asm_jmp(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 1) |
return (EMSYNTAX); |
|
if (ISMEM(parm[0].memory_space)) { |
/* Make sure M flag is set */ |
if (parm[0].memory_space != PC_RELATIVE) |
instr->op = (BYTE) (instr->op | 0x01); |
else |
instr->op = (BYTE) instr->op ; |
instr->c = (BYTE) ((parm[0].address >> 10) & 0xff); |
instr->a = 0; |
instr->b = (BYTE) ((parm[0].address >> 2) & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_jmp() */ |
|
|
|
/* |
** Formats: <nmemonic> RB |
** Examples: JMPI |
** |
** Note: This function is used only with the JMPI |
** operation. |
*/ |
|
int |
asm_jmpi(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 1) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space)) { |
instr->c = 0; |
instr->a = 0; |
instr->b = (BYTE) (parm[0].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_jmpi() */ |
|
|
|
/* |
** Formats: <nmemonic> RC, SA |
** Examples: MFSR |
** |
** Note: This function is used only with the MFSR |
** operation. |
*/ |
|
int |
asm_mfsr(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISSPECIAL(parm[1].memory_space)) { |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = 0; |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_mfsr() */ |
|
|
|
/* |
** Formats: <nmemonic> SA, RB |
** Examples: MTSR |
** |
** Note: This function is used only with the MTSR |
** operation. |
*/ |
|
int |
asm_mtsr(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISSPECIAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space)) { |
instr->c = 0; |
instr->a = (BYTE) (parm[0].address & 0xff); |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_mtsr() */ |
|
|
|
|
/* |
** Formats: <nmemonic> SA, <const16> |
** Examples: MTSRIM |
** |
** Note: This function is used only with the MTSRIM |
** operation. |
*/ |
|
int |
asm_mtsrim(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISSPECIAL(parm[0].memory_space) && |
ISMEM(parm[1].memory_space)) { |
instr->c = (BYTE) ((parm[1].address >> 8) & 0xff); |
instr->a = (BYTE) (parm[0].address & 0xff); |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_mtsrim() */ |
|
|
|
|
/* |
** Formats: <nmemonic> RC, RA |
** Examples: MFTLB |
** |
** Note: This function is used only with the MFTLB |
** operation. |
*/ |
|
int |
asm_mftlb(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space)) { |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = 0; |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_mftlb() */ |
|
|
/* |
** Formats: <nmemonic> RA, RB |
** Examples: MTTLB |
** |
** Note: This function is used only with the MTTLB |
** operation. |
*/ |
|
int |
asm_mttlb(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 2) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space)) { |
instr->c = 0; |
instr->a = (BYTE) (parm[0].address & 0xff); |
instr->b = (BYTE) (parm[1].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_mttlb() */ |
|
|
|
|
/* |
** Formats: <nmemonic> RC, RA, FS |
** Examples: SQRT |
** |
** Note: This function is used only with the SQRT |
** operation. |
*/ |
|
int |
asm_sqrt(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 3) |
return (EMSYNTAX); |
|
if (ISGENERAL(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISMEM(parm[2].memory_space)) { |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0x03); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_sqrt() */ |
|
|
|
/* |
** Formats: <nmemonic>, VN, RA, RB |
** Examples: EMULATE |
** |
** Note: This function is used only with the EMULATE |
** operation. |
** |
*/ |
|
int |
asm_emulate(instr, parm, parm_count) |
struct instr_t *instr; |
struct addr_29k_t *parm; |
int parm_count; |
{ |
if (parm_count != 3) |
return (EMSYNTAX); |
|
if (ISMEM(parm[0].memory_space) && |
ISGENERAL(parm[1].memory_space) && |
ISGENERAL(parm[2].memory_space)) { |
instr->c = (BYTE) (parm[0].address & 0xff); |
instr->a = (BYTE) (parm[1].address & 0xff); |
instr->b = (BYTE) (parm[2].address & 0xff); |
} |
else |
return(EMSYNTAX); |
|
return (0); |
} /* end asm_emulate() */ |
|
|
|
|
|
/main.c
0,0 → 1,481
static char _[] = "@(#)main.c 5.27 93/10/27 15:11:04, Srini, AMD"; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
* This is the main module of MONDFE. |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <signal.h> |
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
#else |
#include <strings.h> |
#endif |
#include "coff.h" |
#include "main.h" |
#include "monitor.h" |
#include "memspcs.h" |
#include "miniint.h" |
#include "error.h" |
#include "versions.h" |
|
#ifdef MSDOS |
#define strcasecmp stricmp |
#endif |
|
/* Externals */ |
extern void Def_CtrlC_Hdlr PARAMS((int)); |
extern void Mini_parse_args PARAMS((int argc, char **argv)); |
extern INT32 Mini_initialize PARAMS((HOST_CONFIG *host, IO_CONFIG *io, |
INIT_INFO *init)); |
extern INT32 Mini_io_setup PARAMS((void)); |
extern INT32 Mini_io_reset PARAMS((void)); |
extern INT32 Mini_load_file PARAMS((char *fname, INT32 mspace, |
int argc, char *args, |
INT32 symbols, INT32 sections, int msg)); |
extern void Mini_monitor PARAMS((void)); |
extern INT32 Mini_go_forever PARAMS((void)); |
|
/* Globals */ |
|
GLOBAL char *host_version = HOST_VERSION; |
GLOBAL char *host_date = HOST_DATE; |
|
GLOBAL TARGET_CONFIG target_config; |
GLOBAL VERSIONS_ETC versions_etc; |
GLOBAL TARGET_STATUS target_status; |
GLOBAL HOST_CONFIG host_config; |
GLOBAL IO_CONFIG io_config; |
|
/* The filenos of the monitor's stdin, stdout, adn stderr */ |
int MON_STDIN; |
int MON_STDOUT; |
int MON_STDERR; |
|
int Session_ids[MAX_SESSIONS]; |
int NumberOfConnections=0; |
/* The following variables are to be set/initialized in Mini_parse_args() |
*/ |
GLOBAL BOOLEAN monitor_enable = FALSE; |
GLOBAL int QuietMode = 0; |
GLOBAL BOOLEAN ROM_flag = FALSE; |
|
GLOBAL char *ROM_file = NULL; |
GLOBAL char **ROM_argv; |
GLOBAL int ROM_sym, ROM_sects; |
GLOBAL int ROM_argc; |
|
GLOBAL char CoffFileName[1024]; |
static char Ex_argstring[1024]; |
GLOBAL int Ex_sym, Ex_sects, Ex_space; |
GLOBAL int Ex_argc; |
static int Ex_loaded=0; |
|
GLOBAL char *ProgramName=NULL; |
|
GLOBAL char *connect_string; |
|
GLOBAL INT32 udi_waittime; |
|
/* Main routine */ |
|
main(argc, argv) |
int argc; |
char *argv[]; |
{ |
|
char *temp; |
int i; |
UINT32 ProcessorState; |
int GrossState; |
INT32 retval; |
|
ProgramName=argv[0]; |
if (strpbrk( ProgramName, "/\\" )) |
{ |
temp = ProgramName + strlen( ProgramName ); |
while (!strchr( "/\\", *--temp )) |
; |
ProgramName = temp+1; |
} |
|
if (argc < 2 ) { |
fprintf(stderr, "MiniMON29K Release 3.0\n"); |
fprintf(stderr, "MONDFE Debugger Front End (UDI 1.2) Version %s Date %s\n", HOST_VERSION, HOST_DATE); |
fatal_error(EMUSAGE); |
} |
|
/* Initialize stdin, stdout, sdterr to defaults */ |
MON_STDIN = fileno(stdin); |
MON_STDOUT = fileno(stdout); |
MON_STDERR = fileno(stderr); |
NumberOfConnections = 0; |
(void) strcpy (CoffFileName,""); |
|
udi_waittime = (INT32) 10; /* default poll every ? secs */ |
/* |
** Initialize host configuration structure (global), set defaults |
*/ |
if (Mini_initialize (&host_config, &io_config, &init_info) != SUCCESS) |
fatal_error(EMHINIT); |
|
/* Parse args */ |
(void) Mini_parse_args(argc, argv); |
|
if (io_config.echo_mode == (INT32) TRUE) { |
for (i=0; i < argc; i++) |
fprintf(io_config.echo_file, "%s ", argv[i]); |
fprintf(io_config.echo_file, "\n"); |
fflush (io_config.echo_file); |
}; |
|
if ((monitor_enable == FALSE) & !Ex_loaded) |
fatal_error (EMNOFILE); |
|
/* |
** Initialize host I/O. |
*/ |
|
if (Mini_io_setup() != SUCCESS) |
fatal_error(EMIOSETF); |
|
/* |
* Initialize TIP. Load ROM file, if necessary. |
** Open communication channel |
*/ |
if (signal (SIGINT, Def_CtrlC_Hdlr) == SIG_ERR) { |
fprintf(stderr, "Couldn't install default Ctrl-C handler.\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Couldn't install default Ctrl-C handler.\n"); |
} |
/* connect_string is made by the Mini_parse_args routine */ |
retval = Mini_TIP_init(connect_string, &Session_ids[NumberOfConnections]); |
if (retval > (INT32) 0) { |
fatal_error(EMTIPINIT); |
} else if (retval == (INT32) SUCCESS) { |
NumberOfConnections=NumberOfConnections+1; |
} else { |
Mini_TIP_exit(); |
fatal_error(EMTIPINIT); |
} |
if (Mini_get_target_stats((INT32) -1, &ProcessorState) != SUCCESS) {/* reconnect?*/ |
Mini_TIP_exit(); |
fatal_error(EMFATAL); |
}; |
GrossState = (int) (ProcessorState & 0xFF); |
if (GrossState == NOTEXECUTING) |
if (Mini_TIP_CreateProc() != SUCCESS) { |
Mini_TIP_exit(); |
fatal_error(EMNOPROCESS); |
} |
|
/* Get capabilities */ |
if (Mini_TIP_Capabilities() != SUCCESS) { |
Mini_TIP_DestroyProc(); |
Mini_TIP_exit(); |
fatal_error(EMNOTCOMP); |
} |
|
/* Get the target memory configuration, and processor type */ |
versions_etc.version = 0; /* initialize in case not returned */ |
if (Mini_config_req(&target_config, &versions_etc) != SUCCESS) { |
warning(EMCONFIG); |
} |
|
if (strcmp(CoffFileName,"") != 0) { |
if (Mini_load_file(&CoffFileName[0], |
Ex_space, |
Ex_argc, |
Ex_argstring, |
Ex_sym, |
Ex_sects, |
QuietMode) != SUCCESS) { |
Ex_loaded = 0; |
warning(EMLOADF); |
} else { |
Ex_loaded = 1; |
}; |
} |
|
if (monitor_enable == FALSE) { |
if (Ex_loaded) |
Mini_go_forever(); |
else { /* nothing to do, so quit */ |
Mini_TIP_DestroyProc(); |
Mini_TIP_exit(); |
warning (EMNOFILE); |
} |
} else { |
Mini_monitor(); |
}; |
|
fflush(stderr); |
fflush(stdout); |
|
/* Perform host-specific clean-up */ |
if (Mini_io_reset() != SUCCESS) |
warning(EMIORESETF); |
|
if (!QuietMode) { |
fprintf(stderr, "\nGoodbye.\n"); |
if (io_config.echo_mode == (INT32) TRUE) { |
fprintf(io_config.echo_file, "\nGoodbye.\n"); |
(void) fclose (io_config.echo_file); |
} |
} |
return(0); |
|
} /* end Main */ |
|
|
|
/* |
** Functions |
*/ |
|
/* |
** This function prints out a fatal error message |
** from error_msg[]. |
** Finally, the program exits with error_number. |
*/ |
#ifndef MINIMON |
extern UINT32 UDIGetDFEIPCId PARAMS((void)); |
#endif |
|
void |
fatal_error(error_number) |
INT32 error_number; |
{ |
UINT32 IPCId; |
|
if (error_number == (INT32) EMUSAGE) { |
#ifndef MINIMON |
IPCId = (UINT32) UDIGetDFEIPCId(); |
fprintf(stderr, "MONDFE UDI IPC Implementation Id %d.%d.%d\n", |
(int) ((IPCId & 0xf00) >> 8), |
(int) ((IPCId & 0xf0) >> 4), |
(int) (IPCId & 0xf)); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "MONDFE UDI IPC Implementation Id %d.%d.%d\n", |
(int) ((IPCId & 0xf00) >> 8), |
(int) ((IPCId & 0xf0) >> 4), |
(int) (IPCId & 0xf)); |
#else |
fprintf(stderr, "Procedurally linked MiniMON29K 3.0 Delta\n"); |
#endif |
fprintf(stderr, "Usage: %s %s\nGoodbye.\n", |
ProgramName, error_msg[(int)error_number]); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Usage: %s %s\nGoodbye.\n", |
ProgramName, error_msg[(int)error_number]); |
} else { |
fprintf(stderr, "DFEERROR: %d : %s\nFatal error. Exiting.\n", |
(int)error_number, error_msg[(int)error_number]); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "DFEERROR: %d : %s\nFatal error. Exiting.\n", |
(int)error_number, error_msg[(int)error_number]); |
} |
|
NumberOfConnections=0; |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fclose(io_config.echo_file); |
|
exit((int) error_number); |
} |
|
|
/* |
** This function prints out a warning message from |
** the error_msg[] string array. |
*/ |
|
void |
warning(error_number) |
INT32 error_number; |
{ |
fprintf(stderr, "DFEWARNING: %d : %s\n", (int) error_number, error_msg[(int)error_number]); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "DFEWARNING: %d : %s\n", error_number, error_msg[(int)error_number]); |
} |
|
|
/* Parse the command line arguments */ |
void |
Mini_parse_args(argc, argv) |
int argc; |
char **argv; |
{ |
int i, j; |
int len; |
|
len = 0; |
for (i = 1; i < argc; i++) { /* ISS */ |
len = len + (int) strlen(argv[i]); |
}; |
if (len == (int) 0) { |
connect_string = NULL; |
} else { |
if ((connect_string = (char *) malloc (len + argc)) == NULL) { |
fatal_error(EMALLOC); |
}; |
for (i = 1; i < argc; i++) { /* ISS */ |
if (strcasecmp(argv[i], "-TIP") == 0) { |
i++; |
if (i >= argc) |
fatal_error(EMUSAGE); |
connect_string = argv[i]; |
} else if (strcmp(argv[i], "-log") == 0) { |
i++; |
if (i >= argc) |
fatal_error(EMUSAGE); |
(void) strcpy((char *)(&(io_config.log_filename[0])),argv[i]); |
io_config.log_mode = (INT32) TRUE; |
} else if (strcmp (argv[i], "-w") == 0) { /* Wait time param */ |
i++; |
if (i >= argc) |
fatal_error(EMUSAGE); |
if (sscanf(argv[i], "%ld", &udi_waittime) != 1) |
fatal_error(EMUSAGE); |
} else if (strcmp (argv[i], "-ms") == 0) { /* mem stack size */ |
i++; |
if (i >= argc) |
fatal_error(EMUSAGE); |
if (sscanf(argv[i], "%lx", &init_info.mem_stack_size) != 1) |
fatal_error(EMUSAGE); |
} else if (strcmp (argv[i], "-rs") == 0) { /* reg stack size */ |
i++; |
if (i >= argc) |
fatal_error(EMUSAGE); |
if (sscanf(argv[i], "%lx", &init_info.reg_stack_size) != 1) |
fatal_error(EMUSAGE); |
} else if (strcmp(argv[i], "-d") == 0) { |
monitor_enable = TRUE; |
} else if (strcasecmp(argv[i], "-D") == 0) { |
monitor_enable = TRUE; |
} else if (strcmp(argv[i], "-le") == 0) { |
host_config.target_endian = LITTLE; |
} else if (strcmp(argv[i], "-q") == 0) { |
QuietMode = 1; |
} else if (strcmp(argv[i], "-c") == 0) { |
i++; |
if (i >= argc) |
fatal_error(EMUSAGE); |
(void) strcpy((char *)(&(io_config.cmd_filename[0])),argv[i]); |
io_config.cmd_file_io = TRUE; |
} else if (strcmp(argv[i], "-e") == 0) { |
i++; |
if (i >= argc) |
fatal_error(EMUSAGE); |
(void) strcpy((char *)(&(io_config.echo_filename[0])),argv[i]); |
io_config.echo_mode = (INT32) TRUE; |
if ((io_config.echo_file = fopen (io_config.echo_filename, "w")) == NULL) { |
warning (EMECHOPEN); |
io_config.echo_mode = (INT32) FALSE; |
} |
} else { |
(void) strcpy (&CoffFileName[0], argv[i]); |
Ex_argc = argc - i; |
(void) strcpy(Ex_argstring, argv[i]); |
for (j=1; j < Ex_argc; j++) { |
(void) strcat(Ex_argstring, " "); |
(void) strcat (Ex_argstring, argv[i+j]); |
} |
Ex_sym = 0; |
Ex_sects = (STYP_ABS|STYP_TEXT|STYP_LIT|STYP_DATA|STYP_BSS); |
Ex_space = (INT32) I_MEM; |
Ex_loaded = 1; /* given */ |
break; |
} |
}; /* end for */ |
}; /* end if-else */ |
} |
|
/* Function to initialize host_config and io_config data structures |
* to their default values * |
*/ |
|
INT32 |
Mini_initialize(host, io, init) |
HOST_CONFIG *host; |
IO_CONFIG *io; |
INIT_INFO *init; |
{ |
/* Initialize host configuration information */ |
|
#ifdef MSDOS |
host->host_endian = LITTLE; |
#else |
host->host_endian = BIG; |
#endif |
|
host->target_endian = BIG; /* default */ |
host->version = host_version; |
host->date = host_date; |
|
/* Initialize I/O configuration information */ |
|
io->hif = TRUE; |
io->io_control = TERM_USER; |
io->cmd_ready = FALSE; |
io->clear_to_send = TRUE; |
io->target_running = FALSE; |
io->cmd_file = NULL; |
io->cmd_filename[0] = '\0'; |
io->cmd_file_io = FALSE; |
io->log_mode = FALSE; |
io->log_file = NULL; |
io->log_filename[0] = '\0'; |
io->echo_mode = FALSE; |
io->echo_file = NULL; |
io->echo_filename[0] = '\0'; |
io->io_toggle_char = (BYTE) 21; /* CTRL-U */ |
|
init->mem_stack_size = (UINT32) -1; |
init->reg_stack_size = (UINT32) -1; |
return(SUCCESS); |
} |
|
void |
Def_CtrlC_Hdlr(num) |
int num; |
{ |
Mini_io_reset(); |
if (!QuietMode) { |
fprintf(stderr, "\nInterrupted.\n"); |
if (io_config.echo_mode == (INT32) TRUE) { |
fprintf(io_config.echo_file, "\nInterrupted.\n"); |
(void) fclose (io_config.echo_file); |
} |
} |
Mini_TIP_SetCurrSession(0); |
Mini_TIP_exit(); |
exit(1); |
} |
|
/dasm.c
0,0 → 1,1452
static char _[] = " @(#)dasm.c 5.22 93/08/11 11:43:53, Srini, AMD"; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** |
** This code is used to disasseble Am29000 instructions. Each |
** instruction is treated as four sequential bytes representing |
** the instruction in big endian format. This should permit the |
** code to run on both big and little endian machines, provided |
** that the buffer containing the instructions is in big endian |
** format. |
** |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <string.h> |
#ifdef MSDOS |
#include <stdlib.h> |
#endif |
#include "opcodes.h" |
#include "memspcs.h" |
#include "main.h" |
#include "monitor.h" |
#include "miniint.h" |
#include "error.h" |
|
|
/* |
** There are approximately 23 different instruction formats for the |
** Am29000. Instructions are disassembled using one of these formats. |
** It should be noted that more compact code for doing diassembly |
** could have been produced. It was decided that this approach was |
** the easiest to understand and modify and that the structure would |
** lend itself to the possibility of automatic code generation in |
** future disassemblers (a disassembler-compiler?). |
** |
** Also note that these functions will correctly disassemble |
** instructions in a buffer in big endian format. Since the data is |
** read in from the target as a stream of bytes, no conversion should |
** be necessary. This disassembly code should work on either big or |
** little endian hosts. |
** |
** Note: Opcodes in the "switch" statement are sorted in numerical |
** order. |
** |
** Note2: CLASS, CONVERT, SQRT may require a different format. |
** |
*/ |
|
|
int get_addr_29k_m PARAMS((char *, struct addr_29k_t *, INT32)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
void convert32 PARAMS((BYTE *)); |
INT32 match_entry PARAMS((ADDR32 offset, |
INT32 space, |
int *id, |
struct bkpt_t **table)); |
|
void dasm_instr PARAMS((ADDR32, struct instr_t *)); |
|
void dasm_undefined PARAMS((struct instr_t *, ADDR32)); |
void dasm_ra_const16n PARAMS((struct instr_t *, ADDR32)); |
void dasm_ra_const16h PARAMS((struct instr_t *, ADDR32)); |
void dasm_ra_const16 PARAMS((struct instr_t *, ADDR32)); |
void dasm_spid_const16 PARAMS((struct instr_t *, ADDR32)); |
void dasm_ce_cntl_ra_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_ce_cntl_ra_const8 PARAMS((struct instr_t *, ADDR32)); |
void dasm_rc_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_rc_const8 PARAMS((struct instr_t *, ADDR32)); |
void dasm_rc_ra_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_rc_ra_const8 PARAMS((struct instr_t *, ADDR32)); |
void dasm_vn_ra_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_vn_ra_const8 PARAMS((struct instr_t *, ADDR32)); |
void dasm_rc_ra PARAMS((struct instr_t *, ADDR32)); |
void dasm_none PARAMS((struct instr_t *, ADDR32)); |
void dasm_one PARAMS((struct instr_t *, ADDR32)); |
void dasm_atarget PARAMS((struct instr_t *, ADDR32)); |
void dasm_rtarget PARAMS((struct instr_t *, ADDR32)); |
void dasm_ra_rtarget PARAMS((struct instr_t *, ADDR32)); |
void dasm_ra_atarget PARAMS((struct instr_t *, ADDR32)); |
void dasm_ra_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_rc_spid PARAMS((struct instr_t *, ADDR32)); |
void dasm_spid_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_dc_ra_rb PARAMS((struct instr_t *, ADDR32)); |
void dasm_convert PARAMS((struct instr_t *, ADDR32)); |
|
|
|
INT32 |
dasm_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
static INT32 memory_space=I_MEM; |
static ADDR32 address=0; |
INT32 byte_count=(16*sizeof(INST32)); |
int i; |
int result; |
INT32 bytes_returned; |
int bkpt_index; |
struct instr_t instr; |
struct addr_29k_t addr_29k; |
struct addr_29k_t addr_29k_start; |
struct addr_29k_t addr_29k_end; |
|
INT32 retval; |
INT32 hostendian; |
BYTE *read_buffer; |
|
|
/* Is it an 'l' (disassemble) command? */ |
if (strcmp(token[0], "l") != 0) |
return (EMSYNTAX); |
|
/* |
** Parse parameters |
*/ |
|
if (token_count == 1) { |
address = (address & 0xfffffffc) + byte_count; |
} |
else |
if (token_count == 2) { |
result = get_addr_29k_m(token[1], &addr_29k_start, I_MEM); |
if (result != 0) |
return (EMSYNTAX); |
result = addr_29k_ok(&addr_29k_start); |
if (result != 0) |
return (result); |
address = (addr_29k_start.address & 0xfffffffc); |
memory_space = addr_29k_start.memory_space; |
} |
else |
if (token_count == 3) { |
result = get_addr_29k_m(token[1], &addr_29k_start, I_MEM); |
if (result != 0) |
return (EMSYNTAX); |
result = addr_29k_ok(&addr_29k_start); |
if (result != 0) |
return (result); |
result = get_addr_29k_m(token[2], &addr_29k_end, I_MEM); |
if (result != 0) |
return (EMSYNTAX); |
result = addr_29k_ok(&addr_29k_end); |
if (result != 0) |
return (result); |
if (addr_29k_start.memory_space != addr_29k_end.memory_space) |
return (EMBADADDR); |
if (addr_29k_start.address > addr_29k_end.address) |
return (EMBADADDR); |
address = (addr_29k_start.address & 0xfffffffc); |
memory_space = addr_29k_start.memory_space; |
byte_count = (addr_29k_end.address & 0xfffffffc) - |
(addr_29k_start.address & 0xfffffffc) + |
sizeof(INT32); |
} |
else |
/* Too many args */ |
return (EMSYNTAX); |
|
/* Will the data overflow the message buffer? Done in TIP */ |
|
if ((read_buffer = (BYTE *) malloc((unsigned int) byte_count)) == NULL) { |
warning(EMALLOC); |
return(FAILURE); |
}; |
|
hostendian = FALSE; |
if ((retval = Mini_read_req(memory_space, |
address, |
(byte_count/4), |
(INT16) 4, /* I_MEM/I_ROM always size 4 */ |
&bytes_returned, |
read_buffer, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
} else if (retval == SUCCESS) { |
for (i=0; i<(int)(bytes_returned*4); i=i+sizeof(INST32)) { |
|
addr_29k.memory_space = memory_space; |
addr_29k.address = address + (ADDR32) i; |
|
if (host_config.target_endian == LITTLE) { |
instr.op = read_buffer[i+3]; |
instr.c = read_buffer[i+2]; |
instr.a = read_buffer[i+1]; |
instr.b = read_buffer[i]; |
} else { /* BIG endian assumed */ |
instr.op = read_buffer[i]; |
instr.c = read_buffer[i+1]; |
instr.a = read_buffer[i+2]; |
instr.b = read_buffer[i+3]; |
} |
|
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%08lx ", addr_29k.address); |
fprintf(stderr, "%08lx ", addr_29k.address); |
|
/* Is there an breakpoint at this location? */ |
match_entry(addr_29k.address, addr_29k.memory_space, &bkpt_index, &bkpt_table); |
if (io_config.echo_mode == (INT32) TRUE) |
if (bkpt_index <= (int) 0) |
fprintf(io_config.echo_file, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
else |
fprintf(io_config.echo_file, "%02x%02x%02x%02x *", instr.op, instr.c, |
instr.a, instr.b); |
|
if (bkpt_index <= (int) 0) |
fprintf(stderr, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
else |
fprintf(stderr, "%02x%02x%02x%02x *", instr.op, instr.c, |
instr.a, instr.b); |
|
dasm_instr((address + (ADDR32) i), |
&instr); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
fprintf(stderr, "\n"); |
} /* end for loop */ |
}; |
|
(void) free ((char *) read_buffer); |
return (0); |
} |
|
|
|
/* |
** This function is used to disassemble a singe Am29000 instruction. |
** A pointer to the next free space in the buffer is returned. |
*/ |
|
|
void |
dasm_instr(addr, instr) |
ADDR32 addr; |
struct instr_t *instr; |
{ |
|
switch (instr->op) { |
|
/* Opcodes 0x00 to 0x0F */ |
case ILLEGAL_00: dasm_undefined(instr, addr); |
break; |
case CONSTN: dasm_ra_const16n(instr, addr); |
break; |
case CONSTH: dasm_ra_const16h(instr, addr); |
break; |
case CONST: dasm_ra_const16(instr, addr); |
break; |
case MTSRIM: dasm_spid_const16(instr, addr); |
break; |
case CONSTHZ: dasm_ra_const16(instr, addr); |
break; |
case LOADL0: dasm_ce_cntl_ra_rb(instr, addr); |
break; |
case LOADL1: dasm_ce_cntl_ra_const8(instr, addr); |
break; |
case CLZ0: dasm_rc_rb(instr, addr); |
break; |
case CLZ1: dasm_rc_const8(instr, addr); |
break; |
case EXBYTE0: dasm_rc_ra_rb(instr, addr); |
break; |
case EXBYTE1: dasm_rc_ra_const8(instr, addr); |
break; |
case INBYTE0: dasm_rc_ra_rb(instr, addr); |
break; |
case INBYTE1: dasm_rc_ra_const8(instr, addr); |
break; |
case STOREL0: dasm_ce_cntl_ra_rb(instr, addr); |
break; |
case STOREL1: dasm_ce_cntl_ra_const8(instr, addr); |
break; |
|
/* Opcodes 0x10 to 0x1F */ |
case ADDS0: dasm_rc_ra_rb(instr, addr); |
break; |
case ADDS1: dasm_rc_ra_const8(instr, addr); |
break; |
case ADDU0: dasm_rc_ra_rb(instr, addr); |
break; |
case ADDU1: dasm_rc_ra_const8(instr, addr); |
break; |
case ADD0: dasm_rc_ra_rb(instr, addr); |
break; |
case ADD1: dasm_rc_ra_const8(instr, addr); |
break; |
case LOAD0: dasm_ce_cntl_ra_rb(instr, addr); |
break; |
case LOAD1: dasm_ce_cntl_ra_const8(instr, addr); |
break; |
case ADDCS0: dasm_rc_ra_rb(instr, addr); |
break; |
case ADDCS1: dasm_rc_ra_const8(instr, addr); |
break; |
case ADDCU0: dasm_rc_ra_rb(instr, addr); |
break; |
case ADDCU1: dasm_rc_ra_const8(instr, addr); |
break; |
case ADDC0: dasm_rc_ra_rb(instr, addr); |
break; |
case ADDC1: dasm_rc_ra_const8(instr, addr); |
break; |
case STORE0: dasm_ce_cntl_ra_rb(instr, addr); |
break; |
case STORE1: dasm_ce_cntl_ra_const8(instr, addr); |
break; |
|
/* Opcodes 0x20 to 0x2F */ |
case SUBS0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBS1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUBU0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBU1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUB0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUB1: dasm_rc_ra_const8(instr, addr); |
break; |
case LOADSET0: dasm_ce_cntl_ra_rb(instr, addr); |
break; |
case LOADSET1: dasm_ce_cntl_ra_const8(instr, addr); |
break; |
case SUBCS0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBCS1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUBCU0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBCU1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUBC0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBC1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPBYTE0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPBYTE1: dasm_rc_ra_const8(instr, addr); |
break; |
|
|
/* Opcodes 0x30 to 0x3F */ |
case SUBRS0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBRS1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUBRU0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBRU1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUBR0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBR1: dasm_rc_ra_const8(instr, addr); |
break; |
case LOADM0: dasm_ce_cntl_ra_rb(instr, addr); |
break; |
case LOADM1: dasm_ce_cntl_ra_const8(instr, addr); |
break; |
case SUBRCS0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBRCS1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUBRCU0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBRCU1: dasm_rc_ra_const8(instr, addr); |
break; |
case SUBRC0: dasm_rc_ra_rb(instr, addr); |
break; |
case SUBRC1: dasm_rc_ra_const8(instr, addr); |
break; |
case STOREM0: dasm_ce_cntl_ra_rb(instr, addr); |
break; |
case STOREM1: dasm_ce_cntl_ra_const8(instr, addr); |
break; |
|
/* Opcodes 0x40 to 0x4F */ |
case CPLT0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPLT1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPLTU0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPLTU1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPLE0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPLE1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPLEU0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPLEU1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPGT0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPGT1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPGTU0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPGTU1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPGE0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPGE1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPGEU0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPGEU1: dasm_rc_ra_const8(instr, addr); |
break; |
|
/* Opcodes 0x50 to 0x5F */ |
case ASLT0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASLT1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASLTU0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASLTU1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASLE0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASLE1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASLEU0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASLEU1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASGT0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASGT1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASGTU0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASGTU1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASGE0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASGE1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASGEU0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASGEU1: dasm_vn_ra_const8(instr, addr); |
break; |
|
/* Opcodes 0x60 to 0x6F */ |
case CPEQ0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPEQ1: dasm_rc_ra_const8(instr, addr); |
break; |
case CPNEQ0: dasm_rc_ra_rb(instr, addr); |
break; |
case CPNEQ1: dasm_rc_ra_const8(instr, addr); |
break; |
case MUL0: dasm_rc_ra_rb(instr, addr); |
break; |
case MUL1: dasm_rc_ra_const8(instr, addr); |
break; |
case MULL0: dasm_rc_ra_rb(instr, addr); |
break; |
case MULL1: dasm_rc_ra_const8(instr, addr); |
break; |
case DIV0_OP0: dasm_rc_rb(instr, addr); |
break; |
case DIV0_OP1: dasm_rc_const8(instr, addr); |
break; |
case DIV_OP0: dasm_rc_ra_rb(instr, addr); |
break; |
case DIV_OP1: dasm_rc_ra_const8(instr, addr); |
break; |
case DIVL0: dasm_rc_ra_rb(instr, addr); |
break; |
case DIVL1: dasm_rc_ra_const8(instr, addr); |
break; |
case DIVREM0: dasm_rc_ra_rb(instr, addr); |
break; |
case DIVREM1: dasm_rc_ra_const8(instr, addr); |
break; |
|
/* Opcodes 0x70 to 0x7F */ |
case ASEQ0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASEQ1: dasm_vn_ra_const8(instr, addr); |
break; |
case ASNEQ0: dasm_vn_ra_rb(instr, addr); |
break; |
case ASNEQ1: dasm_vn_ra_const8(instr, addr); |
break; |
case MULU0: dasm_rc_ra_rb(instr, addr); |
break; |
case MULU1: dasm_rc_ra_const8(instr, addr); |
break; |
case ILLEGAL_76: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_77: dasm_undefined(instr, addr); |
break; |
case INHW0: dasm_rc_ra_rb(instr, addr); |
break; |
case INHW1: dasm_rc_ra_const8(instr, addr); |
break; |
case EXTRACT0: dasm_rc_ra_rb(instr, addr); |
break; |
case EXTRACT1: dasm_rc_ra_const8(instr, addr); |
break; |
case EXHW0: dasm_rc_ra_rb(instr, addr); |
break; |
case EXHW1: dasm_rc_ra_const8(instr, addr); |
break; |
case EXHWS: dasm_rc_ra(instr, addr); |
break; |
case ILLEGAL_7F: dasm_undefined(instr, addr); |
break; |
|
/* Opcodes 0x80 to 0x8F */ |
case SLL0: dasm_rc_ra_rb(instr, addr); |
break; |
case SLL1: dasm_rc_ra_const8(instr, addr); |
break; |
case SRL0: dasm_rc_ra_rb(instr, addr); |
break; |
case SRL1: dasm_rc_ra_const8(instr, addr); |
break; |
case ILLEGAL_84: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_85: dasm_undefined(instr, addr); |
break; |
case SRA0: dasm_rc_ra_rb(instr, addr); |
break; |
case SRA1: dasm_rc_ra_const8(instr, addr); |
break; |
case IRET: dasm_none(instr, addr); |
break; |
case HALT_OP: dasm_none(instr, addr); |
break; |
case ILLEGAL_8A: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_8B: dasm_undefined(instr, addr); |
break; |
case IRETINV: |
if ((target_config.processor_id & 0x60) == 0x60) |
dasm_one(instr, addr); |
else |
dasm_none(instr, addr); |
break; |
case ILLEGAL_8D: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_8E: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_8F: dasm_undefined(instr, addr); |
break; |
|
/* Opcodes 0x90 to 0x9F */ |
case AND_OP0: dasm_rc_ra_rb(instr, addr); |
break; |
case AND_OP1: dasm_rc_ra_const8(instr, addr); |
break; |
case OR_OP0: dasm_rc_ra_rb(instr, addr); |
break; |
case OR_OP1: dasm_rc_ra_const8(instr, addr); |
break; |
case XOR_OP0: dasm_rc_ra_rb(instr, addr); |
break; |
case XOR_OP1: dasm_rc_ra_const8(instr, addr); |
break; |
case XNOR0: dasm_rc_ra_rb(instr, addr); |
break; |
case XNOR1: dasm_rc_ra_const8(instr, addr); |
break; |
case NOR0: dasm_rc_ra_rb(instr, addr); |
break; |
case NOR1: dasm_rc_ra_const8(instr, addr); |
break; |
case NAND0: dasm_rc_ra_rb(instr, addr); |
break; |
case NAND1: dasm_rc_ra_const8(instr, addr); |
break; |
case ANDN0: dasm_rc_ra_rb(instr, addr); |
break; |
case ANDN1: dasm_rc_ra_const8(instr, addr); |
break; |
case SETIP: dasm_rc_ra_rb(instr, addr); |
break; |
case INV: |
if ((target_config.processor_id & 0x60) == 0x60) |
dasm_one(instr, addr); |
else |
dasm_none(instr, addr); |
break; |
|
/* Opcodes 0xA0 to 0xAF */ |
case JMP0: dasm_rtarget(instr, addr); |
break; |
case JMP1: dasm_atarget(instr, addr); |
break; |
case ILLEGAL_A2: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_A3: dasm_undefined(instr, addr); |
break; |
case JMPF0: dasm_ra_rtarget(instr, addr); |
break; |
case JMPF1: dasm_ra_atarget(instr, addr); |
break; |
case ILLEGAL_A6: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_A7: dasm_undefined(instr, addr); |
break; |
case CALL0: dasm_ra_rtarget(instr, addr); |
break; |
case CALL1: dasm_ra_atarget(instr, addr); |
break; |
case ORN_OP0: dasm_undefined(instr, addr); |
break; |
case ORN_OP1: dasm_undefined(instr, addr); |
break; |
case JMPT0: dasm_ra_rtarget(instr, addr); |
break; |
case JMPT1: dasm_ra_atarget(instr, addr); |
break; |
case ILLEGAL_AE: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_AF: dasm_undefined(instr, addr); |
break; |
|
/* Opcodes 0xB0 to 0xBF */ |
case ILLEGAL_B0: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_B1: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_B2: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_B3: dasm_undefined(instr, addr); |
break; |
case JMPFDEC0: dasm_ra_rtarget(instr, addr); |
break; |
case JMPFDEC1: dasm_ra_atarget(instr, addr); |
break; |
case MFTLB: dasm_rc_ra(instr, addr); |
break; |
case ILLEGAL_B7: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_B8: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_B9: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_BA: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_BB: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_BC: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_BD: dasm_undefined(instr, addr); |
break; |
case MTTLB: dasm_ra_rb(instr, addr); |
break; |
case ILLEGAL_BF: dasm_undefined(instr, addr); |
break; |
|
/* Opcodes 0xC0 to 0xCF */ |
case JMPI: dasm_rb(instr, addr); |
break; |
case ILLEGAL_C1: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_C2: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_C3: dasm_undefined(instr, addr); |
break; |
case JMPFI: dasm_ra_rb(instr, addr); |
break; |
case ILLEGAL_C5: dasm_undefined(instr, addr); |
break; |
case MFSR: dasm_rc_spid(instr, addr); |
break; |
case ILLEGAL_C7: dasm_undefined(instr, addr); |
break; |
case CALLI: dasm_ra_rb(instr, addr); |
break; |
case ILLEGAL_C9: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_CA: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_CB: dasm_undefined(instr, addr); |
break; |
case JMPTI: dasm_ra_rb(instr, addr); |
break; |
case ILLEGAL_CD: dasm_undefined(instr, addr); |
break; |
case MTSR: dasm_spid_rb(instr, addr); |
break; |
case ILLEGAL_CF: dasm_undefined(instr, addr); |
break; |
|
/* Opcodes 0xD0 to 0xDF */ |
case ILLEGAL_D0: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_D1: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_D2: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_D3: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_D4: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_D5: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_D6: dasm_undefined(instr, addr); |
break; |
case EMULATE: dasm_vn_ra_rb(instr, addr); |
break; |
case ILLEGAL_D8: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_D9: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_DA: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_DB: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_DC: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_DD: dasm_undefined(instr, addr); |
break; |
case MULTM: dasm_rc_ra_rb(instr, addr); |
break; |
case MULTMU: dasm_rc_ra_rb(instr, addr); |
break; |
|
/* Opcodes 0xE0 to 0xEF */ |
case MULTIPLY: dasm_rc_ra_rb(instr, addr); |
break; |
case DIVIDE: dasm_rc_ra_rb(instr, addr); |
break; |
case MULTIPLU: dasm_rc_ra_rb(instr, addr); |
break; |
case DIVIDU: dasm_rc_ra_rb(instr, addr); |
break; |
case CONVERT: dasm_convert(instr, addr); |
break; |
case SQRT: dasm_rc_ra_const8(instr, addr); |
break; |
case CLASS: dasm_dc_ra_rb(instr, addr); |
break; |
case ILLEGAL_E7: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_E8: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_E9: dasm_undefined(instr, addr); |
break; |
case FEQ: dasm_rc_ra_rb(instr, addr); |
break; |
case DEQ: dasm_rc_ra_rb(instr, addr); |
break; |
case FGT: dasm_rc_ra_rb(instr, addr); |
break; |
case DGT: dasm_rc_ra_rb(instr, addr); |
break; |
case FGE: dasm_rc_ra_rb(instr, addr); |
break; |
case DGE: dasm_rc_ra_rb(instr, addr); |
break; |
|
/* Opcodes 0xF0 to 0xFF */ |
case FADD: dasm_rc_ra_rb(instr, addr); |
break; |
case DADD: dasm_rc_ra_rb(instr, addr); |
break; |
case FSUB: dasm_rc_ra_rb(instr, addr); |
break; |
case DSUB: dasm_rc_ra_rb(instr, addr); |
break; |
case FMUL: dasm_rc_ra_rb(instr, addr); |
break; |
case DMUL: dasm_rc_ra_rb(instr, addr); |
break; |
case FDIV: dasm_rc_ra_rb(instr, addr); |
break; |
case DDIV: dasm_rc_ra_rb(instr, addr); |
break; |
case ILLEGAL_F8: dasm_undefined(instr, addr); |
break; |
case FDMUL: dasm_rc_ra_rb(instr, addr); |
break; |
case ILLEGAL_FA: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_FB: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_FC: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_FD: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_FE: dasm_undefined(instr, addr); |
break; |
case ILLEGAL_FF: dasm_undefined(instr, addr); |
break; |
} /* end switch */ |
|
} /* End dasm_instr() */ |
|
|
|
|
/* |
** The following functions are used to format an instruction |
** into human-readable form. All of the Am29000 instruction |
** formats are supported below. |
*/ |
|
|
/* |
** Format: 0xnnnnnnnn |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_undefined(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, ".word 0x%02x%02x%02x%02x", instr->op, |
instr->c, instr->a, instr->b); |
(void) fprintf(stderr, ".word 0x%02x%02x%02x%02x", instr->op, |
instr->c, instr->a, instr->b); |
} |
|
|
|
/* |
** Format: <Mnemonic> ra, const16 |
** |
** (See CONSTN) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_ra_const16n(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const16; |
const16 = (INT32) ((instr->b | (instr->c << 8)) | 0xffff0000); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], const16); |
(void) fprintf(stderr, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], const16); |
} |
|
|
|
/* |
** Format: <Mnemonic> ra, const16 |
** |
** (See CONSTH) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_ra_const16h(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const32; |
INT32 i_15_8; |
INT32 i_7_0; |
|
i_15_8 = (INT32) instr->c; |
i_7_0 = (INT32) instr->b; |
const32 = ((i_15_8 << 24) | (i_7_0 << 16)); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], const32); |
(void) fprintf(stderr, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], const32); |
} |
|
|
|
/* |
** Format: <Mnemonic> ra, const16 |
** |
** (See CONST) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_ra_const16(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const16; |
const16 = (INT32) (instr->b | (instr->c << 8)); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,0x%x", opcode_name[instr->op], |
reg[instr->a], const16); |
(void) fprintf(stderr, "%s %s,0x%x", opcode_name[instr->op], |
reg[instr->a], const16); |
} |
|
|
|
/* |
** Format: <Mnemonic> spid, const16 |
** |
** (See MTSRIM) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_spid_const16(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const16; |
INT32 i_15_8; |
INT32 i_7_0; |
|
i_15_8 = (INT32) instr->c; |
i_7_0 = (INT32) instr->b; |
|
const16 = ((i_15_8 << 8) | i_7_0); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,0x%x", opcode_name[instr->op], |
spreg[instr->a], const16); |
(void) fprintf(stderr, "%s %s,0x%x", opcode_name[instr->op], |
spreg[instr->a], const16); |
} |
|
|
|
|
/* |
** Format: <Mnemonic> ce, cntl, ra, rb |
** |
** (See LOADM, LOADSET, STORE, STOREL, etc...) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_ce_cntl_ra_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
int ce; |
int cntl; |
|
ce = (int) ((instr->c >> 7) & 0x01); |
cntl = (int) (instr->c & 0x7f); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %x,0x%x,%s,%s", |
opcode_name[instr->op], ce, cntl, |
reg[instr->a], reg[instr->b]); |
(void) fprintf(stderr, "%s %x,0x%x,%s,%s", |
opcode_name[instr->op], ce, cntl, |
reg[instr->a], reg[instr->b]); |
} |
|
|
|
/* |
** Format: <Mnemonic> ce, cntl, ra, const8 |
** |
** (See LOADM, LOADSET, STORE, STOREL, etc...) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_ce_cntl_ra_const8(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
int ce; |
int cntl; |
|
ce = (int) ((instr->c >> 7) & 0x01); |
cntl = (int) (instr->c & 0x7f); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %x,0x%x,%s,0x%x", |
opcode_name[instr->op], ce, cntl, |
reg[instr->a], instr->b); |
(void) fprintf(stderr, "%s %x,0x%x,%s,0x%x", |
opcode_name[instr->op], ce, cntl, |
reg[instr->a], instr->b); |
} |
|
|
|
/* |
** Format: <Mnemonic> rc, rb |
** |
** (See CLZ, DIV0) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_rc_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->b]); |
(void) fprintf(stderr, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->b]); |
} |
|
|
|
/* |
** Format: <Mnemonic> rc, const8 |
** |
** (See CLZ, DIV0) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_rc_const8(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,0x%x", opcode_name[instr->op], |
reg[instr->c], instr->b); |
(void) fprintf(stderr, "%s %s,0x%x", opcode_name[instr->op], |
reg[instr->c], instr->b); |
} |
|
|
|
/* |
** Format: <Mnemonic> rc, ra, rb |
** |
** (See ADD, AND, etc...) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_rc_ra_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->a], reg[instr->b]); |
(void) fprintf(stderr, "%s %s,%s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->a], reg[instr->b]); |
} |
|
|
|
/* |
** Format: <Mnemonic> rc, ra, const8 |
** |
** (See ADD, AND, etc...) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_rc_ra_const8(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s,0x%x", opcode_name[instr->op], |
reg[instr->c], reg[instr->a], instr->b); |
(void) fprintf(stderr, "%s %s,%s,0x%x", opcode_name[instr->op], |
reg[instr->c], reg[instr->a], instr->b); |
} |
|
|
|
/* |
** Format: <Mnemonic> vn, ra, rb |
** |
** (See ASEQ, ASGE, etc...) |
** |
** Note: This function also prints out a "nop" if the |
** instruction is an ASEQ and RA == RB. |
** |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_vn_ra_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if ((instr->op == ASEQ0) && |
(instr->a == instr->b)) { |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "nop"); |
(void) fprintf(stderr, "nop"); |
} else { |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s 0x%x,%s,%s", opcode_name[instr->op], |
instr->c, reg[instr->a], reg[instr->b]); |
(void) fprintf(stderr, "%s 0x%x,%s,%s", opcode_name[instr->op], |
instr->c, reg[instr->a], reg[instr->b]); |
} |
} |
|
|
/* |
** Format: <Mnemonic> vn, ra, const8 |
** |
** (See ASEQ, ASGE, etc...) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_vn_ra_const8(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s 0x%x,%s,0x%x", opcode_name[instr->op], |
instr->c, reg[instr->a], instr->b); |
(void) fprintf(stderr, "%s 0x%x,%s,0x%x", opcode_name[instr->op], |
instr->c, reg[instr->a], instr->b); |
} |
|
|
|
/* |
** Format: <Mnemonic> rc, ra |
** |
** (See MFTBL) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_rc_ra(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->a]); |
(void) fprintf(stderr, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->a]); |
} |
|
|
|
/* |
** Format: <Mnemonic> |
** |
** (See HALT, IRET) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_none(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
(void) fprintf(stderr, "%s", opcode_name[instr->op]); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s", opcode_name[instr->op]); |
} |
|
void |
dasm_one(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
(void) fprintf(stderr, "%s 0x%x", opcode_name[instr->op],(int) (instr->c & 0x3)); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s 0x%x", opcode_name[instr->op], (int) (instr->c & 0x3)); |
} |
|
|
/* |
** Format: <Mnemonic> target |
** |
** (See JMP, etc...) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_atarget(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const16; |
INT32 i_17_10; |
INT32 i_9_2; |
|
i_17_10 = ((INT32) instr->c) << 10; |
i_9_2 = ((INT32) instr->b) << 2; |
const16 = (i_17_10 | i_9_2); |
(void) fprintf(stderr, "%s 0x%lx", opcode_name[instr->op], |
const16); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s 0x%lx", opcode_name[instr->op], |
const16); |
} |
|
|
|
/* |
** Format: <Mnemonic> target+pc |
** |
** (See JMP, etc...) |
*/ |
|
void |
dasm_rtarget(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const16; |
INT32 i_17_10; |
INT32 i_9_2; |
|
i_17_10 = ((INT32) instr->c) << 10; |
i_9_2 = ((INT32) instr->b) << 2; |
const16 = (i_17_10 | i_9_2); |
if ((const16 & 0x00020000) != 0) /* Sign extend (bit 17) */ |
const16 = (const16 | 0xfffc0000); |
(void) fprintf(stderr, "%s 0x%lx", opcode_name[instr->op], |
(const16+pc)); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s 0x%lx", opcode_name[instr->op], |
(const16+pc)); |
} |
|
|
|
/* |
** Format: <Mnemonic> ra, target |
** |
** (See CALL, JMPFDEC, JMPT, etc...) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_ra_atarget(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const16; |
INT32 i_17_10; |
INT32 i_9_2; |
|
i_17_10 = ((INT32) instr->c) << 10; |
i_9_2 = ((INT32) instr->b) << 2; |
const16 = (i_17_10 | i_9_2); |
(void) fprintf(stderr, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], const16); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], const16); |
} |
|
|
|
/* |
** Format: <Mnemonic> ra, target |
** |
** (See CALL, JMPFDEC, JMPT, etc...) |
*/ |
|
void |
dasm_ra_rtarget(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
INT32 const16; |
INT32 i_17_10; |
INT32 i_9_2; |
|
i_17_10 = ((INT32) instr->c) << 10; |
i_9_2 = ((INT32) instr->b) << 2; |
const16 = (i_17_10 | i_9_2); |
if ((const16 & 0x00020000) != 0) /* Sign extend (bit 17) */ |
const16 = (const16 | 0xfffc0000); |
(void) fprintf(stderr, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], (const16+pc)); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,0x%lx", opcode_name[instr->op], |
reg[instr->a], (const16+pc)); |
} |
|
|
|
/* |
** Format: <Mnemonic> ra, rb |
** |
** (See CALLI, JMPFI) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_ra_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
(void) fprintf(stderr, "%s %s,%s", opcode_name[instr->op], |
reg[instr->a], reg[instr->b]); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s", opcode_name[instr->op], |
reg[instr->a], reg[instr->b]); |
} |
|
|
|
/* |
** Format: <Mnemonic> rb |
** |
** (See JMPI) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
(void) fprintf(stderr, "%s %s", opcode_name[instr->op], |
reg[instr->b]); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s", opcode_name[instr->op], |
reg[instr->b]); |
} |
|
|
|
/* |
** Format: <Mnemonic> rc, spid |
** |
** (See MFSR) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_rc_spid(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
(void) fprintf(stderr, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], spreg[instr->a]); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], spreg[instr->a]); |
} |
|
|
|
/* |
** Format: <Mnemonic> spid, rb |
** |
** (See MTSR) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_spid_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s", opcode_name[instr->op], |
spreg[instr->a], reg[instr->b]); |
(void) fprintf(stderr, "%s %s,%s", opcode_name[instr->op], |
spreg[instr->a], reg[instr->b]); |
} |
|
|
|
/* |
** Format: <Mnemonic> dc, ra, rb |
** |
** (See CLASS) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_dc_ra_rb(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
(void) fprintf(stderr, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->a]); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s", opcode_name[instr->op], |
reg[instr->c], reg[instr->a]); |
} |
|
|
|
/* |
** Format: <Mnemonic> rc, ra, UI, RND, FD, FS |
** |
** (See CONVERT) |
*/ |
/*ARGSUSED*/ |
|
void |
dasm_convert(instr, pc) |
struct instr_t *instr; |
ADDR32 pc; |
{ |
int ui; |
int rnd; |
int fd; |
int fs; |
|
ui = (int) ((instr->b >> 7) & 0x01); |
rnd = (int) ((instr->b >> 4) & 0x07); |
fd = (int) ((instr->b >> 2) & 0x03); |
fs = (int) (instr->b & 0x03); |
if (io_config.echo_mode == (INT32) TRUE) |
(void) fprintf(io_config.echo_file, "%s %s,%s,%x,%x,%x,%x", |
opcode_name[instr->op], |
reg[instr->c], reg[instr->a], |
ui, rnd, fd, fs); |
(void) fprintf(stderr, "%s %s,%s,%x,%x,%x,%x", |
opcode_name[instr->op], |
reg[instr->c], reg[instr->a], |
ui, rnd, fd, fs); |
} |
|
|
|
/fill.c
0,0 → 1,257
static char _[] = "@(#)fill.c 5.20 93/07/30 16:38:31, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** |
** This code provides "fill" routines to fill memory and |
** registers. Data may be set as words (32 bit), half-words (16 |
** bit), bytes (8 bit), float (32 bit floating point) or double |
** (64 bit floating point). |
** |
** Since registers are 32 bits long, the fill byte and fill half |
** commands will only be permitted for memory accesses. |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <string.h> |
#include <ctype.h> |
#include <memory.h> |
#include "main.h" |
#include "memspcs.h" |
#include "miniint.h" |
#include "macros.h" |
#include "error.h" |
|
|
#ifdef MSDOS |
#include <stdlib.h> |
#else |
#include <malloc.h> |
#endif |
|
int get_addr_29k PARAMS((char *, struct addr_29k_t *)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
|
int get_word PARAMS((char *, INT32 *)); |
int get_half PARAMS((char *, INT16 *)); |
int get_byte PARAMS((char *, BYTE *)); |
int get_float PARAMS((char *, float *)); |
int get_double PARAMS((char *, double *)); |
|
int set_data PARAMS((BYTE *, BYTE *, int)); |
|
|
/* |
** The function below is used in filling data. This function is |
** called in the main command loop parser of the monitor. The |
** parameters passed to this function are: |
** |
** token - This is an array of pointers to strings. Each string |
** referenced by this array is a "token" of the user's |
** input, translated to lower case. |
** |
** token_count - This is the number of items in the token array. |
** |
** This function reduces the tokens to four parameters: |
** the start address of the fill, the end address ofthe fill and |
** and the data to be filled in this range. This data |
** is one of the "temp_" variables. |
** |
*/ |
|
#define MAX_FILL_LEN 128 |
|
INT32 |
fill_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int result; |
INT32 object_size; |
INT32 align_mask; |
INT32 fill_count; |
struct addr_29k_t addr_29k_start; |
struct addr_29k_t addr_29k_end; |
INT32 temp_word; |
INT16 temp_half; |
BYTE temp_byte; |
float temp_float; |
double temp_double; |
|
INT32 retval; |
BYTE fill_data[MAX_FILL_LEN]; |
|
|
if (token_count < 4) { |
return (EMSYNTAX); |
} |
|
/* |
** What is the data format? |
*/ |
|
if ((strcmp(token[0], "f") == 0) || |
(strcmp(token[0], "fw") == 0)) { |
object_size = sizeof(INT32); |
align_mask = 0xfffffffc; |
result = get_word(token[3], &temp_word); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data( fill_data, (BYTE *)&temp_word, sizeof(INT32)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "fh") == 0) { |
object_size = sizeof(INT16); |
align_mask = 0xfffffffe; |
result = get_half(token[3], &temp_half); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data( fill_data, (BYTE *)&temp_half, sizeof(INT16)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "fb") == 0) { |
object_size = sizeof(BYTE); |
align_mask = 0xffffffff; |
result = get_byte(token[3], &temp_byte); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(fill_data, (BYTE *)&temp_byte, sizeof(BYTE)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "ff") == 0) { |
object_size = sizeof(float); |
align_mask = 0xfffffffc; |
result = get_float(token[3], &temp_float); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(fill_data, (BYTE *)&temp_float, sizeof(float)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "fd") == 0) { |
object_size = sizeof(double); |
align_mask = 0xfffffffc; |
result = get_double(token[3], &temp_double); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(fill_data, (BYTE *)&temp_double, sizeof(double)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "fs") == 0) { /* fill_data a string */ |
object_size = (INT32) strlen ((char *) token[3]); |
if ((int) object_size >= (int) MAX_FILL_LEN) |
return (EMSYNTAX); |
align_mask = 0xfffffffc; |
(void) memset ((char *) fill_data, (int) '\0', sizeof(fill_data)); |
(void) strcpy ((char *)&fill_data[0], (char *) token[3]); |
} |
else |
return(EMSYNTAX); |
|
/* |
** Get addresses |
*/ |
|
result = get_addr_29k(token[1], &addr_29k_start); |
if (result != 0) |
return (EMSYNTAX); |
result = addr_29k_ok(&addr_29k_start); |
if (result != 0) |
return (result); |
|
result = get_addr_29k(token[2], &addr_29k_end); |
if (result != 0) |
return (EMSYNTAX); |
result = addr_29k_ok(&addr_29k_end); |
if (result != 0) |
return (result); |
|
/* Memory spaces must be the same */ |
if (addr_29k_start.memory_space != addr_29k_end.memory_space) |
return (EMSYNTAX); |
|
/* No need to align registers */ |
if (ISREG(addr_29k_start.memory_space)) |
align_mask = 0xffffffff; |
|
/* Align addresses */ |
addr_29k_start.address = (addr_29k_start.address & align_mask); |
addr_29k_end.address = (addr_29k_end.address & align_mask); |
|
/* End address must be larger than start address */ |
if (addr_29k_start.address > addr_29k_end.address) |
return (EMSYNTAX); |
|
if (ISREG(addr_29k_end.memory_space)) { |
fill_count = ((addr_29k_end.address - |
addr_29k_start.address + 1) * 4) / |
object_size; |
} |
else |
if (ISMEM(addr_29k_end.memory_space)) { |
fill_count = (addr_29k_end.address - |
addr_29k_start.address + |
object_size) / object_size; |
} |
else |
return (EMSYNTAX); |
|
/* |
** We don't set bytes or half words in registers |
*/ |
|
if (ISREG(addr_29k_start.memory_space) && |
(object_size < sizeof(INT32))) |
return (EMSYNTAX); |
|
if ((retval = Mini_fill (addr_29k_start.memory_space, |
addr_29k_start.address, |
fill_count, |
object_size, |
fill_data)) <= TIPFAILURE) { |
return(FAILURE); |
} else if (retval == SUCCESS) { |
return(SUCCESS); |
} else { |
warning(retval); |
return(FAILURE); |
}; |
|
} /* end set_cmd() */ |
|
|
|
/monitor.c
0,0 → 1,1654
static char _[] = "@(#)monitor.c 5.28 93/11/02 11:46:54, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
* This module implements the monitor command interpreter. |
***************************************************************************** |
*/ |
|
#include <stdio.h> |
#include <string.h> |
#include <ctype.h> |
#include <signal.h> |
#ifdef MSDOS |
#include <stdlib.h> |
#include <conio.h> |
#include <io.h> |
#else |
#include <fcntl.h> |
#include <termio.h> |
/* #include <sys/ioctl.h> */ |
#endif |
#include "monitor.h" |
#include "main.h" |
#include "memspcs.h" |
#include "error.h" |
#include "miniint.h" |
|
/* Function declarations */ |
extern void Mini_Ctrl_C_Handler PARAMS((int)); |
extern void Mini_loop PARAMS((void)); |
extern INT32 Mini_go_forever PARAMS((void)); |
extern void Mini_poll_kbd PARAMS((char *cmd_buffer, int size, int mode)); |
extern int Mini_cmdfile_input PARAMS((char *cmd_buffer, int size)); |
extern int tokenize_cmd PARAMS((char *, char **)); |
extern void lcase_tokens PARAMS((char **, int)); |
extern int get_word PARAMS((char *, INT32 *)); |
extern void PrintTrapMsg PARAMS((int trapnum)); |
extern void display_msg PARAMS((void)); |
extern void display_termuser PARAMS((void)); |
extern void display_term29k PARAMS((void)); |
extern INT32 get_pc_addrs PARAMS((ADDR32 *pc1, ADDR32 *cps)); |
extern INT32 get_pc1_inst PARAMS((ADDR32 cps, ADDR32 pc1, BYTE *inst)); |
extern void dasm_instr PARAMS((ADDR32, struct instr_t *)); |
extern void convert32 PARAMS((BYTE *)); |
extern INT32 Mini_send_init_info PARAMS((INIT_INFO *init)); |
|
static int FindCmdIndx PARAMS((char *string)); |
|
/* Globals */ |
GLOBAL struct bkpt_t *bkpt_table; |
|
GLOBAL char cmd_buffer[BUFFER_SIZE]; |
GLOBAL char tip_cmd_buffer[256]; |
GLOBAL int GoCmdFlag=0; |
|
#define TOGGLE_CHAR (io_config.io_toggle_char) |
|
/* Following three vars to be used in stdin/stdout/stderr funcs */ |
#define IO_BUFSIZE 1024 |
static char io_buffer[IO_BUFSIZE]; |
static INT32 io_bufsize; |
static INT32 io_count_done; |
|
static INT32 ProcessorState; |
static int GrossState; |
static INT32 exit_loop; |
static int CtrlCHit=0; |
static int BlockMode; |
/* These modes are defined in montip, udi2mtip.c file */ |
#define TIP_COOKED 0x0 |
#define TIP_RAW 0x1 |
#define TIP_CBREAK 0x2 |
#define TIP_ECHO 0x4 |
#define TIP_ASYNC 0x8 |
#define TIP_NBLOCK 0x10 |
static INT32 TipStdinMode = TIP_COOKED; /* initial */ |
#ifndef MSDOS |
struct termio OldTermbuf, NewTermbuf; /* STDIN, Channel0 */ |
#endif /* MSDOS */ |
|
/* Monitor command table */ |
struct MonitorCommands_t { |
char *CmdString; /* Maximum length */ |
INT32 (*CmdFn) PARAMS((char **, int)); |
}; |
|
static struct MonitorCommands_t MonitorCommands[] = { |
"a", asm_cmd, |
"attach", set_sessionid_cmd, |
"b", bkpt_cmd, |
"bc", bkpt_cmd, |
"b050", bkpt_cmd, |
"b050v", bkpt_cmd, |
"b050p", bkpt_cmd, |
"c", config_cmd, |
"caps", capab_cmd, |
"cp", create_proc_cmd, |
"con", connect_cmd, |
"ch0", channel0_cmd, |
"d", dump_cmd, |
"ex", exit_conn_cmd, |
"dw", dump_cmd, |
"dh", dump_cmd, |
"db", dump_cmd, |
"df", dump_cmd, |
"dd", dump_cmd, |
"dp", destroy_proc_cmd, |
"disc", disconnect_cmd, |
"detach", disconnect_cmd, |
"esc", escape_cmd, |
"eon", echomode_on, |
"eoff", echomode_off, |
"f", fill_cmd, |
"fw", fill_cmd, |
"fh", fill_cmd, |
"fb", fill_cmd, |
"ff", fill_cmd, |
"fd", fill_cmd, |
"fs", fill_cmd, |
"g", go_cmd, |
"h", help_cmd, |
"ix", ix_cmd, |
"il", il_cmd, |
"init", init_proc_cmd, |
"k", kill_cmd, |
"l", dasm_cmd, |
"logon", logon_cmd, |
"logoff", logoff_cmd, |
"m", move_cmd, |
"pid", set_pid_cmd, |
"q", quit_cmd, |
"qoff", quietmode_off, |
"qon", quietmode_on, |
"r", reset_cmd, |
"s", set_cmd, |
"sw", set_cmd, |
"sh", set_cmd, |
"sb", set_cmd, |
"sf", set_cmd, |
"sd", set_cmd, |
"sid", set_sessionid_cmd, |
"t", trace_cmd, |
"target", connect_cmd, |
"tip", tip_cmd, |
"ver", version_cmd, |
"xp", xp_cmd, |
"xc", xc_cmd, |
"y", yank_cmd, |
"zc", cmdfile_cmd, |
"ze", echofile_cmd, |
"zl", set_logfile, |
"?", help_cmd, |
"|", dummy_cmd, |
"", dummy_cmd, |
NULL |
}; |
|
/* Trap Messages */ |
static char *TrapMsg[] = { |
"Illegal Opcode", |
"Unaligned Access", |
"Out of Range", |
"Coprocessor Not Present", |
"Coprocessor Exception", |
"Protection Violation", |
"Instruction Access Exception", |
"Data Access Exception", |
"User-Mode Instruction TLB Miss", |
"User-Mode Data TLB Miss", |
"Supervisor-Mode Instruction TLB Miss", |
"Supervisor-Mode Data TLB Miss", |
"Instruction TLB Protection Violation", |
"Data TLB Protection Violation", |
"Timer", |
"Trace", |
"INTR0", |
"INTR1", |
"INTR2", |
"INTR3", |
"TRAP0", |
"TRAP1", |
"Floating-Point Exception" |
}; |
|
void |
Mini_monitor() |
{ |
|
/* Initialize breakpoint table */ |
|
bkpt_table = NULL; |
GrossState = NOTEXECUTING; |
|
/* |
* Start with the user being the terminal controller. |
*/ |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
|
#ifndef MSDOS |
ioctl (fileno(stdin), TCGETA, &OldTermbuf); /* Initial settings */ |
#endif |
|
/* |
* Define Ctrl-U as the io_toggle_char as default. |
*/ |
io_config.io_toggle_char = (BYTE) 21; |
|
/* |
** Open cmd file (if necessary) |
*/ |
|
if (io_config.cmd_file_io == TRUE) { /* TRUE if -c option given */ |
io_config.cmd_file = fopen(io_config.cmd_filename, "r"); |
if (io_config.cmd_file == NULL) { |
warning (EMCMDOPEN); |
io_config.cmd_file_io = FALSE; |
} else { |
/* MON_STDIN is command file */ |
MON_STDIN = fileno(io_config.cmd_file); /* set MON_STDIN */ |
}; |
} |
|
/* |
** Open log file, if no command file given. |
*/ |
|
if (io_config.log_mode == (INT32) TRUE) { /* -log option given */ |
if (io_config.log_filename) { |
io_config.log_file = fopen(io_config.log_filename, "w"); |
if (io_config.log_file == NULL) { |
io_config.log_mode = (INT32) FALSE; |
warning(EMLOGOPEN); |
} |
} else { |
io_config.log_mode = (INT32) FALSE; |
warning(EMLOGOPEN); |
} |
} |
|
/* Install ctrl-C handler */ |
|
if (signal (SIGINT, Mini_Ctrl_C_Handler) == SIG_ERR) { |
fprintf(stderr, "Ctrl-C handler not installed.\n"); /* warning */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Ctrl-C handler not installed.\n"); /* warning */ |
} |
/* Get into monitor loop */ |
|
Mini_loop(); |
|
} |
|
void |
Mini_loop() |
{ |
INT32 retval; |
int token_count; |
char *token[MAX_TOKENS]; |
int Indx; |
|
exit_loop = FALSE; |
CtrlCHit = 0; |
/* |
** Enter command interpreter loop |
*/ |
|
fprintf(stderr, "%s>", ProgramName); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s>", ProgramName); |
|
BlockMode = BLOCK; /* wait for a user command */ |
do { |
|
if (CtrlCHit) { |
CtrlCHit = 0; |
/* Print a prompt */ |
fprintf(stderr, "\n%s>", ProgramName); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n%s>", ProgramName); |
} |
/* |
** If the target was set to run, get its current status. |
*/ |
if (Mini_get_target_stats((INT32) udi_waittime, &ProcessorState) != SUCCESS) { |
Mini_TIP_DestroyProc(); |
Mini_TIP_exit(); |
fatal_error(EMFATAL); |
}; |
GrossState = (int) (ProcessorState & 0xFF); |
switch (GrossState) { |
case NOTEXECUTING: /* do nothing */ |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
BlockMode = BLOCK; /* wait for a user command */ |
break; |
case EXITED: /* do nothing */ |
if (GoCmdFlag) { |
GoCmdFlag = 0; |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
if (!QuietMode) { |
fprintf (stderr, "Process exited with 0x%lx\n", |
(ProcessorState >> 8)); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "Process exited with 0x%lx\n", |
(ProcessorState >> 8)); |
} |
fprintf (stderr, "%s>", ProgramName); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s> ", ProgramName); |
} |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
BlockMode = BLOCK; /* wait for a user command */ |
break; |
case RUNNING: /* any request from target? */ |
io_config.target_running = TRUE; |
BlockMode = NONBLOCK; /* return immediately */ |
break; |
case STOPPED: |
io_config.io_control=TERM_USER; |
io_config.target_running = TRUE; |
if (GoCmdFlag) { |
GoCmdFlag = 0; |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
fprintf(stderr, "Execution stopped at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Execution stopped at "); |
display_msg(); |
} |
BlockMode = BLOCK; /* wait for next user command */ |
break; |
case BREAK: |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
if (GoCmdFlag) { |
GoCmdFlag = 0; |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
fprintf(stderr, "Breakpoint hit at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Breakpoint hit at "); |
display_msg(); |
} |
BlockMode = BLOCK; /* wait for next user command */ |
break; |
case STEPPED: |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
if (GoCmdFlag) { |
GoCmdFlag = 0; |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
fprintf(stderr, "Stepping... Execution stopped at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Stepping...Execution stopped at "); |
display_msg(); |
} |
BlockMode = BLOCK; /* wait for next user command */ |
break; |
case WAITING: |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
break; |
case HALTED: |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
if (GoCmdFlag) { |
GoCmdFlag = 0; |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
fprintf(stderr, "Execution halted at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Execution halted at "); |
display_msg(); |
} |
BlockMode = BLOCK; /* wait for next user command */ |
break; |
case WARNED: |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
break; |
case TRAPPED: |
io_config.io_control=TERM_USER; |
io_config.target_running = FALSE; |
if (GoCmdFlag) { |
GoCmdFlag = 0; |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
PrintTrapMsg((int) (ProcessorState >> 8)); |
display_msg(); |
} |
BlockMode = BLOCK; /* wait for next user command */ |
break; |
case STDOUT_READY: |
io_bufsize = 0; |
io_count_done = (INT32) 0; |
do { |
Mini_get_stdout(io_buffer, IO_BUFSIZE, &io_count_done); |
write(MON_STDOUT, &io_buffer[0], (int) io_count_done); |
if (io_config.echo_mode == (INT32) TRUE) { |
fflush (io_config.echo_file); |
write (fileno(io_config.echo_file), &io_buffer[0], (int) io_count_done); |
} |
} while (io_count_done == (INT32) IO_BUFSIZE); |
break; |
case STDERR_READY: |
io_bufsize = 0; |
io_count_done = (INT32) 0; |
do { |
Mini_get_stderr(io_buffer, IO_BUFSIZE, &io_count_done); |
write(MON_STDERR, &io_buffer[0], (int) io_count_done); |
if (io_config.echo_mode == (INT32) TRUE) { |
fflush (io_config.echo_file); |
write (fileno(io_config.echo_file), &io_buffer[0], (int) io_count_done); |
} |
} while (io_count_done == (INT32) IO_BUFSIZE); |
break; |
case STDIN_NEEDED: |
/* Line buffered reads only */ |
if (io_config.cmd_file_io == TRUE) { /* read from command file */ |
if (Mini_cmdfile_input(io_buffer, IO_BUFSIZE) == SUCCESS) { |
io_bufsize = strlen(io_buffer); |
fprintf(stderr, "%s", io_buffer); /* echo */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s", io_buffer); /* echo */ |
} else { /* read from terminal */ |
io_bufsize = read( fileno(stdin), io_buffer, IO_BUFSIZE ); |
} |
} else { |
io_bufsize = read( fileno(stdin), io_buffer, IO_BUFSIZE ); |
}; |
if (io_bufsize < 0) |
{ |
fprintf(stderr, "fatal error reading from stdin\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "fatal error reading from stdin\n"); |
} |
if (io_config.echo_mode == (INT32) TRUE) { |
write (fileno(io_config.echo_file), &io_buffer[0], (int) io_bufsize); |
fflush (io_config.echo_file); |
} |
Mini_put_stdin(io_buffer, io_bufsize, &io_count_done); |
break; |
case STDINMODEX: |
/* call TIP to get StdinMode */ |
Mini_stdin_mode_x((INT32 *)&TipStdinMode); |
if (TipStdinMode & TIP_NBLOCK) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode & TIP_ASYNC) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode == TIP_COOKED) |
io_config.io_control = TERM_USER; |
else { |
fprintf(stderr, "DFEWARNING: TIP Requested Stdin Mode Not Supported.\n"); |
fprintf(stderr, "DFEWARNING: Using default mode.\n"); |
TipStdinMode = TIP_COOKED; |
io_config.io_control = TERM_USER; |
} |
|
if (io_config.io_control == TERM_29K) |
display_term29k(); |
break; |
|
default: |
break; |
}; /* end switch */ |
|
|
/* |
** Check for keyboard input from command file first, then keyboard. |
*/ |
if (io_config.io_control == TERM_USER) { |
if (io_config.target_running == FALSE) { |
if (io_config.cmd_ready == FALSE) { /* Get a new user command */ |
if (io_config.cmd_file_io == TRUE) { /* try command file first*/ |
if (Mini_cmdfile_input(cmd_buffer, BUFFER_SIZE) == SUCCESS) { |
fprintf(stderr, "%s", cmd_buffer); |
io_config.cmd_ready = TRUE; |
} else { |
Mini_poll_kbd(cmd_buffer, BUFFER_SIZE, BlockMode); |
} |
} else { /* keyboard */ |
/* Mini_poll_kbd function sets io_config.cmd_ready */ |
Mini_poll_kbd(cmd_buffer, BUFFER_SIZE, BlockMode); |
} |
} |
} else { |
Mini_poll_kbd(cmd_buffer, BUFFER_SIZE, BlockMode); |
} |
} else if (io_config.io_control == TERM_29K) { |
if ((GrossState == RUNNING) || GoCmdFlag) |
Mini_poll_channel0(); /* non-blocking */ |
} else { |
fprintf(stderr, "fatal error: Don't know who is controlling the terminal!\n"); |
return; |
} |
|
|
if (io_config.cmd_ready == TRUE) { /* if there is a command in buffer */ |
#ifdef MSDOS |
if (io_config.log_mode == (INT32) TRUE) /* make a log file */ |
fprintf(io_config.log_file, "%s\n", cmd_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s\n", cmd_buffer); |
#else |
if (io_config.log_mode == (INT32) TRUE) /* make a log file */ |
fprintf(io_config.log_file, "%s", cmd_buffer); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s", cmd_buffer); |
#endif |
/* |
** Parse command |
*/ |
|
token_count = tokenize_cmd(cmd_buffer, token); |
/* Convert first character (command) to lcase */ |
if (isupper(*token[0])) |
(*token[0]) = (char) tolower(*token[0]); |
|
/* If anything but a y or z command, convert to lower case */ |
if ( ((*token[0]) != 'y') && |
((*token[0]) != 'z') ) |
lcase_tokens(token, token_count); |
|
if ((Indx = FindCmdIndx(token[0])) != (int) FAILURE) |
io_config.cmd_ready = TRUE; |
else { |
warning(EMNOSUCHCMD); |
/* Print a prompt */ |
fprintf(stderr, "\n%s>", ProgramName); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n%s>", ProgramName); |
io_config.cmd_ready = FALSE; /* nothing to execute */ |
} |
} |
|
/* |
** Execute command |
*/ |
|
if (io_config.cmd_ready == TRUE) { |
retval = MonitorCommands[Indx].CmdFn(token, token_count); |
io_config.cmd_ready = FALSE; |
if (retval == FAILURE) { |
fprintf(stderr, "Command failed\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Command failed\n"); |
} else if (retval != SUCCESS) { |
warning(retval); |
}; |
/* Print a prompt */ |
if (io_config.io_control == TERM_USER) { |
fprintf(stderr, "%s>", ProgramName); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s>", ProgramName); |
} else { |
display_term29k(); |
} |
} /* if cmd ready */ |
|
} while (exit_loop != TRUE); /* end of do-while */ |
|
/* Close log file */ |
if (io_config.log_mode == (INT32) TRUE) |
(void) fclose(io_config.log_file); |
|
if (bkpt_table != NULL) |
(void) free((char *) bkpt_table); |
} |
|
/* |
** This function takes in a string and produces a lower case, |
** " argv - argc" style array. Then number of elements in the |
** array is returned. |
*/ |
|
int |
tokenize_cmd(cmd, token) |
char *cmd; |
char *token[]; |
{ |
int token_count; |
|
/* Break input into tokens */ |
token_count = 0; |
token[0] = cmd; |
|
if (cmd[0] != '\0') { |
token[token_count] = strtok(cmd, " \t,;\n\r"); |
|
if (token[token_count] != NULL) { |
do { |
token_count = token_count + 1; |
token[token_count] = strtok((char *) NULL, " \t,;\n\r"); |
} while ((token[token_count] != NULL) && |
(token_count < MAX_TOKENS)); |
} |
else { |
token[0] = cmd; |
*token[0] = '\0'; |
} |
} |
|
return (token_count); |
|
} /* end tokenize_cmd() */ |
|
|
|
/* |
** This function is used to convert a list of tokens |
** to all lower case letters. |
*/ |
|
void |
lcase_tokens(token, token_count) |
char *token[MAX_TOKENS]; |
int token_count; |
{ |
int i; |
char *temp_str; |
|
for (i=0; i<token_count; i=i+1) { |
temp_str = token[i]; |
while (*temp_str != '\0') { |
if (isupper(*temp_str)) |
*temp_str = (char) tolower(*temp_str); |
temp_str++; |
} |
} /* end for() */ |
} /* end lcase_string() */ |
|
|
INT32 |
Mini_go_forever() |
{ |
static int complete=0; |
|
/* Terminal control initialization. */ |
io_config.io_control = TERM_USER; /* 3.1-7 */ |
io_config.target_running = TRUE; |
|
#ifndef MSDOS |
ioctl (fileno(stdin), TCGETA, &OldTermbuf); /* Initial settings */ |
#endif |
|
/* Install ctrl-C handler */ |
|
if (signal (SIGINT, Mini_Ctrl_C_Handler) == SIG_ERR) { |
fprintf(stderr, "Ctrl-C handler not installed.\n"); /* warning */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Ctrl-C handler not installed.\n"); /* warning */ |
} |
/* |
** Open cmd file (if necessary) |
*/ |
|
if (io_config.cmd_file_io == TRUE) { /* TRUE if -c option given */ |
io_config.cmd_file = fopen(io_config.cmd_filename, "r"); |
if (io_config.cmd_file == NULL) { |
warning (EMCMDOPEN); |
io_config.cmd_file_io = FALSE; |
} else { |
/* MON_STDIN is command file */ |
MON_STDIN = fileno(io_config.cmd_file); /* set MON_STDIN */ |
}; |
} |
|
Mini_go(); /* set target running */ |
|
do { |
|
/* |
** If the target was set to run, get its current status. |
*/ |
if (Mini_get_target_stats((INT32) udi_waittime, &ProcessorState) != SUCCESS) { |
Mini_TIP_DestroyProc(); |
Mini_TIP_exit(); |
fatal_error(EMFATAL); |
} |
GrossState = (int) (ProcessorState & 0xFF); |
switch (GrossState) { |
case NOTEXECUTING: /* do nothing */ |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
break; |
case EXITED: /* do nothing */ |
if (!QuietMode) { |
fprintf (stderr, "Process exited with 0x%lx\n", |
(ProcessorState >> 8)); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "Process exited with 0x%lx\n", |
(ProcessorState >> 8)); |
} |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
complete=1; |
break; |
case RUNNING: /* any request from target? */ |
break; |
case STOPPED: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
fprintf(stderr, "Execution stopped at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Execution stopped at "); |
display_msg(); |
break; |
case BREAK: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
fprintf(stderr, "Breakpoint hit at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Breakpoint hit at "); |
display_msg(); |
break; |
case STEPPED: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
fprintf(stderr, "Stepping...Execution stopped at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Stepping...Execution stopped at "); |
display_msg(); |
break; |
case WAITING: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
break; |
case HALTED: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
fprintf(stderr, "Execution halted at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Execution halted at "); |
display_msg(); |
break; |
case WARNED: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
break; |
case TRAPPED: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
PrintTrapMsg((int) (ProcessorState >> 8)); |
display_msg(); |
break; |
case STDOUT_READY: |
io_bufsize = 0; |
io_count_done = (INT32) 0; |
do { |
Mini_get_stdout(io_buffer, IO_BUFSIZE, &io_count_done); |
write(MON_STDOUT, &io_buffer[0], (int) io_count_done); |
if (io_config.echo_mode == (INT32) TRUE) { |
fflush (io_config.echo_file); |
write (fileno(io_config.echo_file), &io_buffer[0], (int) io_count_done); |
} |
} while (io_count_done == (INT32) IO_BUFSIZE); |
break; |
case STDERR_READY: |
io_bufsize = 0; |
io_count_done = (INT32) 0; |
do { |
Mini_get_stderr(io_buffer, IO_BUFSIZE, &io_count_done); |
write(MON_STDERR, &io_buffer[0], (int) io_count_done); |
if (io_config.echo_mode == (INT32) TRUE) { |
fflush (io_config.echo_file); |
write (fileno(io_config.echo_file), &io_buffer[0], (int) io_count_done); |
} |
} while (io_count_done == (INT32) IO_BUFSIZE); |
break; |
case STDIN_NEEDED: |
/* Line buffered reads only */ |
if (io_config.cmd_file_io == TRUE) { /* read from command file */ |
if (Mini_cmdfile_input(io_buffer, IO_BUFSIZE) == SUCCESS) { |
io_bufsize = strlen(io_buffer); |
fprintf(stderr, "%s", io_buffer); /* echo */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s", io_buffer); /* echo */ |
} else { /* read from terminal */ |
io_bufsize = read( fileno(stdin), io_buffer, IO_BUFSIZE ); |
} |
} else { |
io_bufsize = read( fileno(stdin), io_buffer, IO_BUFSIZE ); |
}; |
if (io_bufsize < 0) |
{ |
fprintf(stderr, "fatal error reading from stdin\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "fatal error reading from stdin\n"); |
} |
if (io_config.echo_mode == (INT32) TRUE) { |
fflush (io_config.echo_file); |
write (fileno(io_config.echo_file), &io_buffer[0], (int) io_bufsize); |
} |
Mini_put_stdin(io_buffer, io_bufsize, &io_count_done); |
break; |
case STDINMODEX: |
/* call TIP to get StdinMode */ |
Mini_stdin_mode_x((INT32 *)&TipStdinMode); |
if (TipStdinMode & TIP_NBLOCK) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode & TIP_ASYNC) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode == TIP_COOKED) |
io_config.io_control = TERM_USER; |
else { |
fprintf(stderr, "DFEWARNING: TIP Requested Stdin Mode Not Supported.\n"); |
fprintf(stderr, "DFEWARNING: Using default mode.\n"); |
TipStdinMode = TIP_COOKED; |
io_config.io_control = TERM_USER; |
} |
if (io_config.io_control == TERM_29K) |
display_term29k(); |
break; |
|
default: |
complete=1; |
io_config.io_control = TERM_USER; |
io_config.target_running = FALSE; |
break; |
}; /* end switch */ |
#ifdef MSDOS |
if (!complete) |
kbhit(); /* Poll for Ctrl-C */ |
#endif |
if (CtrlCHit) { |
CtrlCHit = 0; |
complete = 1; |
} |
|
if (io_config.io_control == TERM_29K) |
if (GrossState == RUNNING) |
Mini_poll_channel0(); /* non-blocking */ |
else |
TipStdinMode = TIP_COOKED; |
|
} while (!complete); |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
|
fflush(stdout); |
fflush(stderr); |
|
Mini_TIP_DestroyProc(); |
Mini_TIP_exit(); |
|
NumberOfConnections=0; |
return (SUCCESS); |
} |
|
|
INT32 |
get_pc_addrs(pc1, cps) |
ADDR32 *pc1; |
ADDR32 *cps; |
{ |
ADDR32 pc_1; |
ADDR32 cps_b; |
INT32 hostendian; |
INT32 bytes_ret; |
INT32 retval; |
|
hostendian = FALSE; |
if ((retval = Mini_read_req (PC_SPACE, |
(ADDR32) 0, /* doesn't matter */ |
(INT32) 1, |
(INT16) 4, /* size */ |
&bytes_ret, |
(BYTE *) &pc_1, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
}; |
|
*pc1 = (ADDR32) pc_1; |
if (host_config.host_endian != host_config.target_endian) { |
convert32((BYTE *)pc1); |
} |
|
/* get cps */ |
hostendian = FALSE; |
if ((retval = Mini_read_req (SPECIAL_REG, |
(ADDR32) 2, |
(INT32) 1, |
(INT16) 4, /* size */ |
&bytes_ret, |
(BYTE *) &cps_b, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
}; |
*cps = (ADDR32) cps_b; |
if (host_config.host_endian != host_config.target_endian) { |
convert32((BYTE *)cps); |
} |
|
return (SUCCESS); |
} |
|
INT32 |
get_pc1_inst(cps, pc1, inst) |
ADDR32 cps; |
ADDR32 pc1; |
BYTE *inst; |
{ |
INT32 bytes_ret; |
INT32 hostendian; |
INT32 retval; |
INT32 memory_space; |
|
hostendian = FALSE; |
|
if (cps & 0x100L) /* RE bit */ |
memory_space = I_ROM; |
else |
memory_space = I_MEM; |
|
if ((retval = Mini_read_req(memory_space, |
pc1, |
(INT32) 1, |
(INT16) sizeof(INST32), /* size */ |
&bytes_ret, |
(BYTE *) inst, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
}; |
return (SUCCESS); |
} |
|
void |
display_msg() |
{ |
ADDR32 c_pc1; |
ADDR32 c_cps; |
|
union instruction_t { |
BYTE buf[sizeof(struct instr_t)]; |
struct instr_t instr; |
}; |
union instruction_t instruction; |
struct instr_t temp; |
|
(void) get_pc_addrs(&c_pc1, &c_cps); |
(void) get_pc1_inst(c_cps, c_pc1, instruction.buf); |
fprintf(stderr, " %08lx\n", c_pc1); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, " %08lx\n", c_pc1); |
if (host_config.target_endian == LITTLE) { |
temp.op = instruction.instr.b; |
temp.c = instruction.instr.a; |
temp.a = instruction.instr.c; |
temp.b = instruction.instr.op; |
} else { /* default BIG endian */ |
temp.op = instruction.instr.op; |
temp.c = instruction.instr.c; |
temp.a = instruction.instr.a; |
temp.b = instruction.instr.b; |
} |
fprintf(stderr, "%08lx\t %02x%02x%02x%02x\t", c_pc1, |
temp.op, |
temp.c, |
temp.a, |
temp.b); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%08lx\t %02x%02x%02x%02x\t", c_pc1, |
temp.op, |
temp.c, |
temp.a, |
temp.b); |
(void) dasm_instr(c_pc1, &(temp)); |
if (io_config.io_control == TERM_USER) { |
fprintf(stderr, "\n%s>", ProgramName); |
fflush(stderr); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n%s>", ProgramName); |
} |
} |
|
int |
Mini_cmdfile_input(cmd_buffer, size) |
char *cmd_buffer; |
int size; |
{ |
if (fgets(cmd_buffer, size, io_config.cmd_file) == NULL) { |
io_config.cmd_file_io = FALSE; |
(void) fclose(io_config.cmd_file); |
MON_STDIN = fileno (stdin); /* reset to terminal after EOF */ |
return (FAILURE); |
} else { |
return (SUCCESS); |
} |
} |
|
void |
Mini_Ctrl_C_Handler(num) |
int num; |
{ |
CtrlCHit = 1; /* used for run-only mode, no debugging */ |
if (io_config.io_control == TERM_29K) { |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
} |
if (io_config.target_running == TRUE) |
Mini_break(); |
io_config.cmd_ready == FALSE; |
#ifdef MSDOS |
if (signal (SIGINT, Mini_Ctrl_C_Handler) == SIG_ERR) { |
fprintf(stderr, "Ctrl-C handler not installed.\n"); /* warning */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Ctrl-C handler not installed.\n"); /* warning */ |
} |
#endif |
return; |
} |
|
static int |
FindCmdIndx(CmdString) |
char *CmdString; |
{ |
int i; |
|
i = 0; |
while (MonitorCommands[i].CmdString) { |
if (strcmp(CmdString, MonitorCommands[i].CmdString)) |
i++; |
else |
return (i); |
}; |
return (-1); |
} |
|
INT32 |
escape_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
int retval; |
#ifdef MSDOS |
if ((retval = system ((char *) getenv("COMSPEC"))) != 0) |
return ((INT32) EMDOSERR); |
return ((INT32) SUCCESS); |
#else |
if ((retval = system ((char *) getenv("SHELL"))) != 0) |
return ((INT32) EMSYSERR); |
return ((INT32) SUCCESS); |
#endif |
} |
|
INT32 |
dummy_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
return ((INT32) 0); |
} |
|
INT32 |
quit_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
int i; |
|
for (i =0; i < NumberOfConnections; i++) { |
Mini_TIP_SetCurrSession(Session_ids[i]); |
Mini_TIP_DestroyProc(); |
Mini_TIP_exit(); |
}; |
fflush(stdout); |
fflush(stderr); |
exit_loop = TRUE; |
NumberOfConnections=0; |
return ((INT32) 0); |
} |
|
INT32 |
connect_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
|
if (tokencnt < 2) |
return (EMSYNTAX); |
|
if ((retval = Mini_TIP_init(token[1], &Session_ids[NumberOfConnections])) |
== SUCCESS) { |
NumberOfConnections=NumberOfConnections+1; |
}; |
|
return ((INT32) retval); |
} |
|
INT32 |
disconnect_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
int i; |
|
if ((retval = Mini_TIP_disc()) != SUCCESS) |
return ((INT32) retval); |
else { /* find some other session */ |
NumberOfConnections=NumberOfConnections - 1; |
for (i = 0; i < NumberOfConnections; i++) { |
if ((retval = Mini_TIP_SetCurrSession(Session_ids[i])) == SUCCESS) |
return (retval); |
} |
if (i >= NumberOfConnections) { /* exit DFE */ |
exit_loop = TRUE; |
} |
} |
|
return ((INT32) retval); |
} |
|
INT32 |
create_proc_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
|
retval = Mini_TIP_CreateProc(); |
|
return ((INT32) retval); |
} |
|
INT32 |
capab_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
|
retval = Mini_TIP_Capabilities(); |
|
return ((INT32) retval); |
} |
|
INT32 |
exit_conn_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
int i; |
|
if ((retval = Mini_TIP_exit()) != SUCCESS) {; |
return (retval); |
} else { /* find some other session */ |
NumberOfConnections=NumberOfConnections - 1; |
for (i = 0; i < NumberOfConnections; i++) { |
if ((retval = Mini_TIP_SetCurrSession(Session_ids[i])) == SUCCESS) |
return (retval); |
} |
if (i >= NumberOfConnections) { /* exit DFE */ |
exit_loop = TRUE; |
} |
} |
|
|
return ((INT32) retval); |
} |
|
INT32 |
init_proc_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
|
retval = Mini_send_init_info(&init_info); |
|
return ((INT32) retval); |
} |
|
INT32 |
destroy_proc_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
|
retval = Mini_TIP_DestroyProc(); |
|
return ((INT32) retval); |
} |
|
INT32 |
set_sessionid_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
int sid; |
|
if (tokencnt < 2) |
return (EMSYNTAX); |
|
if (sscanf(token[1],"%d",&sid) != 1) |
return (EMSYNTAX); |
|
retval = Mini_TIP_SetCurrSession(sid); |
|
return ((INT32) retval); |
} |
|
INT32 |
set_pid_cmd(token, tokencnt) |
char **token; |
int tokencnt; |
{ |
INT32 retval; |
int pid; |
|
if (tokencnt < 2) |
return (EMSYNTAX); |
|
if (sscanf(token[1],"%d",&pid) != 1) |
return (EMSYNTAX); |
|
retval = Mini_TIP_SetPID(pid); |
|
return ((INT32) retval); |
} |
|
|
INT32 |
go_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
|
INT32 retval; |
|
if ((retval = Mini_go()) != SUCCESS) { |
return(FAILURE); |
} else { |
GoCmdFlag = 1; |
BlockMode = NONBLOCK; |
if (TipStdinMode & TIP_NBLOCK) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode & TIP_ASYNC) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode == TIP_COOKED) |
io_config.io_control = TERM_USER; |
else { |
TipStdinMode = TIP_COOKED; |
io_config.io_control = TERM_USER; |
} |
io_config.target_running = TRUE; |
return(SUCCESS); |
}; |
|
} /* end go_cmd() */ |
|
/* |
** This command is used to "trace" or step through code. |
** A "t" command with no parameters defaults to a single. |
** step. A "t" command with an integer value following |
** steps for as many instructions as is specified by |
** that integer. |
*/ |
|
INT32 |
trace_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
int result; |
INT32 count; |
INT32 retval; |
|
if (token_count == 1) { |
count = 1; |
} |
else |
if (token_count >= 2) { |
result = get_word(token[1], &count); |
if (result != 0) |
return (EMSYNTAX); |
} |
|
if ((retval = Mini_step(count)) != SUCCESS) { |
return(FAILURE); |
} else { |
GoCmdFlag = 1; |
BlockMode = NONBLOCK; |
if (TipStdinMode & TIP_NBLOCK) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode & TIP_ASYNC) |
io_config.io_control = TERM_29K; |
else if (TipStdinMode == TIP_COOKED) |
io_config.io_control = TERM_USER; |
else { |
TipStdinMode = TIP_COOKED; |
io_config.io_control = TERM_USER; |
} |
io_config.target_running = TRUE; |
return(SUCCESS); |
} |
|
} /* end trace_cmd() */ |
|
/* |
* The "ch0" command is used to send characters (input) to the application |
* program asynchronously. This command deinstalls the control-C handler, |
* sets up input to raw mode, polls the keyboard, sends the bytes to the |
* TIP. The command is exited when Ctrl-U is typed. |
*/ |
|
INT32 |
channel0_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
io_config.io_control = TERM_29K; |
#ifndef MSDOS |
ioctl (fileno(stdin), TCGETA, &NewTermbuf); /* New settings */ |
NewTermbuf.c_lflag &= ~(ICANON); |
NewTermbuf.c_cc[4] = 0; /* MIN */ |
NewTermbuf.c_cc[5] = 0; /* TIME */ |
ioctl (fileno(stdin), TCSETA, &NewTermbuf); /* Set new settings */ |
#endif |
return (0); |
} |
|
/* |
* Only for stdin, not for command file input |
*/ |
INT32 |
Mini_poll_channel0() |
{ |
BYTE ch; |
|
/* read from terminal */ |
#ifdef MSDOS |
/* CBREAK mode */ |
if (kbhit()) { |
ch = (unsigned char) getche(); |
if (io_config.echo_mode == (INT32) TRUE) { |
putc (ch, io_config.echo_file); |
fflush (io_config.echo_file); |
} |
if (ch == (BYTE) TOGGLE_CHAR) { /* Ctrl-U typed, give control back to User */ |
io_config.io_control = TERM_USER; |
display_termuser(); |
return (0); |
} else { |
if (ch == (unsigned char) 13) { /* \r, insert \n */ |
putchar(10); /* line feed */ |
if (io_config.echo_mode == (INT32) TRUE) { |
putc (ch, io_config.echo_file); |
fflush (io_config.echo_file); |
} |
} |
#ifdef MSDOS |
if (ch == (unsigned char) 10) { /* \n, ignore \n */ |
return (0); |
} |
#endif |
Mini_put_stdin((char *)&ch, 1, &io_count_done); |
return (0); |
} |
} |
return(0); |
#else /* Unix */ |
/* |
* Set STDIN to CBREAK mode. For each character read() send it |
* to TIP using Mini_put_stdin(). This is done only if the |
* terminal is controlled by the 29K Target System, i.e. when |
* io_config.io_control == TERM_29K. Otherwise, this function should |
* not be called as it would affect the command-line processing. |
*/ |
/* while ((io_bufsize = read (fileno(stdin), &ch, 1)) == 1) { */ |
if ((io_bufsize = read (fileno(stdin), &ch, 1)) == 1) { |
if (io_config.echo_mode == (INT32) TRUE) { |
putc (ch, io_config.echo_file); |
fflush (io_config.echo_file); |
} |
if (ch == (BYTE) TOGGLE_CHAR) { /* process ctrl-U */ |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /* reset old settings */ |
io_config.io_control = TERM_USER; |
display_termuser(); |
return (0); |
} else { /* send it to TIP */ |
Mini_put_stdin((char *)&ch, 1, &io_count_done); |
} |
} |
return (0); |
#endif |
} /* end Mini_poll_channel0() */ |
|
void |
PrintTrapMsg(num) |
int num; |
{ |
if ((num >= 0) && (num <= 22)) { |
fprintf(stderr, "%s Trap occurred at ", TrapMsg[num]); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%s Trap occurred at ", TrapMsg[num]); |
} else { |
fprintf(stderr, "Trap %d occurred at "); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "Trap %d occurred at "); |
} |
} |
|
void |
display_term29k() |
{ |
fprintf(stderr,"\nTerminal controlled 29K target...Type Ctrl-U <ret> for mondfe prompt\n"); |
fflush (stderr); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(stderr,"\nTerminal controlled 29K target...Type Ctrl-U <ret> for mondfe prompt\n"); |
#ifndef MSDOS |
ioctl (fileno(stdin), TCGETA, &NewTermbuf); /* New settings */ |
NewTermbuf.c_lflag &= ~(ICANON); |
NewTermbuf.c_cc[4] = 0; /* MIN */ |
NewTermbuf.c_cc[5] = 0; /* TIME */ |
ioctl (fileno(stdin), TCSETA, &NewTermbuf); /* Set new settings */ |
#endif |
} |
|
void |
display_termuser() |
{ |
#ifndef MSDOS |
ioctl (fileno(stdin), TCSETA, &OldTermbuf); /*reset settings */ |
#endif |
/* Print a prompt */ |
fprintf(stderr, "\n%s>", ProgramName); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n%s>", ProgramName); |
} |
|
INT32 |
quietmode_off(token, token_count) |
char *token[]; |
int token_count; |
{ |
QuietMode = 0; |
return (0); |
} |
|
INT32 |
quietmode_on(token, token_count) |
char *token[]; |
int token_count; |
{ |
QuietMode = 1; |
return (0); |
} |
|
INT32 |
logoff_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (io_config.log_mode == (INT32) TRUE) { |
io_config.log_mode = (INT32) FALSE; |
(void) fclose(io_config.log_file); |
} |
return (0); |
} |
|
INT32 |
logon_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (io_config.log_mode == (INT32) FALSE) { |
if (strcmp(io_config.log_filename, "\0") != 0) {/* valid file */ |
io_config.log_mode = (INT32) TRUE; |
if ((io_config.log_file = fopen(io_config.log_filename, "a")) == NULL) |
{ |
io_config.log_mode = (INT32) FALSE; |
warning(EMLOGOPEN); |
}; |
} else { |
warning(EMLOGOPEN); |
} |
} |
return (0); |
} |
|
INT32 |
set_logfile(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (token_count < 2) /* insufficient number of args */ |
return (EMSYNTAX); |
|
(void) strcpy ((char *)(&(io_config.log_filename[0])),token[1]); |
|
if (io_config.log_mode == (INT32) TRUE) { /* replace log file used */ |
if ((io_config.log_file = |
fopen (io_config.log_filename, "w")) == NULL) { |
warning (EMLOGOPEN); |
io_config.log_mode = (INT32) FALSE; |
} |
} else { |
io_config.log_mode = (INT32) TRUE; |
if ((io_config.log_file = |
fopen (io_config.log_filename, "w")) == NULL) { |
warning (EMLOGOPEN); |
io_config.log_mode = (INT32) FALSE; |
} |
} |
return (0); |
|
} |
|
INT32 |
echomode_on(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (io_config.echo_mode == (INT32) FALSE) { |
if (strcmp(io_config.echo_filename, "\0") != 0) { /* if valid file in effect */ |
io_config.echo_mode = (INT32) TRUE; |
if ((io_config.echo_file = fopen (io_config.echo_filename, "a")) == NULL) |
{ |
warning (EMECHOPEN); |
io_config.echo_mode = (INT32) FALSE; |
} |
} else |
warning(EMINVECHOFILE); |
} |
return (0); |
} |
|
INT32 |
echomode_off(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (io_config.echo_mode == (INT32) TRUE) { |
io_config.echo_mode = (INT32) FALSE; |
(void) fclose(io_config.echo_file); |
} |
return (0); |
} |
|
INT32 |
echofile_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (token_count < 2) /* insufficient number of args */ |
return (EMSYNTAX); |
|
(void) strcpy ((char *)(&(io_config.echo_filename[0])),token[1]); |
|
if (io_config.echo_mode == (INT32) TRUE) { /* replace echo file used */ |
if ((io_config.echo_file = |
fopen (io_config.echo_filename, "w")) == NULL) { |
warning (EMECHOPEN); |
io_config.echo_mode = (INT32) FALSE; |
} |
} else { |
io_config.echo_mode = (INT32) TRUE; |
if ((io_config.echo_file = |
fopen (io_config.echo_filename, "w")) == NULL) { |
warning (EMECHOPEN); |
io_config.echo_mode = (INT32) FALSE; |
} |
} |
return (0); |
} |
|
INT32 |
cmdfile_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (token_count < 2) |
return (EMSYNTAX); |
|
(void) strcpy((char *)(&(io_config.cmd_filename[0])),token[1]); |
|
if (io_config.cmd_file_io == (INT32) TRUE) { |
warning (EMCMDFILENEST); /* command file nesting not allowed */ |
} else { |
io_config.cmd_file_io = (INT32) TRUE; |
if ((io_config.cmd_file = fopen (io_config.cmd_filename,"r")) == NULL) { |
warning (EMCMDOPEN); |
io_config.cmd_file_io = (INT32) FALSE; |
} else { |
/* MON_STDIN is command file */ |
MON_STDIN = fileno(io_config.cmd_file); /* set MON_STDIN */ |
} |
} |
|
return (0); |
} |
|
INT32 |
tip_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
if (token_count < 2) |
return (EMSYNTAX); |
|
sprintf(tip_cmd_buffer, "%s %s\0", token[0], token[1]); |
|
Mini_put_trans(tip_cmd_buffer); |
|
return (0); |
} |
/help.c
0,0 → 1,594
static char _[] = "@(#)help.c 5.22 93/08/23 15:30:33, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This file contains the help screens for the monitor. |
***************************************************************************** |
*/ |
|
/* |
** Main help |
*/ |
|
char *help_main[] = { |
|
"Use 'h <letter>' for individual command help", |
" ", |
" --------------------- MONDFE Monitor Commands -----------------------------", |
" a - Assemble Instruction | b,b050,bc - Set/Clear/Display Breakpoint", |
" c - Print Configuration | caps - DFE and TIP Capabilities", |
" cp - Create UDI Process | con - Connect to a UDI Debug Session", |
" ch0 - 29K Terminal Control | d,dw,dh,db,df,dd - Dump Memory/Registers", |
" dp - Destroy UDI Process | disc - Temporarily Disconnect UDI Session", |
" ex - Exit UDI Session | esc - Escape to Host Operating System", |
" eon - Turn Echo Mode ON | eoff - Turn Echo Mode OFF", |
" g - Start/Resume Execution | f,fw,fh,ff,fd,fs - Fill Memory/Registers", |
" h - Help Command | init - Initialize Current UDI Process", |
" ix,il - Display Am2903X Cache | k - Kill Running Program on 29K Target", |
" logon - Turn ON log mode | logoff - Turn OFF log mode", |
" l - List/Disassemble Memory | m - Move Data to Memory/Registers", |
" pid - Set UDI Process ID | q - Quit mondfe", |
" qon - Turn Quiet Mode ON | qoff - Turn Quiet Mode OFF", |
" sid - Set UDI Session ID | r - Reset (software reset) 29K Target", |
" t - Trace/Single Step Execution | s,sw,sh,sb,sf,sd - Set Memory/Registers", |
" ver - Montip Version Command | tip - Montip Transparent Mode Command", |
" y - Yank/Download COFF File | xp - Display Protected Special Registers", |
" ze - Echo File For Echo Mode | zc - Execute commands from command file", |
" zl - Use log file for log mode | | - Comment character (in Command File)", |
" ----------------------------------------------------------------------------", |
"" |
}; |
|
|
/* |
** Assemble |
*/ |
|
char *help_a[] = { |
|
"A <address> <instruction>", |
" ", |
"Assemble instructions into memory.", |
" ", |
"The address, is the memory address for the instruction.", |
" ", |
"The instruction will be assembled and placed in memory at the", |
"specified address.", |
" ", |
"Memory addresses:", |
" ", |
"<hex>m - data memory <hex>i - instruction memory", |
"<hex>r - rom memory <hex>u - unspecified (no addr check)", |
"" |
}; |
|
|
/* |
** Breakpoint |
*/ |
|
char *help_b[] = { |
|
"Breakpoint display, set and clear.", |
" ", |
"B - displays valid breakpoints", |
"B <address> [<passcount>] - to set software breakpoint", |
"B050[P,V] <address> [<passcount>] - to set Am29050 hardware breakpoint", |
" When B050P is used, breakpoint is hit only if translation is disabled.", |
" When B050V is used, breakpoint is hit only if translation is enables.", |
"A breakpoint is set at the specified address. An optional", |
"<pass count> sets the pass count. The B050 command sets", |
"a breakpoint using an Am29050 breakpoint register. ", |
"BC <address> - to clear the breakpoint set at <address>", |
"BC - clears all breakpoints.", |
" ", |
"<address> format:", |
" ", |
"<hex>m - data memory <hex>i - instruction memory", |
"<hex>r - rom memory <hex>u - unspecified (no addr check)", |
" B Command usage: B, B050, B050V, B050P", |
"" |
}; |
|
|
/* |
** Configuration help |
*/ |
|
char *help_c[] = { |
|
"C - Prints target system configuration.", |
" ", |
"This command is used to read and display the target configuration.", |
"A banner is printed displaying information about the target.", |
" ", |
" Other C commands: CAPS, CP, CON, CH0", |
"" |
}; |
|
char *help_caps[] = { |
" CAPS - Prints UDI capabilities of DFE and TIP", |
" This prints the DFE version number, TIP version number, and UDI revision.", |
"" |
}; |
|
char *help_cp[] = { |
"CP - Create a UDI Process.", |
" This sends a request to the TIP to create a new process.", |
"" |
}; |
|
char *help_con[] = { |
"CON <session_id>- Requests connection to UDI TIP running <session_id>.", |
" This connects to the debug session specified by <session_id>.", |
"" |
}; |
|
char *help_ch0[] = { |
" CH0 - Transfers control of the terminal to the 29K target.", |
" This is used to transfer control to the 29K target program.", |
" The input characters typed are sent to the TIP without interpreting", |
" for a mondfe command. Control is transferred to mondfe when a Ctrl-U", |
" is typed.", |
"" |
}; |
/* |
** Dump |
*/ |
|
char *help_d[] = { |
|
"D[W|H|B|F|D] [<from_address> [<to_address>]]", |
" ", |
"Display memory or register contents.", |
" ", |
"DW or D - display as words. DF - display in floating point.", |
"DH - display as half-words. DD - display in double precision", |
"DB - display as bytes. floating point.", |
" ", |
"<from_address> defaults to address last displayed. The ", |
"<to_address> is the address of the last data to display. The default", |
"is about eight lines of data.", |
" ", |
"Valid register names:", |
"gr0-gr1, gr64-gr127 - global register names", |
"sr0-sr14, sr128-sr135, sr160-sr162,sr164 - special register names", |
"lr0-lr127 - local register names ", |
"tr0-tr127 - TLB register names ", |
"<address> format:", |
" ", |
"<hex>m - data memory <hex>i - instruction memory", |
"<hex>r - rom memory <hex>u - unspecified (no addr check)", |
" D Command usage: D, DW, DH, DB, DF, DD", |
" Other D Commands: DP, DISC", |
"" |
}; |
|
|
char *help_dp[] = { |
" DP - Destroy process.", |
" This requests the TIP to destroy a UDI process. ", |
"" |
}; |
|
char *help_disc[] = { |
" DISC - Disconnect from the debug session.", |
" This disconnects the DFE from the current debug session. The TIP is", |
" not destroyed and left running for later reconnections.", |
"" |
}; |
/* |
* Escape command |
*/ |
|
char *help_e[] = { |
"ESC", |
" ", |
"Temporarily exit to host operating system.", |
"Use EXIT command to resume debug session.", |
"Other E commands: EON, EOFF", |
"" |
}; |
|
char *help_ex[] = { |
" EX - Exit current debug session.", |
" This command can be used to exit from a debug session when done. Mondfe", |
" looks for another session in progress and connects to that session. If", |
" there are no more debug sessions in progress, this command causes Mondfe", |
" to quit, i.e. it has the same effect as the Quit command", |
"" |
}; |
|
char *help_esc[] = { |
"ESC", |
" ", |
"Temporarily exit to host operating system.", |
"Use EXIT command to resume debug session.", |
"Other E commands: EON, EOFF", |
"" |
}; |
|
char *help_eon[] = { |
" EON and EOFF can be used to turn echo mode ON and OFF during the", |
" interactive debug session. Echo mode is specified by using the -e ", |
" mondfe command line option and an file name. During echo mode, everything", |
" displayed on the screen are captured in the file specified.", |
"" |
}; |
|
/* |
** Fill |
*/ |
|
char *help_f[] = { |
|
"F[W|H|B|F|D] <start address>, <end address>, <value>", |
" ", |
"Fill memory or register contents.", |
" ", |
"FW or F - fill as 32-bit integers | FF - fill as floating point value.", |
"FH - fill as 16-bit integers | FD - fill as double precision", |
"FB - fill as 8-bit integers | floating point value.", |
"FS - fill with the string/pattern given.", |
" ", |
"Valid register names:", |
"gr0-gr1, gr64-gr127 - global register names", |
"sr0-sr14, sr128-sr135, sr160-sr162,sr164 - special register names", |
"lr0-lr127 - local register names ", |
"tr0-tr127 - TLB register names ", |
" ", |
"<address> format:", |
" ", |
"<hex>m - data memory <hex>i - instruction memory", |
"<hex>r - rom memory <hex>u - unspecified (no addr check)", |
" F command usage: F, FW, FH, FB, FD, FS", |
"" |
}; |
|
|
/* |
** Go |
*/ |
|
char *help_g[] = { |
|
"G - Start program execution", |
" ", |
"This resumes program execution at the next instruction.", |
" The program runs either until completion or until it hits a breakpoint", |
" It is used to run the downloaded program and to resume after hitting", |
" a breakpoint. The trace command can be used to execute a specified", |
" number of instructions.", |
"" |
}; |
|
|
/* |
** I (ix, ia, il) |
*/ |
|
char *help_i[] = { |
"IX, IL - Display/Disassemble Am2903X cache registers", |
" ", |
"Display/Disassemble 2903x cache registers by bit field name.", |
" I Commands: IX, IL ", |
" Other I commands: INIT", |
"" |
}; |
|
char *help_init[] = { |
" INIT - Initialize the current process.", |
" This is used to initialize the downloaded program to restart execution", |
" or to reset the target. It resets the target when the current process", |
" ID is set to -1. It does not clear BSS of the downloaded program for ", |
" restart.", |
"" |
}; |
|
/* |
** Help |
*/ |
|
char *help_h[] = { |
|
"H <cmd>", |
" ", |
"Get help for a monitor command", |
" ", |
"This gets help for a particular monitor command. If <cmd>.", |
"is not a valid monitor command the main help screen is listed.", |
" Type <command_name> for help on a particular command.", |
"" |
}; |
|
|
/* |
** Kill |
*/ |
|
char *help_k[] = { |
|
"K - Kill command.", |
" When a K command is issued, the running program on the 29K target", |
" is stopped.", |
"" |
}; |
|
|
/* |
** List (disassemble) |
*/ |
|
char *help_l[] = { |
|
"L [<first_address> [<last_address>]]", |
" ", |
"Disassemble instructions from memory.", |
" ", |
"The <first_address,> if specified, is the memory address for the first", |
"instruction. If no <first_address> is specified, disassembly will begin", |
"from the address in the buffer.", |
" ", |
"The <last_address,> if specified, is the last address to be disassembled.", |
"If no <last_address> is specified, the number of lines of data in the", |
"previous disassemble command will be displayed.", |
" ", |
"<address> format:", |
" ", |
"<hex>m - data memory <hex>i - instruction memory", |
"<hex>r - rom memory <hex>u - unspecified (no addr check)", |
" Other L commands: logon, logoff", |
"" |
}; |
|
char *help_logon[] = { |
" LOGON and LOGOFF commands can be used to turn ON or OFF the log mode", |
" from the mondfe command prompt. WHen log mode is on, every command entered", |
" by the user is logged into the log file specified at invocation or using", |
" the ZL command. When log mode is off, the commands are not logged.", |
"" |
}; |
|
/* |
** Move |
*/ |
|
char *help_m[] = { |
|
"M <source start> <source end> <destination start>", |
" ", |
"Move within memory or registers. Destination will contain exact", |
"copy of original source regardless of overlap. (The source", |
"will be partially altered in the case of overlap.)", |
" ", |
"Valid register names:", |
"gr0-gr1, gr64-gr127 - global register names", |
"sr0-sr14, sr128-sr135, sr160-sr162,sr164 - special register names", |
"lr0-lr127 - local register names ", |
"tr0-tr127 - TLB register names ", |
" ", |
"<address> format :", |
" ", |
"<hex>m - data memory <hex>i - instruction memory", |
"<hex>r - rom memory <hex>u - unspecified (no addr check)", |
"" |
}; |
|
char *help_pid[] = { |
" PID <pid_number> - sets the current UDI process to the <pid_number>", |
" specified.", |
" A <pid_number> of -1 is used to represent the bare machine. This is", |
" is used to access physical addresses, and to reset the target.", |
" Use CP command to create process. Use DP command to destroy process.", |
" Use INIT command to initialize process.", |
"" |
}; |
|
/* |
** Quit |
*/ |
|
char *help_q[] = { |
|
"Q", |
" ", |
"Quit - exit from the monitor.", |
"" |
}; |
|
char *help_qoff[] = { |
" QON and QOFF can be used to turn ON/OFF quiet mode of Mondfe. The -q", |
" command line option of mondfe can be used to invoke mondfe in quiet", |
" mode. In quiet mode, the debug messages are suppressed. These messages", |
" can be turned on anytime during the debug session using the QON command", |
" and turned off using the QOFF command.", |
"" |
}; |
|
|
/* |
** Reset |
*/ |
|
char *help_r[] = { |
|
"R - Reset the target.", |
" This command resets (performs a software reset) of the target. This is", |
" equivalent to setting the UDI process ID to -1, and initializing the", |
" process using INIT.", |
"" |
}; |
|
|
/* |
** Set |
*/ |
|
char *help_s[] = { |
|
"S[W|H|B|F|D] <address> <data>", |
" ", |
"Set memory or register contents.", |
" ", |
"SW or S - set as words. SF - set in floating point.", |
"SH - set as half-words. SD - set in double precision", |
"SB - set as bytes. floating point.", |
" ", |
"<address> indicates location to be set. <Data> is the value", |
"to be set. The data is entered in hexadecimal.", |
" ", |
"Valid register names:", |
"gr0-gr1, gr64-gr127 - global register names", |
"sr0-sr14, sr128-sr135, sr160-sr162,sr164 - special register names", |
"lr0-lr127 - local register names ", |
"tr0-tr127 - TLB register names ", |
" ", |
"<address> format:", |
" ", |
"<hex>m - data memory <hex>i - instruction memory", |
"<hex>r - rom memory <hex>u - unspecified (no addr check)", |
" S command usage: S, SW, SH, SB, SF, SD", |
" Other S command: SID", |
"" |
}; |
|
char *help_sid[] = { |
" SID <sid_number> - sets the UDI session ID to <sid_number>.", |
" This command can be used to set the current debug session when there", |
" is multiple debug sessions going on.", |
"" |
}; |
|
/* |
** Trace |
*/ |
|
char *help_t[] = { |
|
"T <count> - Trace or Step <count> instructions.", |
"Trace allows stepping through code. The optional <count>", |
"allows multiple steps to be taken. The count is in hex.", |
" The default value of <count> is 1. This may not step into", |
" trap handlers based on the target/TIP capabilities.", |
" Other T commands: TIP", |
"" |
}; |
|
char *help_tip[] = { |
" TIP <montip_command> - sends <montip_command> string to montip for execution", |
" The TIP command can be used to inform Montip to change some of its", |
" parameters. The TIP command uses the UDI Transparent mode to pass", |
" the command string. The following TIP commands are now supported:", |
" tip lpt=0", |
" - requests Montip is stop using the parallel port for communicating", |
" to the 29K target - valid for 29K microcontroller targets.", |
" tip lpt=1", |
" - requests Montip to use the parallel port for communicating", |
" to the 29K target - valid for 29K microcontroller targets.", |
" The TIP command can be used before issuing a Y(ank) command to download", |
" a program (COFF) file using the PC parallel port. The parallel port", |
" download capability is only applicable for a PC host. The parallel port", |
" to use MUST be specified as a Montip command line option in the UDI ", |
" configuration file - udiconfs.txt on PC, udi_soc on Unix hosts - using", |
" the -par Montip command line option.", |
" As the parallel port communication is only unidirectional, the serial", |
" communications port - com1, or com2 - must also be specified on Montip", |
" command line in the UDI configuration file.", |
" This command is valid ONLY with MiniMON29K Montip.", |
"" |
}; |
|
/* |
** X |
*/ |
|
char *help_x[] = { |
"XP - Display protected special purpose registers.", |
" ", |
"Display protected special purpose registers by bit field name.", |
"" |
}; |
|
|
/* |
** Yank |
*/ |
|
char *help_y[] = { |
|
"Y [-t|d|l|b] [-noi|-i] [-ms <mstk_x>] [-rs <rstk_x] [fname] [arglist]", |
" ", |
"This is the Yank command to download program (COFF) file to the 29K target.", |
" ", |
"where <fname> is name of a COFF file.", |
" ", |
"<arglist> is the list of command line arguments for the program.", |
" ", |
"-t|d|l|b| gives sections for loading. t->text, d->data, l->lit, b->bss.", |
" ", |
"-noi -> no process created, -i -> download for execute (default).", |
" ", |
"-ms <memstk_hex> -> memory stack size, -rs <regstk_hex> -> reg stack size.", |
" ", |
"Ex: y -db hello.pcb arg1 arg2, loads only the DATA and LIT sections.", |
" ", |
"Simply typing Y will use args from the previous Y issued.", |
" ", |
" See the TIP command for downloading using parallel port", |
"" |
}; |
|
|
char *help_zc[] = { |
" ZC <cmdfile_name> - execute commands from the <cmdfile_name> command file", |
" The ZC command can be used to execute a series of Mondfe commands", |
" out of a command file. The <cmdfile_name> is the name of the file", |
" containing the command input. This command can be executed at the", |
" mondfe> prompt. When all the commands from the file are executed, the", |
" mondfe> prompt appears again.", |
" Nesting of command files is not allowed.", |
" ", |
" Other Z commands: ZE, ZL", |
"" |
}; |
|
char *help_ze[] = { |
" ZE <echofile_name> - turns ECHO mode ON and specifies the echo file", |
" When echo mode is on, everything that is displayed on the screen is ", |
" also written into a file, the echo file. The <echofile_name> string ", |
" specifies the file name of the echo file to use.", |
"" |
}; |
|
char *help_zl[] = { |
" ZL <logfile_name> - turns LOG mode ON and specifies the log file to use", |
" When log mode is on, every mondfe command entered by the user is logged", |
" in the log file. The log file thus created can be directly used an an", |
" input command file for subsequent debug session to repeat the same sequence", |
" of commands. Log mode can be turned on or off using logon or logoff command", |
"" |
}; |
/error.c
0,0 → 1,122
static char _[] = "@(#)error.c 5.20 93/07/30 16:38:29, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This file defines the error and warning messages in the |
** monitor. The error codes which correspond to the messages |
** are defined in the error.h header file. |
***************************************************************************** |
*/ |
|
|
char *error_msg[] = { |
|
/* 0 */ "Dummy error message (0).", |
|
/* 1 (EMUSAGE) */ |
" Valid command-line options are:\n\ |
[-D] - to invoke in interactive debug mode\n\ |
-TIP <tip_id_from_udi_config_file> - MUST specify the TIP to use\n\ |
[-e <echo_ filename_for_script>] - to capture session in a file\n\ |
[-w] - specifies how long to wait, -1 means WaitForever, default 10000\n\ |
[-q] - to suppress download messages\n\ |
[-le] - to specify little endian target (default is BIG)\n\ |
[-c <input_cmd_filename>] - to specify command file for input\n\ |
[-ms <mem_stack_size_in_hex> ] - memory stack size to be used for appln\n\ |
[-rs <reg_stack_size_in_hex> ] - register stack size to be used for appln\n\ |
[-log <log_filename>] - file to log debug session\n\ |
[[<pgm>] [<pgm_args>]] - program and its optional arg list\n", |
/* 2 */ "EMFAIL: Unrecoverable error.", |
/* 3 */ "EMBADADDR: Illegal address.", |
/* 4 */ "EMBADREG: Illegal register.", |
/* 5 */ "EMSYNTAX: Illegal command syntax.", |
/* 6 */ "EMACCESS: Could not access memory.", |
/* 7 */ "EMALLOC: Could not allocate memory.", |
/* 8 */ "EMTARGET: Unknown target type.", |
/* 9 */ "EMHINIT: Could not initialize host.", |
/* 10 */ "EMCOMM: Could not open communication channel.", |
|
/* 11 */ "EMBADMSG: Unknown message type.", |
/* 12 */ "EMMSG2BIG: Message too large for buffer.", |
|
/* 13 */ "EMRESET: Could not RESET target.", |
/* 14 */ "EMCONFIG: Could not get target CONFIG.", |
/* 15 */ "EMSTATUS: Could not get target STATUS.", |
/* 16 */ "EMREAD: Could not READ target memory.", |
/* 17 */ "EMWRITE: Could not WRITE target memory.", |
/* 18 */ "EMBKPTSET: Could not set breakpoint.", |
/* 19 */ "EMBKPTRM: Could not remove breakpoint.", |
/* 20 */ "EMBKPTSTAT: Could not get breakpoint status.", |
/* 21 */ "EMBKPTNONE: All breakpoints in use.", |
/* 22 */ "EMBKPTUSED: Breakpoint already in use", |
/* 23 */ "EMCOPY: Could not COPY target memory.", |
/* 24 */ "EMFILL: Could not FILL target memory.", |
/* 25 */ "EMINIT: Could not initialize target memory.", |
/* 26 */ "EMGO: Could not start execution.", |
/* 27 */ "EMSTEP: Could not single step.", |
/* 28 */ "EMBREAK: Could not BREAK execution.", |
/* 29 */ "EMHIF: Could not perform HIF service.", |
/* 30 */ "EMCHANNEL0: Could not read CHANNEL0.", |
/* 31 */ "EMCHANNEL1: Could not write CHANNEL1.", |
/* 32 */ "EMOPEN: Could not open COFF file.", |
/* 33 */ "EMHDR: Could not read COFF header.", |
/* 34 */ "EMMAGIC: Bad COFF file magic number.", |
/* 35 */ "EMAOUT: Could not read COFF a.out header.", |
/* 36 */ "EMSCNHDR: Could not read COFF section header.", |
/* 37 */ "EMSCN: Could not read COFF section.", |
/* 38 */ "EMCLOSE: Could not close COFF file.", |
/* 39 */ "EMLOGOPEN: Could not open log file.", |
/* 40 */ "EMLOGREAD: Could not read log file.", |
/* 41 */ "EMLOGWRITE: Could not write log file.", |
/* 42 */ "EMLOGCLOSE: Could not close log file.", |
/* 43 */ "EMCMDOPEN: Could not open command file.", |
/* 44 */ "EMCMDREAD: Could not read comand file.", |
/* 45 */ "EMCMDWRITE: Could not write command file.", |
/* 46 */ "EMCMDCLOSE: Could not close command file.", |
/* 47 */ "EMTIMEOUT: Host timed out waiting for a message.", |
/* 48 */ "EMCOMMTYPE: A '-t' flag must be specified.", |
/* 49 */ "EMCOMMERR: Communication error.", |
/* 50 */ "EMBAUD: Invalid baud rate specified.", |
/* 51 */ "EMTIPINIT: TIP initialization failed. Exiting TIP.", |
/* 52 */ "EMIOSETF: Host I/O setup failure.", |
/* 53 */ "EMIORESETF: Host I/O reset failure.", |
/* 54 */ "EMLOADF: Loading COFF file failure.", |
/* 55 */ "EMNOFILE: No program to run.", |
/* 56 */ "EMECHOPEN: Could not open echo file.", |
/* 57 */ "EMCTRLC: Ctrl-C interrupt. Exiting.", |
/* 58 */ "EMNOSUCHCMD: Unrecognized command.", |
/* 59 */ "EMNOPROCESS: Failed creating process zero.", |
/* 60 */ "EMNOTCOMP: DFE and TIP versions not compatible.", |
/* 61 */ "EMFATAL: No session in progress.", |
/* 62 */ "EMNOINITP: (-n) No process initialized for downloaded program.", |
/* 63 */ "EMDOSERR: DOS error. Cannot escape to DOS.", |
/* 64 */ "EMSYSERR: System error. Cannot escape to host OS.", |
/* 65 */ "EMINCECHOFILE: Invalid echo file. Cannot enable echo.", |
/* 66 */ "EMCMDFILENEST: Nesting of command files not allowed." |
}; |
|
|
/set.c
0,0 → 1,215
static char _[] = "@(#)set.c 5.20 93/07/30 16:39:00, Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This code provides "set" routines to set memory and |
** registers. Data may be set as words (32 bit), half-words |
** (16 bit), bytes (8 bit), float (32 bit floating point) or |
** double (64 bit floating point). |
** |
** Since registers are 32 bits long, the set byte and set half |
** commands will only be permitted for memory accesses. |
***************************************************************************** |
*/ |
|
|
#include <stdio.h> |
#include <ctype.h> |
#include <memory.h> |
#include "main.h" |
#include "monitor.h" |
#include "miniint.h" |
#include "memspcs.h" |
#include "macros.h" |
#include "error.h" |
|
|
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
#else |
#include <string.h> |
|
#endif |
|
int get_addr_29k PARAMS((char *, struct addr_29k_t *)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
|
int get_word PARAMS((char *, INT32 *)); |
int get_half PARAMS((char *, INT16 *)); |
int get_byte PARAMS((char *, BYTE *)); |
int get_float PARAMS((char *, float *)); |
int get_double PARAMS((char *, double *)); |
|
int set_data PARAMS((BYTE *, BYTE *, int)); |
|
/* |
** The function below is used in setting data. This function is |
** called in the main command loop parser of the monitor. The |
** parameters passed to this function are: |
** |
** token - This is an array of pointers to strings. Each string |
** referenced by this array is a "token" of the user's |
** input, translated to lower case. |
** |
** token_count - This is the number of items in the token array. |
** |
** This function reduces the tokens to three parameters: |
** memory_space, address and the data to be set. This data |
** is one of the "temp_" variables. |
** |
*/ |
|
|
INT32 |
set_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
INT16 size; |
int result; |
struct addr_29k_t addr_29k; |
int set_format; |
INT32 temp_word; |
INT16 temp_half; |
BYTE temp_byte; |
float temp_float; |
double temp_double; |
|
INT32 retval; |
BYTE write_buffer[16]; /* */ |
INT32 bytes_ret; |
INT32 hostendian; /* UDI conformant */ |
INT32 count; |
|
|
if (token_count != 3) { |
return (EMSYNTAX); |
} |
|
/* |
** What is the data format? |
*/ |
|
count = (INT32) 1; |
if ((strcmp(token[0], "s") == 0) || |
(strcmp(token[0], "sw") == 0)) { |
set_format = WORD_FORMAT; |
size = (INT16) sizeof(INT32); |
result = get_word(token[2], &temp_word); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(write_buffer, (BYTE *)&temp_word, sizeof(INT32)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "sh") == 0) { |
set_format = HALF_FORMAT; |
size = (INT16) sizeof(INT16); |
result = get_half(token[2], &temp_half); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(write_buffer, (BYTE *)&temp_half, sizeof(INT16)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "sb") == 0) { |
set_format = BYTE_FORMAT; |
size = (INT16) sizeof(BYTE); |
result = get_byte(token[2], &temp_byte); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(write_buffer, (BYTE *)&temp_byte, sizeof(BYTE)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "sf") == 0) { |
set_format = FLOAT_FORMAT; |
size = (INT16) sizeof(float); |
result = get_float(token[2], &temp_float); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(write_buffer, (BYTE *)&temp_float, sizeof(float)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
if (strcmp(token[0], "sd") == 0) { |
set_format = DOUBLE_FORMAT; |
size = (INT16) sizeof(double); |
result = get_double(token[2], &temp_double); |
if (result != 0) |
return (EMSYNTAX); |
result = set_data(write_buffer, (BYTE *)&temp_double, sizeof(double)); |
if (result != 0) |
return (EMSYNTAX); |
} |
else |
return(EMSYNTAX); |
|
/* |
** Get address |
*/ |
|
result = get_addr_29k(token[1], &addr_29k); |
if (result != 0) |
return (EMSYNTAX); |
result = addr_29k_ok(&addr_29k); |
if (result != 0) |
return (result); |
|
/* |
** We don't set bytes or half words in registers |
*/ |
|
if (((ISREG(addr_29k.memory_space)) && |
(set_format == BYTE_FORMAT)) || |
|
((ISREG(addr_29k.memory_space)) && |
(set_format == HALF_FORMAT))) |
return (EMSYNTAX); |
|
/* Will the data overflow the message buffer? Done in TIP */ |
|
hostendian = FALSE; |
if ((retval = Mini_write_req (addr_29k.memory_space, |
addr_29k.address, |
count, |
(INT16) size, |
&bytes_ret, |
write_buffer, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
} else |
return(SUCCESS); |
|
} /* end set_cmd() */ |
|
|
/xcmd.c
0,0 → 1,582
static char _[] = "@(#)xcmd.c 5.20 93/07/30 16:39:02, Srini, AMD"; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This code implements a subset of the MON29K-like "x" |
** commands. |
***************************************************************************** |
*/ |
|
|
#include <stdio.h> |
#include <ctype.h> |
#include <memory.h> |
#include "main.h" |
#include "macros.h" |
#include "miniint.h" |
#include "memspcs.h" |
#include "error.h" |
|
|
#ifdef MSDOS |
#include <stdlib.h> |
#include <string.h> |
#else |
#include <string.h> |
#endif |
|
INT32 xp_cmd PARAMS((char **, int)); |
INT32 xc_cmd PARAMS((char **, int)); |
|
int get_addr_29k PARAMS((char *, struct addr_29k_t *)); |
int addr_29k_ok PARAMS((struct addr_29k_t *)); |
int print_addr_29k PARAMS((INT32, ADDR32)); |
int get_word PARAMS((char *buffer, INT32 *data_word)); |
void convert32 PARAMS(( BYTE *byte)); |
|
void dasm_instr PARAMS((ADDR32, struct instr_t *)); |
|
/* Variable definitions */ |
struct xp_cmd_t { |
INT32 vtb; |
INT32 ops; |
INT32 cps; |
INT32 cfg; |
INT32 cha; |
INT32 chd; |
INT32 chc; |
INT32 rbp; |
INT32 tmc; |
INT32 tmr; |
INT32 pc0; |
INT32 pc1; |
INT32 pc2; |
INT32 mmuc; |
INT32 lru; |
}; |
#define XP_CMD_SZ 15 * sizeof (INT32) |
/* #define XP_CMD_SZ sizeof(struct xp_cmd_t) */ |
|
/* |
** The function below is used to implement the MON29K-like |
** "x" commands. the function below, x_cmd() is called |
** in the main command loop parser of the monitor. The |
** parameters passed to this function are: |
** |
** token - This is an array of pointers to strings. Each string |
** referenced by this array is a "token" of the user's |
** input, translated to lower case. |
** |
** token_count - This is the number of tokens in "token". |
** |
** This function then calls the specific "x" commands, |
** such as "xp" or "xc". |
*/ |
|
|
INT32 |
x_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
INT32 result; |
|
if (strcmp(token[0], "xp") == 0) |
result = xp_cmd(token, token_count); |
else |
if (strcmp(token[0], "xc") == 0) |
result = xc_cmd(token, token_count); |
else |
result = EMSYNTAX; |
|
return (result); |
} /* end xcmd() */ |
|
|
/* |
** This command is used to print out formatted information |
** about protected special registers. The format is borrowed |
** from MON29K, and produces a full screen of data, giving |
** bit fields of the various registers. |
*/ |
|
INT32 |
xp_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
INT32 byte_count; |
int prl; |
INT32 vtb; |
INT32 ops; |
INT32 cps; |
INT32 cfg; |
INT32 cha; |
INT32 chd; |
INT32 chc; |
INT32 rbp; |
INT32 tmc; |
INT32 tmr; |
INT32 pc0; |
INT32 pc1; |
INT32 pc2; |
INT32 mmuc; |
INT32 lru; |
|
INT32 retval; |
INT32 bytes_ret; |
INT32 hostendian; |
union { |
struct xp_cmd_t xp_cmd; |
char read_buffer[XP_CMD_SZ]; |
} xp_cmd_val; |
char prtbuf[256]; |
|
if ((strcmp(token[0], "xp") != 0) || |
(token_count != 1)) |
return (EMSYNTAX); |
|
/* |
** Get data |
*/ |
|
byte_count = XP_CMD_SZ; |
|
/* Will the data overflow the message buffer? Done in TIP */ |
|
hostendian = FALSE; |
if ((retval = Mini_read_req (SPECIAL_REG, |
(ADDR32) 0, |
byte_count/4, |
(INT16) 4, /* size */ |
&bytes_ret, |
xp_cmd_val.read_buffer, |
hostendian)) != SUCCESS) { |
return(FAILURE); |
}; |
/* The following is executed if SUCCESSful */ |
vtb = xp_cmd_val.xp_cmd.vtb; |
ops = xp_cmd_val.xp_cmd.ops; |
cps = xp_cmd_val.xp_cmd.cps; |
cfg = xp_cmd_val.xp_cmd.cfg; |
cha = xp_cmd_val.xp_cmd.cha; |
chd = xp_cmd_val.xp_cmd.chd; |
chc = xp_cmd_val.xp_cmd.chc; |
rbp = xp_cmd_val.xp_cmd.rbp; |
tmc = xp_cmd_val.xp_cmd.tmc; |
tmr = xp_cmd_val.xp_cmd.tmr; |
pc0 = xp_cmd_val.xp_cmd.pc0; |
pc1 = xp_cmd_val.xp_cmd.pc1; |
pc2 = xp_cmd_val.xp_cmd.pc2; |
mmuc = xp_cmd_val.xp_cmd.mmuc; |
lru = xp_cmd_val.xp_cmd.lru; |
|
if (host_config.host_endian != host_config.target_endian) { |
convert32((BYTE *)&vtb); |
convert32((BYTE *)&ops); |
convert32((BYTE *)&cps); |
convert32((BYTE *)&cfg); |
convert32((BYTE *)&cha); |
convert32((BYTE *)&chd); |
convert32((BYTE *)&chc); |
convert32((BYTE *)&rbp); |
convert32((BYTE *)&tmc); |
convert32((BYTE *)&tmr); |
convert32((BYTE *)&pc0); |
convert32((BYTE *)&pc1); |
convert32((BYTE *)&pc2); |
convert32((BYTE *)&mmuc); |
convert32((BYTE *)&lru); |
} |
|
|
/* Print CPS */ |
sprintf(&prtbuf[0], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], " TD MM CA IP TE TP TU FZ LK RE WM PD PI SM IM DI DA\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "CPS:"); |
sprintf(&prtbuf[strlen(prtbuf)], " %3x", ((cps >> 17) & 0x01)); /* td */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 16) & 0x01)); /* mm */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 15) & 0x01)); /* ca */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 14) & 0x01)); /* ip */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 13) & 0x01)); /* te */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 12) & 0x01)); /* tp */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 11) & 0x01)); /* tu */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 10) & 0x01)); /* fz */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 9) & 0x01)); /* lk */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 8) & 0x01)); /* re */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 7) & 0x01)); /* wm */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 6) & 0x01)); /* pd */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 5) & 0x01)); /* pi */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 4) & 0x01)); /* sm */ |
|
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 2) & 0x03)); /* im */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 1) & 0x01)); /* di */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cps >> 0) & 0x01)); /* da */ |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Print OPS */ |
sprintf(&prtbuf[0], "OPS:"); |
sprintf(&prtbuf[strlen(prtbuf)], " %3x", ((ops >> 17) & 0x01)); /* td */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 16) & 0x01)); /* mm */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 15) & 0x01)); /* ca */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 14) & 0x01)); /* ip */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 13) & 0x01)); /* te */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 12) & 0x01)); /* tp */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 11) & 0x01)); /* tu */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 10) & 0x01)); /* fz */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 9) & 0x01)); /* lk */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 8) & 0x01)); /* re */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 7) & 0x01)); /* wm */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 6) & 0x01)); /* pd */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 5) & 0x01)); /* pi */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 4) & 0x01)); /* sm */ |
|
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 2) & 0x03)); /* im */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 1) & 0x01)); /* di */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((ops >> 0) & 0x01)); /* da */ |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Get Processor Revision Number */ |
prl = (int) ((cfg >> 24) & 0xff); |
|
/* Print VAB / CFG */ |
if (PROCESSOR(prl) == PROC_AM29030) { |
sprintf(&prtbuf[0], " VAB CFG: PRL PMB IL ID VF BO\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "%08lx ", vtb); |
sprintf(&prtbuf[strlen(prtbuf)], "%02lx", ((cfg >> 24) & 0xff)); /* prl */ |
sprintf(&prtbuf[strlen(prtbuf)], "%4x", ((cfg >> 16) & 0x03)); /* pmb */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 9) & 0x03)); /* il */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 8) & 0x01)); /* id */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 4) & 0x01)); /* vf */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 2) & 0x01)); /* bo */ |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
} |
else { /* Am29000 or Am29050 */ |
sprintf(&prtbuf[0], " VAB CFG: PRL DW VF RV BO CP CD\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "%08lx ", vtb); |
sprintf(&prtbuf[strlen(prtbuf)], "%02lx", ((cfg >> 24) & 0xff)); /* prl */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 5) & 0x01)); /* dw */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 4) & 0x01)); /* vf */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 3) & 0x01)); /* rv */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 2) & 0x01)); /* bo */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 1) & 0x01)); /* cp */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((cfg >> 0) & 0x01)); /* cd */ |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
} |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Print CHA / CHD / CHC */ |
sprintf(&prtbuf[0], " CHA CHD CHC: CE CNTL CR LS ML ST LA TF TR NN CV\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "%08lx ", cha); /* cha */ |
sprintf(&prtbuf[strlen(prtbuf)], "%08lx ", chd); /* chd */ |
sprintf(&prtbuf[strlen(prtbuf)], "%2x", ((chc >> 31) & 0x01)); /* ce */ |
sprintf(&prtbuf[strlen(prtbuf)], "%5x", ((chc >> 24) & 0xff)); /* cntl */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 16) & 0xff)); /* cr */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 15) & 0x01)); /* ls */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 14) & 0x01)); /* ml */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 13) & 0x01)); /* st */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 12) & 0x01)); /* la */ |
|
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 10) & 0x01)); /* tf */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 2) & 0xff)); /* tr */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 1) & 0x01)); /* nn */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((chc >> 0) & 0x01)); /* cv */ |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Print RBP */ |
sprintf(&prtbuf[0], "RBP: BF BE BD BC BB BA B9 B8 B7 B6 B5 B4 B3 B2 B1 B0\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], " %3x", ((rbp >> 15) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 14) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 13) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 12) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 11) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 10) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 9) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 8) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 7) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 6) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 5) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 4) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 3) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 2) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 1) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((rbp >> 0) & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Print TMC / TMR / PC0 / PC1 / PC2 */ |
sprintf(&prtbuf[0], " TCV TR: OV IN IE TRV PC0 PC1 PC2\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "%06lx", (tmc & 0x00ffffff)); /* tcv */ |
sprintf(&prtbuf[strlen(prtbuf)], "%5x", ((tmr >> 26) & 0x01)); /* ov */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((tmr >> 25) & 0x01)); /* in */ |
sprintf(&prtbuf[strlen(prtbuf)], "%3x", ((tmr >> 24) & 0x01)); /* ie */ |
sprintf(&prtbuf[strlen(prtbuf)], " %06lx", (tmr & 0x00ffffff)); /* trv */ |
sprintf(&prtbuf[strlen(prtbuf)], " %08lx", pc0); /* pc0 */ |
sprintf(&prtbuf[strlen(prtbuf)], " %08lx", pc1); /* pc1 */ |
sprintf(&prtbuf[strlen(prtbuf)], " %08lx", pc2); /* pc2 */ |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Print MMUC / LRU */ |
sprintf(&prtbuf[0], "MMU: PS PID LRU\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], " %02x", ((mmuc >> 8) & 0x03)); /* ps */ |
sprintf(&prtbuf[strlen(prtbuf)], " %02x", (mmuc & 0xff)); /* pid */ |
sprintf(&prtbuf[strlen(prtbuf)], " %02x", (lru & 0xff)); /* lru */ |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
return (0); |
|
} /* end xp_cmd() */ |
|
|
|
/* |
** This command is used to examine the contents of the cache |
** in the Am29030. First set 0 is printed, starting with the |
** tag, followed by a disassembly of four instructions in |
** the set. Set 1 for the line follows similarly. |
** |
** The data comes in from the READ_ACK message in the following |
** order: |
** |
** tag (data[0-3] (set 0) |
** instr1 (data[4-7] |
** instr1 (data[8-11] |
** instr1 (data[12-15] |
** instr1 (data[16-19] |
** |
** tag (data[20-23] (set 1) |
** instr1 (data[24-27] |
** instr1 (data[28-31] |
** instr1 (data[32-35] |
** instr1 (data[36-39] |
*/ |
|
INT32 |
xc_cmd(token, token_count) |
char *token[]; |
int token_count; |
{ |
static INT32 memory_space=I_CACHE; |
static ADDR32 cache_line=0; |
static INT32 byte_count=(10*sizeof(INST32)); |
static INT32 count=1; |
ADDR32 address; |
INT32 i; |
int j; |
int set; |
int index; |
int result; |
struct instr_t instr; |
INT32 cache_line_start; |
INT32 cache_line_end; |
|
INT32 retval; |
INT32 bytes_ret; |
INT32 host_endian; |
BYTE read_buffer[10*sizeof(INST32)]; |
char prtbuf[256]; |
|
|
/* Is it an 'xc' command? */ |
if (strcmp(token[0], "xc") != 0) |
return (EMSYNTAX); |
|
/* |
** Parse parameters |
*/ |
|
if (token_count == 1) { |
cache_line = cache_line + count; |
} |
else |
if (token_count == 2) { |
result = get_word(token[1], &cache_line_start); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_start < 0) || |
(cache_line_start >255)) |
return (EMBADADDR); |
cache_line = cache_line_start; |
} |
else |
if (token_count == 3) { |
/* Get first cache line to be dumped */ |
result = get_word(token[1], &cache_line_start); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_start < 0) || |
(cache_line_start > 255)) |
return (EMBADADDR); |
/* Get last cache line to be dumped */ |
result = get_word(token[2], &cache_line_end); |
if (result != 0) |
return (EMSYNTAX); |
if ((cache_line_end < 0) || |
(cache_line_end > 255)) |
return (EMBADADDR); |
if (cache_line_start > cache_line_end) |
return (EMBADADDR); |
cache_line = cache_line_start; |
count = (cache_line_end - cache_line_start) + 1; |
} |
else |
/* Too many args */ |
return (EMSYNTAX); |
|
i = 0; |
while (i < count) { |
|
host_endian = FALSE; |
if ((retval = Mini_read_req(memory_space, |
(cache_line + i), |
byte_count/4, |
(INT16) 4, /* size */ |
&bytes_ret, |
read_buffer, |
host_endian)) != SUCCESS) { |
return(FAILURE); |
}; |
/* The following is executed if SUCCESSful */ |
|
for (set=0; set<2; set++) { |
|
/* Print out formatted address tag and status information */ |
index = (set * 20); |
sprintf(&prtbuf[0], "\n"); |
sprintf(&prtbuf[strlen(prtbuf)], "Cache line 0x%lx, set %d.\n", (int) (cache_line+i), set); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "IATAG V P US\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
sprintf(&prtbuf[0], "%02x%02x%1x %1x %1x %1x\n", |
read_buffer[index], |
read_buffer[index + 1], |
((read_buffer[index + 2] >> 4) & 0x0f), |
((read_buffer[index + 3] >> 2) & 0x01), |
((read_buffer[index + 3] >> 1) & 0x01), |
(read_buffer[index + 3] & 0x01)); |
sprintf(&prtbuf[strlen(prtbuf)], "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf (io_config.echo_file, "%s", &prtbuf[0]); |
fprintf (stderr, "%s", &prtbuf[0]); |
|
/* Address = IATAG + line_number + <16 byte adddress> */ |
address = ((read_buffer[index] << 24) | |
(read_buffer[index + 1] << 16) | |
(read_buffer[index + 2] << 8) | |
((cache_line+i) << 4)); |
|
/* Disassemble four words */ |
for (j=0; j<4; j=j+1) { |
index = (set * 20) + ((j+1) * sizeof(INT32)); |
instr.op = read_buffer[index]; |
instr.c = read_buffer[index + 1]; |
instr.a = read_buffer[index + 2]; |
instr.b = read_buffer[index + 3]; |
|
/* Print address of instruction (in hex) */ |
address = (address & 0xfffffff0); /* Clear low four bits */ |
address = (address | (j << 2)); |
fprintf(stderr, "%08lx ", address); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%08lx ", address); |
|
/* Print instruction (in hex) */ |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
fprintf(stderr, "%02x%02x%02x%02x ", instr.op, instr.c, |
instr.a, instr.b); |
|
/* Disassemble instruction */ |
dasm_instr(address, &instr); |
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
} /* end for(j) */ |
|
fprintf(stderr, "\n"); |
if (io_config.echo_mode == (INT32) TRUE) |
fprintf(io_config.echo_file, "\n"); |
|
} /* end for(set) */ |
|
i = i + 1; |
|
} /* end while loop */ |
|
return (0); |
|
} /* end xc_cmd() */ |
|
|
/opcodes.c
0,0 → 1,137
static char _[] = "@(#)opcodes.c 5.21 93/08/10 17:46:46,Srini, AMD."; |
/****************************************************************************** |
* Copyright 1991 Advanced Micro Devices, Inc. |
* |
* This software is the property of Advanced Micro Devices, Inc (AMD) which |
* specifically grants the user the right to modify, use and distribute this |
* software provided this notice is not removed or altered. All other rights |
* are reserved by AMD. |
* |
* AMD MAKES NO WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, WITH REGARD TO THIS |
* SOFTWARE. IN NO EVENT SHALL AMD BE LIABLE FOR INCIDENTAL OR CONSEQUENTIAL |
* DAMAGES IN CONNECTION WITH OR ARISING FROM THE FURNISHING, PERFORMANCE, OR |
* USE OF THIS SOFTWARE. |
* |
* So that all may benefit from your experience, please report any problems |
* or suggestions about this software to the 29K Technical Support Center at |
* 800-29-29-AMD (800-292-9263) in the USA, or 0800-89-1131 in the UK, or |
* 0031-11-1129 in Japan, toll free. The direct dial number is 512-462-4118. |
* |
* Advanced Micro Devices, Inc. |
* 29K Support Products |
* Mail Stop 573 |
* 5900 E. Ben White Blvd. |
* Austin, TX 78741 |
* 800-292-9263 |
***************************************************************************** |
* Engineer: Srini Subramanian. |
***************************************************************************** |
** This file contains a data structure which gives the ASCII |
** string associated with each Am29000 opcode. These strings |
** are all in lower case. The string associated with illegal |
** opcodes are null (""). Opcodes are sorted in numerical |
** order. |
** |
***************************************************************************** |
*/ |
char *opcode_name[] = |
{ |
|
/* Opcodes 0x00 to 0x0F */ |
"", "constn ", "consth ", "const ", |
"mtsrim ", "consthz ", "loadl ", "loadl ", |
"clz ", "clz ", "exbyte ", "exbyte ", |
"inbyte ", "inbyte ", "storel ", "storel ", |
|
/* Opcodes 0x10 to 0x1F */ |
"adds ", "adds ", "addu ", "addu ", |
"add ", "add ", "load ", "load ", |
"addcs ", "addcs ", "addcu ", "addcu ", |
"addc ", "addc ", "store ", "store ", |
|
/* Opcodes 0x20 to 0x2F */ |
"subs ", "subs ", "subu ", "subu ", |
"sub ", "sub ", "loadset ", "loadset ", |
"subcs ", "subcs ", "subcu ", "subcu ", |
"subc ", "subc ", "cpbyte ", "cpbyte ", |
|
/* Opcodes 0x30 to 0x3F */ |
"subrs ", "subrs ", "subru ", "subru ", |
"subr ", "subr ", "loadm ", "loadm ", |
"subrcs ", "subrcs ", "subrcu ", "subrcu ", |
"subrc ", "subrc ", "storem ", "storem ", |
|
/* Opcodes 0x40 to 0x4F */ |
"cplt ", "cplt ", "cpltu ", "cpltu ", |
"cple ", "cple ", "cpleu ", "cpleu ", |
"cpgt ", "cpgt ", "cpgtu ", "cpgtu ", |
"cpge ", "cpge ", "cpgeu ", "cpgeu ", |
|
/* Opcodes 0x50 to 0x5F */ |
"aslt ", "aslt ", "asltu ", "asltu ", |
"asle ", "asle ", "asleu ", "asleu ", |
"asgt ", "asgt ", "asgtu ", "asgtu ", |
"asge ", "asge ", "asgeu ", "asgeu ", |
|
/* Opcodes 0x60 to 0x6F */ |
"cpeq ", "cpeq ", "cpneq ", "cpneq ", |
"mul ", "mul ", "mull ", "mull ", |
"div0 ", "div0 ", "div ", "div ", |
"divl ", "divl ", "divrem ", "divrem ", |
|
/* Opcodes 0x70 to 0x7F */ |
"aseq ", "aseq ", "asneq ", "asneq ", |
"mulu ", "mulu ", "", "", |
"inhw ", "inhw ", "extract ", "extract ", |
"exhw ", "exhw ", "exhws ", "", |
|
/* Opcodes 0x80 to 0x8F */ |
"sll ", "sll ", "srl ", "srl ", |
"", "", "sra ", "sra ", |
"iret ", "halt ", "", "", |
"iretinv ", "", "", "", |
|
/* Opcodes 0x90 to 0x9F */ |
"and ", "and ", "or ", "or ", |
"xor ", "xor ", "xnor ", "xnor ", |
"nor ", "nor ", "nand ", "nand ", |
"andn ", "andn ", "setip ", "inv ", |
|
/* Opcodes 0xA0 to 0xAF */ |
"jmp ", "jmp ", "", "", |
"jmpf ", "jmpf ", "", "", |
"call ", "call ", "orn ", "orn ", |
"jmpt ", "jmpt ", "", "", |
|
/* Opcodes 0xB0 to 0xBF */ |
"", "", "", "", |
"jmpfdec ", "jmpfdec ", "mftlb ", "", |
"", "", "", "", |
"", "", "mttlb ", "", |
|
/* Opcodes 0xC0 to 0xCF */ |
"jmpi ", "", "", "", |
"jmpfi ", "", "mfsr ", "", |
"calli ", "", "", "", |
"jmpti ", "", "mtsr ", "", |
|
/* Opcodes 0xD0 to 0xDF */ |
"", "", "", "", |
"", "", "", "emulate ", |
"", "", "", "", |
"", "", "multm ", "multmu ", |
|
/* Opcodes 0xE0 to 0xEF */ |
"multiply", "divide ", "multiplu", "dividu ", |
"convert ", "sqrt ", "class ", "", |
"", "", "feq ", "deq ", |
"fgt ", "dgt ", "fge ", "dge ", |
|
/* Opcodes 0xF0 to 0xFF */ |
"fadd ", "dadd ", "fsub ", "dsub ", |
"fmul ", "dmul ", "fdiv ", "ddiv ", |
"", "fdmul ", "", "", |
"", "", "", "" |
}; |
|
|