Onda VX747:

* Overall cleanup (still needs work)
  * Add preliminary USB support
  * Add power off support
  * Add preliminary MMU handling


git-svn-id: svn://svn.rockbox.org/rockbox/trunk@18348 a1c6a512-1295-4272-9138-f99709370657
This commit is contained in:
Maurus Cuelenaere 2008-08-26 21:48:49 +00:00
parent 753350154e
commit 62c4a2838e
13 changed files with 1424 additions and 123 deletions

View file

@ -42,6 +42,48 @@ static void audiotest(void)
__aic_enable_loopback(); __aic_enable_loopback();
} }
/* CP0 hazard avoidance. */
#define BARRIER __asm__ __volatile__(".set noreorder\n\t" \
"nop; nop; nop; nop; nop; nop;\n\t" \
".set reorder\n\t")
static void show_tlb(void)
{
#define ASID_MASK 0xFF
unsigned int old_ctx;
unsigned int entry;
unsigned int entrylo0, entrylo1, entryhi;
unsigned int pagemask;
cli();
/* Save old context */
old_ctx = (read_c0_entryhi() & 0xff);
printf("TLB content:");
for(entry = 0; entry < 32; entry++)
{
write_c0_index(entry);
BARRIER;
tlb_read();
BARRIER;
entryhi = read_c0_entryhi();
entrylo0 = read_c0_entrylo0();
entrylo1 = read_c0_entrylo1();
pagemask = read_c0_pagemask();
printf("%02d: ASID=%02d%s VA=0x%08x", entry, entryhi & ASID_MASK, (entrylo0 & entrylo1 & 1) ? "(G)" : " ", entryhi & ~ASID_MASK);
printf("PA0=0x%08x C0=%x %s%s%s", (entrylo0>>6)<<12, (entrylo0>>3) & 7, (entrylo0 & 4) ? "Dirty " : "", (entrylo0 & 2) ? "Valid " : "Invalid ", (entrylo0 & 1) ? "Global" : "");
printf("PA1=0x%08x C1=%x %s%s%s", (entrylo1>>6)<<12, (entrylo1>>3) & 7, (entrylo1 & 4) ? "Dirty " : "", (entrylo1 & 2) ? "Valid " : "Invalid ", (entrylo1 & 1) ? "Global" : "");
printf("pagemask=0x%08x entryhi=0x%08x", pagemask, entryhi);
printf("entrylo0=0x%08x entrylo1=0x%08x", entrylo0, entrylo1);
}
BARRIER;
write_c0_entryhi(old_ctx);
sti();
}
int main(void) int main(void)
{ {
cli(); cli();
@ -51,6 +93,7 @@ int main(void)
lcd_setfont(FONT_SYSFIXED); lcd_setfont(FONT_SYSFIXED);
button_init(); button_init();
rtc_init(); rtc_init();
usb_init();
backlight_init(); backlight_init();
@ -59,7 +102,7 @@ int main(void)
sti(); sti();
/* To make Windows say "ding-dong".. */ /* To make Windows say "ding-dong".. */
REG8(USB_REG_POWER) &= ~USB_POWER_SOFTCONN; //REG8(USB_REG_POWER) &= ~USB_POWER_SOFTCONN;
int touch, btn; int touch, btn;
char datetime[30]; char datetime[30];
@ -89,7 +132,9 @@ int main(void)
if(read_c0_config1() & (1 << 5)) printf(" * MDMX available"); if(read_c0_config1() & (1 << 5)) printf(" * MDMX available");
if(read_c0_config1() & (1 << 6)) printf(" * CP2 available"); if(read_c0_config1() & (1 << 6)) printf(" * CP2 available");
printf("C0_STATUS: 0x%x", read_c0_status()); printf("C0_STATUS: 0x%x", read_c0_status());
/* unsigned char testdata[4096];
#if 0
unsigned char testdata[4096];
char msg[30]; char msg[30];
int j = 0; int j = 0;
while(1) while(1)
@ -111,7 +156,8 @@ int main(void)
j--; j--;
if(j<0) if(j<0)
j = 0; j = 0;
}*/ }
#endif
while(1) while(1)
{ {
btn = button_read_device(&touch); btn = button_read_device(&touch);
@ -127,7 +173,16 @@ int main(void)
if(button_hold()) if(button_hold())
{ {
printf("BUTTON_HOLD"); printf("BUTTON_HOLD");
asm("break 7"); asm("break 0x7");
}
if(btn & BUTTON_VOL_DOWN)
{
reset_screen();
show_tlb();
}
if(btn & BUTTON_POWER)
{
power_off();
} }
if(btn & BUTTON_TOUCH) if(btn & BUTTON_TOUCH)
{ {
@ -143,6 +198,16 @@ int main(void)
lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*2, datetime); lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*2, datetime);
snprintf(datetime, 30, "X: %d Y: %d", touch>>16, touch & 0xFFFF); snprintf(datetime, 30, "X: %d Y: %d", touch>>16, touch & 0xFFFF);
lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*3, datetime); lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*3, datetime);
snprintf(datetime, 30, "PIN3: 0x%x", REG_GPIO_PXPIN(3));
lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*4, datetime);
snprintf(datetime, 30, "PIN2: 0x%x", REG_GPIO_PXPIN(2));
lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*5, datetime);
snprintf(datetime, 30, "PIN1: 0x%x", REG_GPIO_PXPIN(1));
lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*6, datetime);
snprintf(datetime, 30, "PIN0: 0x%x", REG_GPIO_PXPIN(0));
lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*7, datetime);
snprintf(datetime, 30, "ICSR: 0x%x", read_c0_badvaddr());
lcd_putsxy(LCD_WIDTH-SYSFONT_WIDTH*strlen(datetime), LCD_HEIGHT-SYSFONT_HEIGHT*8, datetime);
lcd_update(); lcd_update();
} }

View file

@ -1084,6 +1084,7 @@ target/mips/ingenic_jz47xx/ata-nand-jz4740.c
target/mips/ingenic_jz47xx/lcd-jz4740.c target/mips/ingenic_jz47xx/lcd-jz4740.c
target/mips/ingenic_jz47xx/kernel-jz4740.c target/mips/ingenic_jz47xx/kernel-jz4740.c
target/mips/ingenic_jz47xx/system-jz4740.c target/mips/ingenic_jz47xx/system-jz4740.c
target/mips/ingenic_jz47xx/usb-jz4740.c
drivers/nand_id.c drivers/nand_id.c
#endif #endif

View file

@ -706,6 +706,8 @@ do { \
#define read_c0_cache() __read_32bit_c0_register($7, 0) /* TX39xx */ #define read_c0_cache() __read_32bit_c0_register($7, 0) /* TX39xx */
#define write_c0_cache(val) __write_32bit_c0_register($7, 0, val) #define write_c0_cache(val) __write_32bit_c0_register($7, 0, val)
#define read_c0_badvaddr() __read_32bit_c0_register($8, 0)
#define read_c0_count() __read_32bit_c0_register($9, 0) #define read_c0_count() __read_32bit_c0_register($9, 0)
#define write_c0_count(val) __write_32bit_c0_register($9, 0, val) #define write_c0_count(val) __write_32bit_c0_register($9, 0, val)

View file

@ -42,7 +42,9 @@
#define NANDFLASH_ALE 0x00010000 //PA[16] #define NANDFLASH_ALE 0x00010000 //PA[16]
#define NANDFLASH_BASE 0xB8000000 #define NANDFLASH_BASE 0xB8000000
#define REG_NAND_DATA (*((volatile unsigned char *)NANDFLASH_BASE)) #define REG_NAND_DATA8 (*((volatile unsigned char *)NANDFLASH_BASE))
#define REG_NAND_DATA16 (*((volatile unsigned short *)NANDFLASH_BASE))
#define REG_NAND_DATA REG_NAND_DATA8
#define REG_NAND_CMD (*((volatile unsigned char *)(NANDFLASH_BASE + NANDFLASH_CLE))) #define REG_NAND_CMD (*((volatile unsigned char *)(NANDFLASH_BASE + NANDFLASH_CLE)))
#define REG_NAND_ADDR (*((volatile unsigned char *)(NANDFLASH_BASE + NANDFLASH_ALE))) #define REG_NAND_ADDR (*((volatile unsigned char *)(NANDFLASH_BASE + NANDFLASH_ALE)))

View file

@ -31,6 +31,10 @@ SECTIONS
*(.glue_7); *(.glue_7);
*(.glue_7t); *(.glue_7t);
*(.rel.dyn); *(.rel.dyn);
} > DRAM
.vectors :
{
_vectorsstart = .; _vectorsstart = .;
KEEP(*(.vectors)) KEEP(*(.vectors))
*(.vectors); *(.vectors);
@ -69,18 +73,6 @@ SECTIONS
. = ALIGN(4); . = ALIGN(4);
.stack :
{
*(.stack)
_stackbegin = .;
stackbegin = .;
. += 0x2000;
_stackend = .;
stackend = .;
} > DRAM
. = ALIGN(4);
.bss : .bss :
{ {
_edata = .; _edata = .;
@ -91,4 +83,36 @@ SECTIONS
*(.scommon*); *(.scommon*);
_end = .; _end = .;
} > DRAM } > DRAM
.iram IRAMORIG:
{
. = 0x220; /* Vectors take in 0x80000000 -> 0x80000220 */
_iramstart = .;
*(.icode)
*(.irodata)
*(.idata)
. = ALIGN(0x4);
_iramend = .;
} > IRAM AT> DRAM
_iramcopy = LOADADDR(.iram);
.ibss (NOLOAD) :
{
_iedata = .;
*(.ibss)
. = ALIGN(0x4);
_iend = .;
} > IRAM
.stack :
{
*(.stack)
. = ALIGN(0x4);
_stackbegin = .;
stackbegin = .;
. += 0x2000;
_stackend = .;
stackend = .;
} > IRAM
} }

View file

@ -40,7 +40,7 @@
.text .text
.set mips3 .set mips32
.extern system_main .extern system_main
@ -53,28 +53,36 @@
.word 0 /* HACK */ .word 0 /* HACK */
.word 0 /* HACK */ .word 0 /* HACK */
#endif #endif
_start: _start:
la ra, _start la ra, _start
//---------------------------------------------------- /*
// init cp0 registers. ----------------------------------------------------
//---------------------------------------------------- init cp0 registers.
----------------------------------------------------
*/
mtc0 zero, C0_WATCHLO mtc0 zero, C0_WATCHLO
mtc0 zero, C0_WATCHHI mtc0 zero, C0_WATCHHI
li t0, (M_StatusBEV | M_StatusIM7 | M_StatusIM6 \ li t0, (M_StatusBEV | M_StatusIM7 | M_StatusIM6 \
| M_StatusIM5 | M_StatusIM4 | M_StatusIM3 \ | M_StatusIM5 | M_StatusIM4 | M_StatusIM3 \
| M_StatusIM2 | M_StatusERL) | M_StatusIM2 | M_StatusERL | M_StatusSM)
// BEV = Enable Boot Exception Vectors /*
// IMx = Interrupt mask BEV = Enable Boot Exception Vectors
// ERL = Denotes error level IMx = Interrupt mask
ERL = Denotes error level
SM = Supervisor Mode
*/
mtc0 t0, C0_STATUS mtc0 t0, C0_STATUS
li t1, M_CauseIV li t1, M_CauseIV
mtc0 t1, C0_CAUSE mtc0 t1, C0_CAUSE
//---------------------------------------------------- /*
// init caches, assumes a 4way*128set*32byte i/d cache ----------------------------------------------------
//---------------------------------------------------- init caches, assumes a 4way*128set*32byte i/d cache
----------------------------------------------------
*/
li t0, 3 // enable cache for kseg0 accesses li t0, 3 // enable cache for kseg0 accesses
mtc0 t0, C0_CONFIG // CONFIG reg mtc0 t0, C0_CONFIG // CONFIG reg
la t0, 0x80000000 // an idx op should use a unmappable address la t0, 0x80000000 // an idx op should use a unmappable address
@ -82,35 +90,70 @@ _start:
mtc0 zero, C0_TAGLO // TAGLO reg mtc0 zero, C0_TAGLO // TAGLO reg
mtc0 zero, C0_TAGHI // TAGHI reg mtc0 zero, C0_TAGHI // TAGHI reg
_init_cache_loop: _init_cache_loop:
cache 0x8, 0(t0) // index store icache tag cache 0x8, 0(t0) // index store icache tag
cache 0x9, 0(t0) // index store dcache tag cache 0x9, 0(t0) // index store dcache tag
bne t0, t1, _init_cache_loop bne t0, t1, _init_cache_loop
addiu t0, t0, 0x20 // 32 bytes per cache line addiu t0, t0, 0x20 // 32 bytes per cache line
nop nop
//---------------------------------------------------- /*
// Invalidate BTB ----------------------------------------------------
//---------------------------------------------------- Invalidate BTB
----------------------------------------------------
*/
mfc0 t0, C0_CONFIG mfc0 t0, C0_CONFIG
nop nop
ori t0, 2 ori t0, 2
mtc0 t0, C0_CONFIG mtc0 t0, C0_CONFIG
nop nop
//---------------------------------------------------- /*
// clear BSS section ----------------------------------------------------
//---------------------------------------------------- clear BSS section
----------------------------------------------------
*/
la t0, _edata la t0, _edata
la t1, _end la t1, _end
_init_bss_loop: _init_bss_loop:
sw zero, 0(t0) sw zero, 0(t0)
bne t0, t1, _init_bss_loop bne t0, t1, _init_bss_loop
addiu t0, 4 addiu t0, 4
#ifndef BOOTLOADER
/*
----------------------------------------------------
clear IBSS section
----------------------------------------------------
*/
la t0, _iedata
la t1, _iend
_init_ibss_loop:
sw zero, 0(t0)
bne t0, t1, _init_ibss_loop
addiu t0, 4
/*
----------------------------------------------------
copy IRAM section
----------------------------------------------------
*/
la t0, _iramcopy
la t1, _iramstart
la t2, _iramend
_init_iram_loop:
lw t3, 0(t0)
sw t3, 0(t1)
addiu t1, 4
bne t1, t2, _init_iram_loop
addiu t0, 4
#endif
//---------------------------------------------------- /*
// setup stack, jump to C code ----------------------------------------------------
//---------------------------------------------------- setup stack, jump to C code
----------------------------------------------------
*/
la sp, stackend la sp, stackend
la t0, stackbegin la t0, stackbegin
li t1, 0xDEADBEEF li t1, 0xDEADBEEF

View file

@ -35,6 +35,11 @@ void tick_start(unsigned int interval_in_ms)
__tcu_stop_counter(0); __tcu_stop_counter(0);
__tcu_disable_pwm_output(0); __tcu_disable_pwm_output(0);
__tcu_stop_counter(1);
__tcu_disable_pwm_output(1);
__tcu_stop_counter(2);
__tcu_disable_pwm_output(2);
__tcu_clear_full_match_flag(2);
__tcu_mask_half_match_irq(0); __tcu_mask_half_match_irq(0);
__tcu_unmask_full_match_irq(0); __tcu_unmask_full_match_irq(0);
@ -58,12 +63,13 @@ void tick_start(unsigned int interval_in_ms)
__tcu_start_counter(0); __tcu_start_counter(0);
system_enable_irq(IRQ_TCU0); system_enable_irq(IRQ_TCU0);
} }
/* Interrupt handler */ /* Interrupt handler */
void TCU0(void) void TCU0(void)
{ {
__tcu_clear_full_match_flag(0);
int i; int i;
/* Run through the list of tick tasks */ /* Run through the list of tick tasks */

View file

@ -64,7 +64,7 @@ void lcd_update_rect(int x, int y, int width, int height)
REG_DMAC_DTAR(0) = 0x130500B0; /* SLCD_FIFO */ REG_DMAC_DTAR(0) = 0x130500B0; /* SLCD_FIFO */
REG_DMAC_DTCR(0) = width*height; REG_DMAC_DTCR(0) = width*height;
REG_DMAC_DCMD(0) = (DMAC_DCMD_SAI | DMAC_DCMD_RDIL_2 | DMAC_DCMD_SWDH_32 /* (1 << 23) | (0 << 16) | (0 << 14) */ REG_DMAC_DCMD(0) = (DMAC_DCMD_SAI | DMAC_DCMD_RDIL_IGN | DMAC_DCMD_SWDH_32 /* (1 << 23) | (0 << 16) | (0 << 14) */
| DMAC_DCMD_DWDH_16 | DMAC_DCMD_DS_16BIT); /* | (2 << 12) | (3 << 8) */ | DMAC_DCMD_DWDH_16 | DMAC_DCMD_DS_16BIT); /* | (2 << 12) | (3 << 8) */
REG_DMAC_DCCSR(0) = (DMAC_DCCSR_NDES | DMAC_DCCSR_EN); /* (1 << 31) | (1 << 0) */ REG_DMAC_DCCSR(0) = (DMAC_DCCSR_NDES | DMAC_DCCSR_EN); /* (1 << 31) | (1 << 0) */

View file

@ -36,7 +36,7 @@
#define TS_AD_COUNT 5 #define TS_AD_COUNT 5
#define M_SADC_CFG_SNUM ((TS_AD_COUNT - 1) << SADC_CFG_SNUM_BIT) #define M_SADC_CFG_SNUM ((TS_AD_COUNT - 1) << SADC_CFG_SNUM_BIT)
#define SADC_CFG_INIT ( \ #define SADC_CFG_INIT ( \
(2 << SADC_CFG_CLKOUT_NUM_BIT) | \ (2 << SADC_CFG_CLKOUT_NUM_BIT) | \
SADC_CFG_XYZ1Z2 | \ SADC_CFG_XYZ1Z2 | \
M_SADC_CFG_SNUM | \ M_SADC_CFG_SNUM | \
@ -109,6 +109,7 @@ int button_read_device(int *data)
unsigned int key = ~(__gpio_get_port(3)); unsigned int key = ~(__gpio_get_port(3));
int ret = 0; int ret = 0;
if(key & BTN_MASK) if(key & BTN_MASK)
{ {
if(key & BTN_VOL_DOWN) if(key & BTN_VOL_DOWN)
@ -132,10 +133,33 @@ int button_read_device(int *data)
return ret; return ret;
} }
/*
static enum touchpad_mode current_mode = TOUCHPAD_POINT;
static bool touch_available = false;
static int touchpad_buttons[3][3] =
{
{BUTTON_TOPLEFT, BUTTON_TOPMIDDLE, BUTTON_TOPRIGHT},
{BUTTON_MIDLEFT, BUTTON_CENTER, BUTTON_MIDRIGHT},
{BUTTON_BOTTOMLEFT, BUTTON_BOTTOMMIDDLE, BUTTON_BOTTOMRIGHT}
};
void touchpad_set_mode(enum touchpad_mode mode)
{
current_mode = mode;
}
enum touchpad_mode touchpad_get_mode(void)
{
return current_mode;
}
void button_set_touch_available(void) void button_set_touch_available(void)
{ {
return; touch_available = true;
} }
*/
/* Interrupt handler */ /* Interrupt handler */
void SADC(void) void SADC(void)
@ -167,51 +191,50 @@ void SADC(void)
} }
if(state & SADC_CTRL_TSRDYM) if(state & SADC_CTRL_TSRDYM)
{ {
unsigned int dat; unsigned int dat;
unsigned short xData, yData; unsigned short xData, yData;
short tsz1Data, tsz2Data; short tsz1Data, tsz2Data;
dat = REG_SADC_TSDAT;
xData = (dat >> 0) & 0xfff;
yData = (dat >> 16) & 0xfff;
dat = REG_SADC_TSDAT;
tsz1Data = (dat >> 0) & 0xfff;
tsz2Data = (dat >> 16) & 0xfff;
if(!pendown_flag) dat = REG_SADC_TSDAT;
return ;
xData = (dat >> 0) & 0xfff;
tsz1Data = tsz2Data - tsz1Data; yData = (dat >> 16) & 0xfff;
if((tsz1Data > 15) || (tsz1Data < -15)) dat = REG_SADC_TSDAT;
tsz1Data = (dat >> 0) & 0xfff;
tsz2Data = (dat >> 16) & 0xfff;
if(!pendown_flag)
return ;
tsz1Data = tsz2Data - tsz1Data;
if((tsz1Data > 15) || (tsz1Data < -15))
{ {
if(x_pos == -1) if(x_pos == -1)
x_pos = xData; x_pos = xData;
else else
x_pos = (x_pos + xData) / 2; x_pos = (x_pos + xData) / 2;
if(y_pos == -1) if(y_pos == -1)
y_pos = yData; y_pos = yData;
else else
y_pos = (y_pos + yData) / 2; y_pos = (y_pos + yData) / 2;
} }
datacount++; datacount++;
if(datacount > TS_AD_COUNT - 1) if(datacount > TS_AD_COUNT - 1)
{ {
if(x_pos != -1) if(x_pos != -1)
{ {
stable_x_pos = x_pos; stable_x_pos = x_pos;
stable_y_pos = y_pos; stable_y_pos = y_pos;
x_pos = -1; x_pos = -1;
y_pos = -1; y_pos = -1;
} }
datacount = 0;
datacount = 0; }
}
} }
if(state & SADC_CTRL_PBATRDYM) if(state & SADC_CTRL_PBATRDYM)
{ {

View file

@ -269,25 +269,15 @@ static void dis_irq(unsigned int irq)
static void ack_irq(unsigned int irq) static void ack_irq(unsigned int irq)
{ {
__intc_ack_irq(irq);
if ((irq >= IRQ_GPIO_0) && (irq <= IRQ_GPIO_0 + NUM_GPIO)) if ((irq >= IRQ_GPIO_0) && (irq <= IRQ_GPIO_0 + NUM_GPIO))
{ {
__intc_ack_irq(IRQ_GPIO0 - ((irq - IRQ_GPIO_0)>>5)); __intc_ack_irq(IRQ_GPIO0 - ((irq - IRQ_GPIO_0)>>5));
__gpio_ack_irq(irq - IRQ_GPIO_0); __gpio_ack_irq(irq - IRQ_GPIO_0);
} }
else if ((irq >= IRQ_DMA_0) && (irq <= IRQ_DMA_0 + NUM_DMA)) else if ((irq >= IRQ_DMA_0) && (irq <= IRQ_DMA_0 + NUM_DMA))
{
__intc_ack_irq(IRQ_DMAC); __intc_ack_irq(IRQ_DMAC);
}
else if (irq < 32) else if (irq < 32)
{
__intc_ack_irq(irq); __intc_ack_irq(irq);
/* TODO: check if really needed */
if (irq == IRQ_TCU0)
{
__tcu_clear_full_match_flag(0);
}
}
} }
static unsigned long ipl; static unsigned long ipl;
@ -296,7 +286,7 @@ static int get_irq_number(void)
register int irq = 0; register int irq = 0;
ipl |= REG_INTC_IPR; ipl |= REG_INTC_IPR;
if (ipl == 0) if (ipl == 0)
return -1; return -1;
@ -341,8 +331,6 @@ void intr_handler(void)
ack_irq(irq); ack_irq(irq);
if(irq > 0) if(irq > 0)
irqvector[irq-1](); irqvector[irq-1]();
return;
} }
#define EXC(x,y) if(_cause == (x)) return (y); #define EXC(x,y) if(_cause == (x)) return (y);
@ -386,7 +374,6 @@ static void detect_clock(void)
cfcr = REG_CPM_CPCCR; cfcr = REG_CPM_CPCCR;
pllout = (__cpm_get_pllm() + 2)* JZ_EXTAL / (__cpm_get_plln() + 2); pllout = (__cpm_get_pllm() + 2)* JZ_EXTAL / (__cpm_get_plln() + 2);
iclk = pllout / FR2n[__cpm_get_cdiv()]; iclk = pllout / FR2n[__cpm_get_cdiv()];
/*printf("EXTAL_CLK = %dM PLL = %d iclk = %d\r\n",EXTAL_CLK / 1000 /1000,pllout,iclk);*/
} }
void udelay(unsigned int usec) void udelay(unsigned int usec)
@ -450,11 +437,11 @@ void sti(void)
#define SYNC_WB() __asm__ __volatile__ ("sync") #define SYNC_WB() __asm__ __volatile__ ("sync")
#define cache_op(op,addr) \ #define __CACHE_OP(op, addr) \
__asm__ __volatile__( \ __asm__ __volatile__( \
" .set noreorder \n" \ " .set noreorder \n" \
" .set mips32\n\t \n" \ " .set mips32\n\t \n" \
" cache %0, %1 \n" \ " cache %0, %1 \n" \
" .set mips0 \n" \ " .set mips0 \n" \
" .set reorder \n" \ " .set reorder \n" \
: \ : \
@ -462,7 +449,7 @@ void sti(void)
void __flush_dcache_line(unsigned long addr) void __flush_dcache_line(unsigned long addr)
{ {
cache_op(Hit_Writeback_Inv_D, addr); __CACHE_OP(Hit_Writeback_Inv_D, addr);
SYNC_WB(); SYNC_WB();
} }
@ -470,6 +457,7 @@ void __icache_invalidate_all(void)
{ {
unsigned int i; unsigned int i;
/*
do do
{ {
unsigned long __k0_addr; unsigned long __k0_addr;
@ -484,17 +472,19 @@ void __icache_invalidate_all(void)
: "r" (0x20000000) : "r" (0x20000000)
); );
} while(0); } while(0);
*/
asm volatile (".set noreorder \n" asm volatile (".set noreorder \n"
".set mips32 \n" ".set mips32 \n"
"mtc0 $0,$28 \n" "mtc0 $0, $28 \n" /* TagLo */
"mtc0 $0,$29 \n" "mtc0 $0, $29 \n" /* TagHi */
".set mips0 \n" ".set mips0 \n"
".set reorder \n" ".set reorder \n"
); );
for(i=KSEG0; i<KSEG0+CACHE_SIZE; i+=CACHE_LINE_SIZE) for(i=KSEG0; i<KSEG0+CACHE_SIZE; i+=CACHE_LINE_SIZE)
cache_op(Index_Store_Tag_I, i); __CACHE_OP(Index_Store_Tag_I, i);
/*
do do
{ {
unsigned long __k0_addr; unsigned long __k0_addr;
@ -507,16 +497,17 @@ void __icache_invalidate_all(void)
: "=&r" (__k0_addr) : "=&r" (__k0_addr)
); );
} while(0); } while(0);
*/
do do
{ {
unsigned long tmp; unsigned long tmp;
__asm__ __volatile__( __asm__ __volatile__(
".set mips32 \n" ".set mips32 \n"
"mfc0 %0, $16, 7 \n" "mfc0 %0, $16, 7 \n" /* Config */
"nop \n" "nop \n"
"ori %0, 2 \n" "ori %0, 2 \n"
"mtc0 %0, $16, 7 \n" "mtc0 %0, $16, 7 \n" /* Config */
"nop \n" "nop \n"
".set mips0 \n" ".set mips0 \n"
: "=&r" (tmp)); : "=&r" (tmp));
@ -529,20 +520,20 @@ void __dcache_invalidate_all(void)
asm volatile (".set noreorder \n" asm volatile (".set noreorder \n"
".set mips32 \n" ".set mips32 \n"
"mtc0 $0,$28 \n" "mtc0 $0, $28 \n"
"mtc0 $0,$29 \n" "mtc0 $0, $29 \n"
".set mips0 \n" ".set mips0 \n"
".set reorder \n" ".set reorder \n"
); );
for (i=KSEG0; i<KSEG0+CACHE_SIZE; i+=CACHE_LINE_SIZE) for (i=KSEG0; i<KSEG0+CACHE_SIZE; i+=CACHE_LINE_SIZE)
cache_op(Index_Store_Tag_D, i); __CACHE_OP(Index_Store_Tag_D, i);
} }
void __dcache_writeback_all(void) void __dcache_writeback_all(void)
{ {
unsigned int i; unsigned int i;
for(i=KSEG0; i<KSEG0+CACHE_SIZE; i+=CACHE_LINE_SIZE) for(i=KSEG0; i<KSEG0+CACHE_SIZE; i+=CACHE_LINE_SIZE)
cache_op(Index_Writeback_Inv_D, i); __CACHE_OP(Index_Writeback_Inv_D, i);
SYNC_WB(); SYNC_WB();
} }
@ -559,37 +550,129 @@ void dma_cache_wback_inv(unsigned long addr, unsigned long size)
a = addr & ~(dc_lsize - 1); a = addr & ~(dc_lsize - 1);
end = (addr + size - 1) & ~(dc_lsize - 1); end = (addr + size - 1) & ~(dc_lsize - 1);
while (1) for(; a < end; a += dc_lsize)
{
__flush_dcache_line(a); /* Hit_Writeback_Inv_D */ __flush_dcache_line(a); /* Hit_Writeback_Inv_D */
if (a == end)
break;
a += dc_lsize;
}
} }
} }
extern int main(void); extern int main(void);
extern unsigned int _vectorsstart; /* see boot.lds/app.lds */ extern void except_common_entry(void);
#define mtc0_tlbw_hazard() \
__asm__ __volatile__( \
" .set noreorder \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" .set reorder \n");
#define tlbw_use_hazard() \
__asm__ __volatile__( \
" .set noreorder \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" nop \n" \
" .set reorder \n");
#define PAGE_SHIFT PL_4K
#define PM_DEFAULT_MASK PM_4K
#define UNIQUE_ENTRYHI(idx) (A_K0BASE + ((idx) << (PAGE_SHIFT + 1)))
static void local_flush_tlb_all(void)
{
unsigned long old_ctx;
int entry;
unsigned int old_irq = disable_irq_save();
/* Save old context and create impossible VPN2 value */
old_ctx = read_c0_entryhi();
write_c0_entrylo0(0);
write_c0_entrylo1(0);
/* Blast 'em all away. */
for(entry = read_c0_wired(); entry < 32; entry++)
{
/* Make sure all entries differ. */
write_c0_entryhi(UNIQUE_ENTRYHI(entry));
write_c0_index(entry);
mtc0_tlbw_hazard();
tlb_write_indexed();
}
tlbw_use_hazard();
write_c0_entryhi(old_ctx);
restore_irq(old_irq);
}
static void tlb_init(void)
{
write_c0_pagemask(PM_DEFAULT_MASK);
write_c0_wired(0);
write_c0_framemask(0);
local_flush_tlb_all();
}
static void tlb_refill_handler(void)
{
#if 1
panicf("TLB refill handler! [0x%x] [0x%x]", read_c0_badvaddr(), read_c0_epc());
#else
__asm__ __volatile__(
"mfc0 k0, C0_BADVADDR\n"
"lui k1, pgdc\n"
"lw k1, pgdc>>16(k0)\n"
"srl k0, k0, 22\n"
"sll k0, k0, 2\n"
"addu k1, k1, k0\n"
"mfc0 k0, C0_CONTEXT\n"
"lw k1, 0(k1)\n"
"andi k0, k0, 0xFFC\n"
"addu k1, k1, k0\n"
"lw k0, 0(k1)\n"
"nop\n"
"mtc0 k0, C0_ENTRYLO0\n"
"mfc0 k1, C0_EPC\n"
"tlbwr\n"
"jr k1\n"
"rfe\n"
);
#endif
}
void system_main(void) void system_main(void)
{ {
int i; int i;
cli(); /*
write_c0_status(1 << 28 | 1 << 10); /* Enable CP | Mask interrupt 2 */ * 0x0 - Simple TLB refill handler
* 0x100 - Cache error handler
memcpy((void *)A_K0BASE, (void *)&_vectorsstart, 0x20); * 0x180 - Exception/Interrupt handler
memcpy((void *)(A_K0BASE + 0x180), (void *)&_vectorsstart, 0x20); * 0x200 - Special Exception Interrupt handler (when IV is set in CP0_CAUSE)
memcpy((void *)(A_K0BASE + 0x200), (void *)&_vectorsstart, 0x20); */
memcpy((void *)A_K0BASE, (void *)&tlb_refill_handler, 0x20);
memcpy((void *)(A_K0BASE + 0x100), (void *)&except_common_entry, 0x20);
memcpy((void *)(A_K0BASE + 0x180), (void *)&except_common_entry, 0x20);
memcpy((void *)(A_K0BASE + 0x200), (void *)&except_common_entry, 0x20);
__dcache_writeback_all(); __dcache_writeback_all();
__icache_invalidate_all(); __icache_invalidate_all();
write_c0_status(1 << 28 | 1 << 10 | 1 << 3); /* Enable CP | Mask interrupt 2 | Supervisor mode */
/* Disable all interrupts */ /* Disable all interrupts */
for(i=0; i<IRQ_MAX; i++) for(i=0; i<IRQ_MAX; i++)
dis_irq(i); dis_irq(i);
tlb_init();
sti(); sti();
detect_clock(); detect_clock();
@ -609,3 +692,17 @@ void system_reboot(void)
while (1); while (1);
} }
void power_off(void)
{
/* Put system into hibernate mode */
__rtc_clear_alarm_flag();
__rtc_clear_hib_stat_all();
//__rtc_set_scratch_pattern(0x12345678);
__rtc_enable_alarm_wakeup();
__rtc_set_hrcr_val(0xfe0);
__rtc_set_hwfcr_val((0xFFFF << 4));
__rtc_power_down();
while(1);
}

View file

@ -99,6 +99,8 @@ void sti(void);
void cli(void); void cli(void);
void udelay(unsigned int usec); void udelay(unsigned int usec);
void mdelay(unsigned int msec); void mdelay(unsigned int msec);
void power_off(void);
void system_reboot(void);
#endif /* __SYSTEM_TARGET_H_ */ #endif /* __SYSTEM_TARGET_H_ */

File diff suppressed because it is too large Load diff

View file

@ -18,9 +18,8 @@
* KIND, either express or implied. * KIND, either express or implied.
* *
****************************************************************************/ ****************************************************************************/
#ifndef USB_TARGET_H
#define USB_TARGET_H
#include <stdbool.h>
int usb_detect(void);
void usb_init_device(void); void usb_init_device(void);
bool usb_drv_connected(void);
#endif