📄 armmem.c
字号:
/*
armmem.c - Memory map decoding, ROM and RAM emulation.
ARMulator extensions for the ARM7100 family.
Copyright (C) 1999 Ben Williamson
Changes to support running uClinux/Atmel AT91 targets
Copyright (C) 2002 David McCullough <davidm@snapgear.com>
This program 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "armdefs.h"
/*ywc 2005-03-30*/
#include "skyeye_flash.h"
//chy 2004-03-11
extern void lcd_write (ARMul_State * state, ARMword addr, ARMword data);
void
mem_reset (ARMul_State * state)
{
int i, num, bank;
FILE *f;
unsigned char *p;
long s;
ARMword swap;
mem_config_t *mc = &skyeye_config.mem;
mem_bank_t *mb = mc->mem_banks;
num = mc->current_num;
for (i = 0; i < num; i++)
{
bank = i;
if (state->mem.rom[bank])
free (state->mem.rom[bank]);
//chy 2003-09-21: if mem type =MEMTYPE_IO, we need not malloc space for it.
state->mem.rom_size[bank] = mb[bank].len;
if (mb[bank].type != MEMTYPE_IO)
{
state->mem.rom[bank] = malloc (mb[bank].len);
if (!state->mem.rom[bank])
{
fprintf (stderr,
"SKYEYE: mem_reset: Error allocating mem for bank number %d.\n",
bank);
exit (-1);
}
/*ywc 2005-04-01 */
#ifndef NO_DBCT
if (!skyeye_config.no_dbct)
{
//teawater add for arm2x86 2004.12.04-------------------------------------------
if (mb[bank].len % TB_LEN)
{
fprintf (stderr,
"SKYEYE: mem_reset: Bank number %d length error.\n",
bank);
exit (-1);
}
state->mem.tbp[bank] = MAP_FAILED;
state->mem.tbt[bank] = NULL;
/*
state->mem.tbp[bank] = mmap(NULL, mb[bank].len / sizeof(ARMword) * TB_INSN_LEN_MAX + mb[bank].len / TB_LEN * op_return.len, PROT_READ|PROT_WRITE|PROT_EXEC, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
if (state->mem.tbp[bank] == MAP_FAILED) {
fprintf(stderr, "SKYEYE: mem_reset: Error allocating mem for bank number %d.\n", bank);
exit(-1);
}
state->mem.tbt[bank] = malloc(mb[bank].len/TB_LEN*sizeof(tb_t));
if (!state->mem.tbt[bank]) {
fprintf(stderr, "SKYEYE: mem_reset: Error allocating mem for bank number %d.\n", bank);
exit(-1);
}
memset(state->mem.tbt[bank], 0, mb[bank].len/TB_LEN*sizeof(tb_t));
*/
//AJ2D--------------------------------------------------------------------------
}
#endif
if (mb[bank].filename && (f = fopen (mb[bank].filename, "r")))
{
if (fread (state->mem.rom[bank], 1, mb[bank].len, f) <= 0)
{
perror ("fread");
fprintf (stderr, "Failed to load '%s'\n",
mb[bank].filename);
exit (-1);
}
fclose (f);
p = (char *) state->mem.rom[bank];
s = 0;
while (s < state->mem.rom_size[bank])
{
if (state->bigendSig == HIGH) /*big enddian? */
swap = ((ARMword) p[3]) | (((ARMword) p[2]) << 8) |
(((ARMword) p[1]) << 16) | (((ARMword) p[0]) << 24);
else
swap = ((ARMword) p[0]) | (((ARMword) p[1]) << 8) |
(((ARMword) p[2]) << 16) | (((ARMword) p[3]) << 24);
*(ARMword *) p = swap;
p += 4;
s += 4;
}
/*ywc 2004-03-30 */
//printf("Loaded ROM %s\n", mb[bank].filename);
if (mb[bank].type == MEMTYPE_FLASH)
{
printf ("Loaded FLASH %s\n", mb[bank].filename);
}
else if (mb[bank].type == MEMTYPE_RAM)
{
printf ("Loaded RAM %s\n", mb[bank].filename);
}
else if (mb[bank].type == MEMTYPE_ROM)
{
printf ("Loaded ROM %s\n", mb[bank].filename);
}
}
else if (mb[bank].filename[0] != '\0')
{
perror (mb[bank].filename);
fprintf (stderr,
"bank %d, Couldn't open boot ROM %s - execution will "
"commence with the debuger.\n", bank,
mb[bank].filename);
exit (-1);
}
}
} /*end for(i = 0;i < num; i++) */
}
// chy: can improve speed !!!! ????
// ywc 2005-04-22: Yes,teawater's code improve the speed, so I open it again.
mem_bank_t *
bank_ptr (ARMword addr)
{
// chy 2005-01-06 add teawater's codes for speed,but I tested it, can not find the big improve
// chy 2005-01-06 maybe some one examines below. now I commit teatwater's codes
//mem_bank_t *mbp;
//---------teawater add for arm2ia32 2004.12.04-----------------
//mem_bank_t *mbp;
static mem_bank_t *mbp = NULL;
if (mbp)
{
if (mbp->addr <= addr && (addr - mbp->addr) < mbp->len)
return (mbp);
}
//AJ2D----------------------------------------------------------
for (mbp = skyeye_config.mem.mem_banks; mbp->len; mbp++)
if (mbp->addr <= addr && (addr - mbp->addr) < mbp->len)
return (mbp);
return (NULL);
}
/*ywc 2005-04-22 , called by dbct/tb.c tb_find FUNCTION */
mem_bank_t *
insn_bank_ptr (ARMword addr)
{
static mem_bank_t *mbp = NULL;
if (mbp)
{
if (mbp->addr <= addr && (addr - mbp->addr) < mbp->len)
return (mbp);
}
for (mbp = skyeye_config.mem.mem_banks; mbp->len; mbp++)
if (mbp->addr <= addr && (addr - mbp->addr) < mbp->len)
return (mbp);
return (NULL);
}
/* ywc 2005-04-22, in order to reduce the bank_ptr call times, use a global variable to
* store the bank_ptr result in mem_read/write_byte/halfword/word. The coresponding
* real_read/write_byte/halfword/word just use the result directly, no need to call
* bank_ptr again.
*/
mem_bank_t *global_mbp;
ARMword
mem_read_byte (ARMul_State * state, ARMword addr)
{
//mem_bank_t *mbp = bank_ptr(addr);
global_mbp = bank_ptr (addr);
//if (mbp && mbp->read_byte)
if (global_mbp && global_mbp->read_byte)
//return mbp->read_byte(state, addr);
return global_mbp->read_byte (state, addr);
else
{
//fprintf(stderr, "SKYEYE:NumInstrs %llu, mem_read_byte addr = %x no bank\n",state->NumInstrs, addr);
//chy 2003-09-03
//SKYEYE_OUTREGS(stderr);
//exit(-1);
return 0;
}
}
ARMword
mem_read_halfword (ARMul_State * state, ARMword addr)
{
//mem_bank_t *mbp = bank_ptr(addr);
global_mbp = bank_ptr (addr);
//if (mbp && mbp->read_halfword)
if (global_mbp && global_mbp->read_halfword)
//return mbp->read_halfword(state, addr);
return global_mbp->read_halfword (state, addr);
else
{
//fprintf(stderr, "SKYEYE:NumInstrs %llu, mem_read_halfword addr = %x no bank\n",state->NumInstrs, addr);
//chy 2003-09-03
//SKYEYE_OUTREGS(stderr);
//exit(-1);
return 0;
}
}
ARMword
mem_read_word (ARMul_State * state, ARMword addr)
{
//chy 2003-07-10 chy: lyh change
//return bank_ptr(addr)->read_word(state, addr);
//mem_bank_t *mbp = bank_ptr(addr);
global_mbp = bank_ptr (addr);
//if (mbp && mbp->read_word)
if (global_mbp && global_mbp->read_word)
//return mbp->read_word(state, addr);
return global_mbp->read_word (state, addr);
else
{
//fprintf(stderr, "SKYEYE:NumInstrs %llu, mem_read_word addr = %x no bank\n",state->NumInstrs, addr);
//chy 2003-09-03
//SKYEYE_OUTREGS(stderr);
//exit(-1);
return 0;
}
}
void
mem_write_byte (ARMul_State * state, ARMword addr, ARMword data)
{
//mem_bank_t *mbp = bank_ptr(addr);
global_mbp = bank_ptr (addr);
//if (mbp && mbp->write_byte){
if (global_mbp && global_mbp->write_byte)
{
/*ywc 2005-03-31 */
/*ywc 2005-04-22 move it to real_write_byte */
/*
if(!skyeye_config.no_dbct){
//teawater add for arm2x86 2005.03.18----------------------------------
tb_setdirty(state, addr, mbp);
//AJ2D----------------------------------------------------------
}
*/
global_mbp->write_byte (state, addr, data);
//mbp->write_byte(state, addr, data);
}
else
{
//fprintf(stderr, "SKYEYE:NumInstrs %llu, mem_write_byte addr = %x no bank\n",state->NumInstrs, addr);
//chy 2003-09-03
//SKYEYE_OUTREGS(stderr);
//exit(-1);
}
}
void
mem_write_halfword (ARMul_State * state, ARMword addr, ARMword data)
{
//mem_bank_t *mbp = bank_ptr(addr);
global_mbp = bank_ptr (addr);
//if (mbp && mbp->write_halfword){
if (global_mbp && global_mbp->write_halfword)
{
/*ywc 2005-03-31 */
/*ywc 2005-04-22 move it to real_write_halfword */
/*
if(!skyeye_config.no_dbct){
//teawater add for arm2x86 2005.03.18----------------------------------
tb_setdirty(state, addr, mbp);
//AJ2D----------------------------------------------------------
}
*/
//mbp->write_halfword(state, addr, data);
global_mbp->write_halfword (state, addr, data);
}
else
{
//fprintf(stderr, "SKYEYE:NumInstrs %llu, mem_write_halfword addr = %x no bank\n",state->NumInstrs, addr);
//chy 2003-09-03
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -