/*
*****************************************************************
*name: IE_egwu_monitor.h
*author: Samuel Igwe
*date: 12/03/2015
*description: IE_egwu_monitor program/command interpreter header.
*****************************************************************
*/
#ifndef IE_EGWU_MONITOR_H
#define IE_EGWU_MONITOR_H
#include "chip.h"
#include "chip_lpc177x_8x.h"
#include "uart_17xx_40xx.h"
#include "IE_egwu_uartio.h"
/*
*************************************************************
*support variables
*************************************************************
*/
enum {
MON_ERROR_CMD=0,
MON_ERROR_ADDRESS,
MON_ERROR_TOKEN,
MON_ERROR_COMMANDS};
enum {
MON_CMD_GO=0,
MON_CMD_HELP,
MON_CMD_LDUSB,
MON_CMD_LDXMODEM,
MON_CMD_MDB,
MON_CMD_MDH,
MON_CMD_MDW,
MON_CMD_MWB,
MON_CMD_MWH,
MON_CMD_MWW,
MON_CMD_RESET,
NUM_MONITOR_COMMANDS};
union UN_ADDR {
volatile unsigned int *ptrInt;
volatile unsigned short *ptrShort;
volatile unsigned char *ptrChar;
}unAddr;
struct MONITOR_CMDLINE {
volatile int wdCmd;
volatile int wdAddr;
volatile int wdOpSize;
volatile int wdVallen;
}strCmdline;
/*
*************************************************************
*routines
*************************************************************
*/
void monitor_assist_reset(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_assist_go(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_assist_ldxmodem(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_assist_ldusb(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_assist_mwx(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_assist_mdx(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_assist_help(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_execution(struct MONITOR_CMDLINE *ptrStrCmdline);
void monitor_flag_error(int wdErrorNum);
int monitor_parse_cmdline(unsigned char *ptrCmdString, struct MONITOR_CMDLINE *ptrStrCmdline);
int monitor_get_next_token(unsigned char *ptrSrc, unsigned char *ptrDst, int DstSize);
int monitor_search_table(unsigned char *ptrString, char *ptrTable[], int wdSize);
#endif
/*
*****************************************************************
*name: IE_egwu_monitor.c
*author: Samuel Igwe
*date: 12/03/2015
*description: monitor program/command interpreter and support
* functions.
*****************************************************************
*/
#ifndef IE_EGWU_MONITOR_C
#define IE_EGWU_MONITOR_C
#include "IE_egwu_monitor.h"
void (*ptrMonCmdFuncTable[NUM_MONITOR_COMMANDS])(struct \
MONITOR_CMDLINE *ptrStrCmdline) ={
monitor_assist_go,
monitor_assist_help,
monitor_assist_ldusb,
monitor_assist_ldxmodem,
monitor_assist_mdx,
monitor_assist_mdx,
monitor_assist_mdx,
monitor_assist_mwx,
monitor_assist_mwx,
monitor_assist_mwx,
monitor_assist_reset};
char *ptrMonErrorStrings[] = {
"\r\ncommand error",
"\r\ninvalid or non existent address",
"\r\ntoken error"};
char *ptrMonCmdStrings[] = {
"go",
"help",
"ldusb",
"ldxmodem",
"mdb",
"mdh",
"mdw",
"mwb",
"mwh",
"mww",
"reset"};
char *ptrBanner = {
"\r\n..ie........\
\r\n..ieieie....\
\r\n..ie........\
\r\n..ieieie....\
\r\n..ie........\tIgbo Embedded\
\r\n..ieieie....\tEGWU v1,1 (c) 2015\
\r\n..ie........\tSamuel Igwe\n\n"};
char *ptrPrompt = "\r\negwu-> ";
char *ptrMonUsage = {
"\r\ngo address :\t jump to address\
\r\nldusb address :\t load file to address using USB\
\r\nldxmodem address :\t load file to address using xmodem+serial port\
\r\nhelp :\t display command table\
\r\nmdb|mdh|mdw addr len :\t display byte|word|dword at address\
\r\nmwb|mwh|mww addr val :\t write byte|word|dword to address\
\r\nreset :\t reset the lpc1778\n\n"};
/*
*****************************************************************
*description: monitor executioner
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*note: clear screen
* print banner
* loop:
* get string
* call monitor_parse_string()
* check result != -1
* take action
* loop loop
*............
*..ie........
*..ieieie....
*..ie........
*..ieieie....
*..ie........
*..ie........
*..ieieie....
*..ie........
*............
*****************************************************************
*/
void
monitor_execution(struct MONITOR_CMDLINE *ptrStrCmdline)
{
volatile unsigned int wdTemp;
unsigned char sbTemp[80+1];
uartio_printf("%s", (unsigned int)ptrBanner);
while(1)
{
tclib_memset((unsigned char *)ptrStrCmdline, 0, sizeof(struct MONITOR_CMDLINE));
uartio_printf("%s", (unsigned int)ptrPrompt);
if((uartio_gets((char *)sbTemp, 80)) < 4)
continue;
wdTemp = monitor_parse_cmdline(sbTemp, ptrStrCmdline);
if(wdTemp >= MON_CMD_GO && wdTemp <= MON_CMD_RESET)
ptrMonCmdFuncTable[wdTemp](ptrStrCmdline);
}
}
/*
*****************************************************************
*description: "reset" command
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*****************************************************************
*/
void
monitor_assist_reset(struct MONITOR_CMDLINE *ptrStrCmdline)
{
uartio_printf("\n\rpreparing to reset board \n", 0);
timer_delay_mS(1000);
/*NVIC_SystemReset();
asm ("ldr r0, =0x10000004");
asm ("mov pc, [r0]"); Error: r15 not allowed here -- `mov pc,[r0]'
*/
/*do something with a register write to the FPGA that resets the
entire system ... although this is only useful for rom code
for now just jump to main*/
main();
}
/*
*****************************************************************
*description: "go" command
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*****************************************************************
*/
void
monitor_assist_go(struct MONITOR_CMDLINE *ptrStrCmdline)
{
unsigned int wdTemp = ptrStrCmdline->wdAddr;
uartio_printf("preparing to jump to address %x\n", wdTemp);
timer_delay_mS(1000);
// asm ("ldr r0, =wdTemp");
asm ("ldr sp, =0x10010000");
asm ("mov pc, r0");
}
/*
*****************************************************************
*description: "ldxmodem" command
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*****************************************************************
*/
void
monitor_assist_ldxmodem(struct MONITOR_CMDLINE *ptrStrCmdline)
{
}
/*
*****************************************************************
*description: "ldusb" command
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*****************************************************************
*/
void
monitor_assist_ldusb(struct MONITOR_CMDLINE *ptrStrCmdline)
{
}
/*
*****************************************************************
*description: "mwb/mwh/mww" commands
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*****************************************************************
*/
void
monitor_assist_mwx(struct MONITOR_CMDLINE *ptrStrCmdline)
{
unsigned int wdTemp;
union UN_ADDR *ptrAddr = &unAddr;
ptrAddr->ptrInt = (volatile unsigned int *)ptrStrCmdline->wdAddr;
if(ptrStrCmdline->wdOpSize == 1)
{
*ptrAddr->ptrChar = ptrStrCmdline->wdVallen;
wdTemp = *ptrAddr->ptrChar;
}
else
{
if(ptrStrCmdline->wdOpSize == 2)
{
*ptrAddr->ptrShort = ptrStrCmdline->wdVallen;
wdTemp = *ptrAddr->ptrShort;
}
else
{
*ptrAddr->ptrInt = ptrStrCmdline->wdVallen;
wdTemp = *ptrAddr->ptrInt;
}
}
uartio_printf("\n\r%x", wdTemp);
}
/*
*****************************************************************
*description: "mdb/mdh/mdw" commands
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*****************************************************************
*/
void
monitor_assist_mdx(struct MONITOR_CMDLINE *ptrStrCmdline)
{
volatile unsigned int wdRow, wdMaxRow, wdTemp, wdValPerRow = 8;
volatile unsigned int wdCol, wdMaxCol, wdLastCol;
volatile union UN_ADDR *ptrAddr = &unAddr;
if(ptrStrCmdline->wdAddr== 0)
{
monitor_flag_error(MON_ERROR_ADDRESS);
return;
}
else
ptrAddr->ptrInt = (volatile unsigned int *)ptrStrCmdline->wdAddr;
if(ptrStrCmdline->wdVallen == 0)
ptrStrCmdline->wdVallen++;
wdMaxRow = (ptrStrCmdline->wdVallen)/wdValPerRow;
if(wdMaxRow == 0)
wdMaxRow++;
wdLastCol= (ptrStrCmdline->wdVallen)%16;
for(wdRow = 0; wdRow < wdMaxRow; wdRow++)
{
uartio_printf("\r\n%x:\t", (unsigned int)ptrAddr->ptrInt);
if(wdRow == (wdMaxRow - 1))
wdMaxCol = wdLastCol;
else
wdMaxCol = wdValPerRow;
for(wdCol = 0; wdCol < wdMaxCol; wdCol++)
{
if(ptrStrCmdline->wdOpSize == 1)
{
wdTemp = *ptrAddr->ptrChar;
ptrAddr->ptrChar++;
wdTemp &= 0x0ff;
}
else
{
if(ptrStrCmdline->wdOpSize == 2)
{
wdTemp = *ptrAddr->ptrShort;
ptrAddr->ptrShort++;
wdTemp &= 0x0ffff;
}
else
{
wdTemp = *ptrAddr->ptrInt;
ptrAddr->ptrInt++;
}
}
switch(ptrStrCmdline->wdOpSize)
{
case 4:
{
uartio_printf("%x", ((wdTemp >> 24)&0x0ff));
uartio_printf("%x", ((wdTemp >> 16)&0x0ff));
wdTemp &= 0x0ffff;
/*slide down to code below*/
}
case 2:
{
uartio_printf("%x", ((wdTemp >> 8)&0x0ff));
wdTemp &= 0x0ff;
/*slide down to code below*/
}
case 1:
{
uartio_printf("%x ",(wdTemp));
break;
}
default:
{
}
}
}
}
uartio_printf("\n", 0);
}
/*
*****************************************************************
*description: "help" command
*inputs: struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*****************************************************************
*/
void
monitor_assist_help(struct MONITOR_CMDLINE *ptrStrCmdline)
{
uartio_printf("%s", (unsigned int)ptrMonUsage);
}
/*
*****************************************************************
*description: command line parsing routine
*inputs: char *ptrString = pointer to input string
* struct MONITOR_CMDLINE *ptrStrCmdline = pointer to
* cmdline structure
*output: int = 0 on success
*****************************************************************
*/
int
monitor_parse_cmdline(unsigned char *ptrString,\
struct MONITOR_CMDLINE *ptrStrCmdline)
{
int wdTemp, wdArgCnt = 0;
unsigned char sbToken[80+1];
tclib_memset((unsigned char *)ptrStrCmdline, 0, sizeof(struct MONITOR_CMDLINE));
ptrStrCmdline->wdCmd = -1; /*0 is a valid cmd index*/
while(1)
{
if((wdTemp = monitor_get_next_token(ptrString, sbToken, 80)) == 0)
return (ptrStrCmdline->wdCmd);
wdArgCnt++;
switch(wdArgCnt)
{
case 1: /*command*/
{
if((wdTemp = monitor_search_table(sbToken, ptrMonCmdStrings, NUM_MONITOR_COMMANDS)) == -1)
{
monitor_flag_error(MON_ERROR_CMD);
return -1;
}
ptrStrCmdline->wdCmd = wdTemp;
switch(wdTemp)
{
case MON_CMD_HELP:
case MON_CMD_RESET:
{
ptrStrCmdline->wdOpSize = 0;
break;
}
case MON_CMD_MDB:
case MON_CMD_MWB:
{
ptrStrCmdline->wdOpSize = 1;
break;
}
case MON_CMD_MDH:
case MON_CMD_MWH:
{
ptrStrCmdline->wdOpSize = 2;
break;
}
case MON_CMD_MDW:
case MON_CMD_MWW:
case MON_CMD_GO:
case MON_CMD_LDXMODEM:
case MON_CMD_LDUSB:
default:
{
ptrStrCmdline->wdOpSize = 4;
break;
}
}
break;
}
case 2: /*address*/
{
if(sbToken[1] == 'x' || sbToken[1] == 'X')
ptrStrCmdline->wdAddr = tclib_atoi(sbToken+2);
else
ptrStrCmdline->wdAddr = tclib_atoi(sbToken);
break;
}
case 3: /*value or length*/
{
if(sbToken[1] == 'x' || sbToken[1] == 'X')
ptrStrCmdline->wdVallen = tclib_atoi(sbToken+2);
else
ptrStrCmdline->wdVallen = tclib_atoi(sbToken);
break;
}
default:
{
monitor_flag_error(MON_ERROR_TOKEN);
return -1;
}
}
}
if(wdArgCnt < 4)
return ptrStrCmdline->wdCmd;
else
return -1;
}
/*
*****************************************************************
*description: token extraction routine
*inputs: char *ptrSrc = pointer to input string
* char *ptrDst = pointer to destination buffer
* int wdSize = size of destination buffer
*output: int = string length on success or 0
*operation: a) scan through ptrSrc extracting a string
* b) see a non space char extract into ptrDst and
* replace with space (convert to lower)
* c) when space or NULL is encountered exit
* d) return 0 on error or string lenght on success
*****************************************************************
*/
int
monitor_get_next_token(unsigned char *ptrSrc,\
unsigned char *ptrDst,\
int wdSize)
{
int wdCount;
char byValue;
while(((*ptrSrc) != 0) && (*(ptrSrc) == ' '))
ptrSrc++;
if((*ptrSrc) == 0)
return 0;
//for(wdCount = 0; ((*ptrSrc) != 0 && (*ptrSrc) != ' '); wdCount++)
for(wdCount = 0; wdCount <wdSize; wdCount++)
{
if((*ptrSrc) == 0 || (*ptrSrc) == ' ')
break;
byValue = (*ptrSrc);
*(ptrSrc++) = ' ';
if(byValue >='A' && byValue <='Z')
{
byValue =('Z'- byValue);
byValue += 'a';
}
*(ptrDst++) = byValue;
}
(*ptrDst) = 0;
return wdCount;
}
/*
*****************************************************************
*description: error routine
*inputs: int wdErrorNum = index into error table
*****************************************************************
*/
void
monitor_flag_error(int wdErrorNum)
{
unsigned int wdAddr;
if(wdErrorNum >= MON_ERROR_COMMANDS)
return;
else
wdAddr = (unsigned int)ptrMonErrorStrings[wdErrorNum];
uartio_printf("%s\n", wdAddr);
}
/*
*****************************************************************
*description: table search routine
*inputs: char *ptrString = pointer to input string
* char *ptrTable[] = pointer to MonCmdStrings table
* int wdSize = NUM_MONITOR_COMMANDS
*output: int = enum index into *ptrMonCmdStrings
*****************************************************************
*/
int
monitor_search_table(unsigned char *ptrString,\
char *ptrTable[],\
int wdSize)
{
short wdTop = wdSize - 1;
short wdMiddle = 0;
short wdBottom = 0;
short wdResult = 0;
while(wdBottom <= wdTop)
{
wdMiddle = (wdTop + wdBottom);
wdMiddle >>= 1;
wdResult = tclib_strcmp(ptrString, (unsigned char *)ptrTable[wdMiddle]);
if(wdResult == 0)
return wdMiddle;
if(wdResult < 0)
wdTop = (wdMiddle - 1);
else
wdBottom = (wdMiddle + 1);
}
return -1;
}
#endif
No comments:
Post a Comment