コード例 #1
0
ファイル: misc.c プロジェクト: JustinSuzumiya/cap_layer_old
__irq void irq_handler(void)
#endif
{
	UINT32 intr_stat = GETREG(APB_INT_STS);

	if (intr_stat & (INTR_TIMER_1 | INTR_TIMER_2 | INTR_TIMER_3))
	{
		g_timer_interrupt_count++;

		CLEAR_TIMER_INTR(TIMER_CH1);
		CLEAR_TIMER_INTR(TIMER_CH2);
		CLEAR_TIMER_INTR(TIMER_CH3);
		SETREG(APB_INT_STS, INTR_TIMER_1 | INTR_TIMER_2 | INTR_TIMER_3);
	}
	else if (intr_stat & INTR_FLASH)
	{
		ftl_isr();
	}
	else if (intr_stat & INTR_SDRAM)
	{
		UINT32 sdram_interrupt = GETREG(SDRAM_INTSTATUS);

	    SETREG(SDRAM_INTSTATUS, 0xFFFFFFFF);

		// clear the DRAM interrupt flag at the interrupt controller
	    SETREG(APB_INT_STS, INTR_SDRAM);

		if (sdram_interrupt & SDRAM_INT_ECC_CORR)
		{
			// Bit errors were detected and corrected.
			// Usually this is NOT an indication of poor SDRAM quality.
			// If the firmware has a bug due to which SDRAM is written by CPU without the help of mem util functions,
			// ECC correction or ECC failure can happen.

			g_sdram_ecc_count++;
		}

		if (sdram_interrupt & SDRAM_INT_ECC_FAIL)
		{
			// Bit errors were detected but could not be corrected.
			g_sdram_ecc_fail_count++;
		}

		if (sdram_interrupt & SDRAM_INT_ADDR_OF)
		{
			// There was an attempt to access beyond DRAM address boundary.
            uart_printf("Error: SDRAM interrupt occred: attempt to access beyond DRAM address boundary");
            led_blink();
		}
	}
}
コード例 #2
0
ファイル: ftl.c プロジェクト: JustinSuzumiya/cap_layer
void ftl_write(UINT32 const lba, UINT32 const total_sectors)
{
	UINT32 num_sectors_to_write;

	UINT32 sect_offset = lba % SECTORS_PER_PAGE;
	UINT32 remain_sectors = total_sectors;

	while (remain_sectors != 0)
	{
		if (sect_offset + remain_sectors >= SECTORS_PER_PAGE)
		{
			num_sectors_to_write = SECTORS_PER_PAGE - sect_offset;
		}
		else
		{
			num_sectors_to_write = remain_sectors;
		}

		while (g_ftl_write_buf_id == GETREG(SATA_WBUF_PTR));	// bm_write_limit should not outpace SATA_WBUF_PTR

		g_ftl_write_buf_id = (g_ftl_write_buf_id + 1) % NUM_WR_BUFFERS;		// Circular buffer

		SETREG(BM_STACK_WRSET, g_ftl_write_buf_id);	// change bm_write_limit
		SETREG(BM_STACK_RESET, 0x01);				// change bm_write_limit

		sect_offset = 0;
		remain_sectors -= num_sectors_to_write;
	}
}
コード例 #3
0
ファイル: ftl.c プロジェクト: JustinSuzumiya/cap_layer
void ftl_read(UINT32 const lba, UINT32 const total_sectors)
{
	UINT32 num_sectors_to_read;

	UINT32 lpage_addr		= lba / SECTORS_PER_PAGE;	// logical page address
	UINT32 sect_offset 		= lba % SECTORS_PER_PAGE;	// sector offset within the page
	UINT32 sectors_remain	= total_sectors;

	while (sectors_remain != 0)	// one page per iteration
	{
		if (sect_offset + sectors_remain < SECTORS_PER_PAGE)
		{
			num_sectors_to_read = sectors_remain;
		}
		else
		{
			num_sectors_to_read = SECTORS_PER_PAGE - sect_offset;
		}

		UINT32 next_read_buf_id = (g_ftl_read_buf_id + 1) % NUM_RD_BUFFERS;

		while (next_read_buf_id == GETREG(SATA_RBUF_PTR));	// wait if the read buffer is full (slow host)

		SETREG(BM_STACK_RDSET, next_read_buf_id);	// change bm_read_limit
		SETREG(BM_STACK_RESET, 0x02);				// change bm_read_limit

		g_ftl_read_buf_id = next_read_buf_id;

		sect_offset = 0;
		sectors_remain -= num_sectors_to_read;
		lpage_addr++;
	}
}
コード例 #4
0
HANDLER_DEF_END
HANDLER_DEF_BEGIN(pop_r32_handler) {

  uint32_t *stack = (uint32_t *)get_real_address( context->esp, table, WRITE, false );
  context->esp+=sizeof(uint32_t);

  switch( context->code[0] ) {
  case 0x58:
  case 0x59:
  case 0x5A:
  case 0x5B:
  case 0x5C:
  case 0x5D:
  case 0x5E:
  case 0x5F:
    GETREG(context,context->code[0]-0x58) = *stack;
    break;
  default:
    log_message( ERROR, "Invalid opcode for POP r");
    assert(0);
    break;
  }
  context->eip++;
  context->code++;
}
コード例 #5
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opMULUr(void)	// mulu r1,r2
{
	UINT32 op1=GETREG(GET1);
	UINT32 op2=GETREG(GET2);
	UINT64 tmp;
	tmp=(UINT64)op1*(UINT64)op2;
	op2=tmp&0xffffffff;
	tmp>>=32;
	CHECK_ZS(tmp);//z = bad!
	SET_Z( (tmp|op2)==0 );
	SET_OV((tmp!=0));
	SET_CY((tmp!=0));
	SETREG(GET2,op2);
	SETREG(30,tmp);
	return clkIF;
}
コード例 #6
0
ファイル: ftl.c プロジェクト: ClydeProjects/OpenSSD
void ftl_read(UINT32 const lba, UINT32 const num_sectors)
{
    UINT32 remain_sects, num_sectors_to_read;
    UINT32 lpn, sect_offset;
    UINT32 bank, vpn;

    lpn          = lba / SECTORS_PER_PAGE;
    sect_offset  = lba % SECTORS_PER_PAGE;
    remain_sects = num_sectors;

    while (remain_sects != 0)
    {
        if ((sect_offset + remain_sects) < SECTORS_PER_PAGE)
        {
            num_sectors_to_read = remain_sects;
        }
        else
        {
            num_sectors_to_read = SECTORS_PER_PAGE - sect_offset;
        }
        bank = get_num_bank(lpn); // page striping
        vpn  = get_vpn(lpn);
        CHECK_VPAGE(vpn);

        if (vpn != NULL)
        {
            nand_page_ptread_to_host(bank,
                                     vpn / PAGES_PER_BLK,
                                     vpn % PAGES_PER_BLK,
                                     sect_offset,
                                     num_sectors_to_read);
        }
        // The host is requesting to read a logical page that has never been written to.
        else
        {
			UINT32 next_read_buf_id = (g_ftl_read_buf_id + 1) % NUM_RD_BUFFERS;

			#if OPTION_FTL_TEST == 0
			while (next_read_buf_id == GETREG(SATA_RBUF_PTR));	// wait if the read buffer is full (slow host)
			#endif

            // fix bug @ v.1.0.6
            // Send 0xFF...FF to host when the host request to read the sector that has never been written.
            // In old version, for example, if the host request to read unwritten sector 0 after programming in sector 1, Jasmine would send 0x00...00 to host.
            // However, if the host already wrote to sector 1, Jasmine would send 0xFF...FF to host when host request to read sector 0. (ftl_read() in ftl_xxx/ftl.c)
			mem_set_dram(RD_BUF_PTR(g_ftl_read_buf_id) + sect_offset*BYTES_PER_SECTOR,
                         0xFFFFFFFF, num_sectors_to_read*BYTES_PER_SECTOR);

            flash_finish();

			SETREG(BM_STACK_RDSET, next_read_buf_id);	// change bm_read_limit
			SETREG(BM_STACK_RESET, 0x02);				// change bm_read_limit

			g_ftl_read_buf_id = next_read_buf_id;
        }
        sect_offset   = 0;
        remain_sects -= num_sectors_to_read;
        lpn++;
    }
}
コード例 #7
0
ファイル: ftl.c プロジェクト: ClydeProjects/OpenSSD
void ftl_trim(UINT32 const lba, UINT32 const num_sectors)
{
	ASSERT(num_sectors > 0);

	uart_printf("Num sectors: %u", num_sectors);
	uart_printf("SATA_WBUF_PTR: %u", GETREG(SATA_WBUF_PTR));
	uart_printf("g_ftl_write_buf_id: %u", g_ftl_write_buf_id);

	UINT32 next_write_buf_id = (g_ftl_write_buf_id + num_sectors) % NUM_WR_BUFFERS;

	for (UINT32 i=0;i<num_sectors;i++)
	{
		for (UINT32 j=0;j<512/8;j=j+2)
		{
			UINT32 address = read_dram_32(WR_BUF_PTR(g_ftl_write_buf_id)+j*sizeof(UINT32));
			UINT32 reg2 = read_dram_32(WR_BUF_PTR(g_ftl_write_buf_id)+(j+1)*sizeof(UINT32));
			UINT32 count = reg2 & 0xFFFF0000; // Count stored in the first four words.

			// If count is zero. We continue, but also, if address is 48bit.
			// We shouldn't get these unless it is an error.
			if (count == 0 || (reg2 & 0x0000FFFF) > 0) //
				continue;

//			uart_print_hex(address);
//			uart_print_hex(count);
		}

		g_ftl_write_buf_id = (g_ftl_write_buf_id + 1) % NUM_WR_BUFFERS;
	}
	SETREG(BM_STACK_WRSET, next_write_buf_id);	// change bm_read_limit
	SETREG(BM_STACK_RESET, 0x02);				// change bm_read_limi
}
コード例 #8
0
ファイル: uart_dev_msm.c プロジェクト: coyizumi/cs111
static int
msm_bus_ipend(struct uart_softc *sc)
{
	struct msm_uart_softc *u = (struct msm_uart_softc *)sc;
	struct uart_bas *bas = &sc->sc_bas;
	uint32_t isr;
	int ipend;

	uart_lock(sc->sc_hwmtx);

	/* Get ISR status */
	isr = GETREG(bas, UART_DM_MISR);

	ipend = 0;

	/* Uart RX starting, notify upper layer */
	if (isr & UART_DM_RXLEV) {
		u->ier &= ~UART_DM_RXLEV;
		SETREG(bas, UART_DM_IMR, u->ier);
		uart_barrier(bas);
		ipend |= SER_INT_RXREADY;
	}

	/* Stale RX interrupt */
	if (isr & UART_DM_RXSTALE) {
		/* Disable and reset it */
		SETREG(bas, UART_DM_CR, UART_DM_STALE_EVENT_DISABLE);
		SETREG(bas, UART_DM_CR, UART_DM_RESET_STALE_INT);
		uart_barrier(bas);
		ipend |= SER_INT_RXREADY;
	}

	/* TX READY interrupt */
	if (isr & UART_DM_TX_READY) {
		/* Clear  TX Ready */
		SETREG(bas, UART_DM_CR, UART_DM_CLEAR_TX_READY);

		/* Disable TX_READY */
		u->ier &= ~UART_DM_TX_READY;
		SETREG(bas, UART_DM_IMR, u->ier);
		uart_barrier(bas);

		if (sc->sc_txbusy != 0)
			ipend |= SER_INT_TXIDLE;
	}

	if (isr & UART_DM_TXLEV) {
		/* TX FIFO is empty */
		u->ier &= ~UART_DM_TXLEV;
		SETREG(bas, UART_DM_IMR, u->ier);
		uart_barrier(bas);

		if (sc->sc_txbusy != 0)
			ipend |= SER_INT_TXIDLE;
	}

	uart_unlock(sc->sc_hwmtx);
	return (ipend);
}
コード例 #9
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opSHRi(void)	// shr imm5,r2
{
	UINT64 tmp;
	UINT32 count=UI5(OP);
	SET_OV(0);
	SET_CY(0);
	if(count)
	{
		tmp=GETREG(GET2);
		tmp>>=count-1;
		SET_CY(tmp&1);
		tmp>>=1;
		SETREG(GET2,tmp&0xffffffff);
	}
	CHECK_ZS(GETREG(GET2));
	return clkIF;
}
コード例 #10
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opSARi(void)	// sar imm5,r2
{
	UINT64 tmp;
	UINT32 count=UI5(OP);
	SET_OV(0);
	SET_CY(0);
	if(count)
	{
		tmp=GETREG(GET2);
		tmp>>=count-1;
		SET_CY(tmp&1);
		tmp>>=1;
		SETREG(GET2,(tmp&0xffffffff)|(~(((GETREG(GET2)&0x80000000)>>count)-1)));
	}
	CHECK_ZS(GETREG(GET2));
	return clkIF;
}
コード例 #11
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static void opCVTS(void)
{
	float val1=u2f(GETREG(GET1));
	SET_OV(0);
	SET_Z((val1==0.0)?1:0);
	SET_S((val1<0.0)?1:0);
	SETREG(GET2,(INT32)val1);
}
コード例 #12
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opSHRr(void)	// shr r1,r2
{
	UINT64 tmp;
	UINT32 count=GETREG(GET1);
	count&=0x1f;
	SET_OV(0);
	SET_CY(0);
	if(count)
	{
		tmp=GETREG(GET2);
		tmp>>=count-1;
		SET_CY(tmp&1);
		SETREG(GET2,(tmp>>1)&0xffffffff);
	}
	CHECK_ZS(GETREG(GET2));
	return clkIF;
}
コード例 #13
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opSHLi(void)	// shl imm5,r2
{
	UINT64 tmp;
	UINT32 count=UI5(OP);

	SET_OV(0);
	SET_CY(0);

	if(count)
	{
		tmp=GETREG(GET2);
		tmp<<=count;
		CHECK_CY(tmp);
		SETREG(GET2,tmp&0xffffffff);
	}
	CHECK_ZS(GETREG(GET2));
	return clkIF;
}
コード例 #14
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opNOTr(void)	// not r1,r2
{
	UINT32 op1=GETREG(GET1);
	UINT32 op2=~op1;
	CHECK_ZS(op2);
	SET_OV(0);
	SETREG(GET2,op2);
	return clkIF;
}
コード例 #15
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opMOVEA(void)	// movea imm16, reg1, reg2
{
	UINT32 op1=GETREG(GET1);
	UINT32 op2=R_OP(PC);
	PC+=2;
	op2=I16(op2);
	SETREG(GET2,op1+op2);
	return clkIF;
}
コード例 #16
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opMOVHI(void) 	// movhi imm16, reg1 ,reg2
{
	UINT32 op2=R_OP(PC);
	PC+=2;
	op2=UI16(op2);
	op2<<=16;
	SETREG(GET2,GETREG(GET1)+op2);
	return clkIF;
}
コード例 #17
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static void opCVTW(void)
{
	//TODO: CY
	float val1=GETREG(GET1);
	SET_OV(0);
	SET_Z((val1==0.0)?1:0);
	SET_S((val1<0.0)?1:0);
	SETREG(GET2,f2u(val1));
}
コード例 #18
0
void nand_page_read_to_host(UINT32 const bank, UINT32 const vblock, UINT32 const page_num)
{

#if PrintStats
    uart_print_level_1("FR ");
    uart_print_level_1_int(SECTORS_PER_PAGE);
    uart_print_level_1("\r\n");
#endif

    UINT32 row;

    ASSERT(bank < NUM_BANKS);
    ASSERT(vblock < VBLKS_PER_BANK);
    ASSERT(page_num < PAGES_PER_BLK);

    row = (vblock * PAGES_PER_BLK) + page_num;

    uart_print("nand_page_read_to_host bank="); uart_print_int(bank);
    uart_print(", vblock="); uart_print_int(vblock);
    uart_print(", page="); uart_print_int(page_num); uart_print("\r\n");
    uart_print("Reading row="); uart_print_int(row); uart_print("\r\n");

    uart_print("read flash: bank="); uart_print_int(bank);
    uart_print(", page="); uart_print_int(row); uart_print("\r\n");

    SETREG(FCP_CMD, FC_COL_ROW_READ_OUT);
    SETREG(FCP_DMA_ADDR, RD_BUF_PTR(g_ftl_read_buf_id));
    SETREG(FCP_DMA_CNT, BYTES_PER_PAGE);

    SETREG(FCP_COL, 0);
#if OPTION_FTL_TEST == TRUE
    SETREG(FCP_OPTION, FO_P | FO_E);
#else
    SETREG(FCP_OPTION, FO_P | FO_E | FO_B_SATA_R);
#endif
    SETREG(FCP_ROW_L(bank), row);
    SETREG(FCP_ROW_H(bank), row);

    g_ftl_read_buf_id = (g_ftl_read_buf_id + 1) % NUM_RD_BUFFERS;

    #if OPTION_FTL_TEST == FALSE
    {
        int count=0;
        while (1) {
            count ++;
            if (count > 100000) {
                uart_print_level_1("Warning1 in nand_page_read_to_host\r\n");
                count=0;
            }
            UINT32 sata_id = GETREG(SATA_RBUF_PTR);
            if (g_ftl_read_buf_id != sata_id)
                break;
        }
    }
    #endif
    flash_issue_cmd(bank, RETURN_ON_ISSUE);
}
コード例 #19
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opINW(void)	// in.w disp16[reg1],reg2
{
	UINT32 tmp=R_OP(PC);
	PC+=2;
	tmp=D16(tmp);
	tmp+=GETREG(GET1);
	tmp=RIO_W(tmp&~3);
	SETREG(GET2,tmp);
	return clkIF+clkMEM;
}
コード例 #20
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opCMPi(void)	// cmpi imm5,r2
{
	UINT32 op1=I5(OP);
	UINT32 op2=GETREG(GET2);
	UINT64 res=(UINT64)op2-(UINT64)op1;
	CHECK_CY(res);
	CHECK_OVSUB(op1,op2,res);
	CHECK_ZS(res);
	return clkIF;
}
コード例 #21
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opSHLr(void)	// shl r1,r2
{
	UINT64 tmp;
	UINT32 count=GETREG(GET1);
	count&=0x1f;

	SET_OV(0);
	SET_CY(0);

	if(count)
	{
		tmp=GETREG(GET2);
		tmp<<=count;
		CHECK_CY(tmp);
		SETREG(GET2,tmp&0xffffffff);
		CHECK_ZS(GETREG(GET2));
	}
	return clkIF;
}
コード例 #22
0
ファイル: ftl - Copy.c プロジェクト: wurikiji/tutorial2-dev
static void format(void)
{
	// This function is called upon the very first power-up of the SSD.
	// This function does the low-level format (i.e. FTL level format) of SSD.
	// A typical FTL would create its mapping table and the list of free blocks.
	// However, this example does nothing more than erasing all the free blocks.
	//
	// This function may take a long time to complete. For example, erasing all the flash blocks can
	// take more than ten seconds depending on the total density.
	// In that case, the host will declare time-out error. (no response from SSD for a long time)
	// A suggested solution to this problem is:
	// When you power-up the SSD for the first time, connect the power cable but not the SATA cable.
	// At the end of this function, you can put a call to led(1) to indicate that the low level format
	// has been completed. When the LED is on, turn off the power, connect the SATA cable, and turn on
	// the power again.

	UINT32 vblk_offset, bank;

	for (vblk_offset = 1; vblk_offset < VBLKS_PER_BANK; vblk_offset++)
	{
		for (bank = 0; bank < NUM_BANKS; bank++)
		{
			if (is_bad_block(bank, vblk_offset))
				continue;

			// You do not need to set the values of FCP_DMA_ADDR, FCP_DMA_CNT and FCP_COL for FC_ERASE.

			SETREG(FCP_CMD, FC_ERASE);
			SETREG(FCP_BANK, REAL_BANK(bank));
			SETREG(FCP_OPTION, FO_P);
			SETREG(FCP_ROW_L(bank), vblk_offset * PAGES_PER_VBLK);
			SETREG(FCP_ROW_H(bank), vblk_offset * PAGES_PER_VBLK);

			// You should not issue a new command when Waiting Room is not empty.

			while ((GETREG(WR_STAT) & 0x00000001) != 0);

			// By writing any value to FCP_ISSUE, you put FC_ERASE into Waiting Room.
			// The value written to FCP_ISSUE does not have any meaning.

			SETREG(FCP_ISSUE, NULL);
		}
	}

	// In general, write_format_mark() should be called upon completion of low level format in order to prevent
	// format() from being called again.
	// However, since the tutorial FTL does not support power off recovery,
	// format() should be called every time.
	
	init_meta_data();
	ftl_flush();
	write_format_mark();
	led(1);
}
コード例 #23
0
ファイル: sata_cmd.c プロジェクト: twoblock/BlockDesigner
void ata_check_power_mode(UINT32 lba, UINT32 sector_count)
{
	UINT32 fis_type = FISTYPE_REGISTER_D2H;
	UINT32 flags = B_IRQ;
	UINT32 status = B_DRDY | BIT4;

	SETREG(SATA_FIS_D2H_0, fis_type | (flags << 8) | (status << 16));
	SETREG(SATA_FIS_D2H_1, GETREG(SATA_FIS_H2D_1));
	SETREG(SATA_FIS_D2H_2, GETREG(SATA_FIS_H2D_2) & 0x00FFFFFF);
	SETREG(SATA_FIS_D2H_3, 0x000000FF);
	SETREG(SATA_FIS_D2H_4, 0);
	SETREG(SATA_FIS_D2H_LEN, 5);

	if ((GETREG(SATA_PHY_STATUS) & 0xF0F) != 0x103)
	{
		return;
	}

	SETREG(SATA_CTRL_2, SEND_NON_DATA_FIS);
}
コード例 #24
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opADDi(void)	// add imm5,r2
{
	UINT32 op1=I5(OP);
	UINT32 op2=GETREG(GET2);
	UINT64 res=(UINT64)op2+(UINT64)op1;
	CHECK_CY(res);
	CHECK_OVADD(op1,op2,res);
	CHECK_ZS(res);
	SETREG(GET2,res);
	return clkIF;
}
コード例 #25
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opLDH(void)	// ld.h disp16[reg1],reg2
{
	UINT32 tmp=R_OP(PC);
	PC+=2;
	tmp=D16(tmp);
	tmp+=GETREG(GET1);
	tmp=R_H(tmp&~1);
	tmp|=(tmp&0x8000)?0xffff0000:0;
	SETREG(GET2,tmp);
	return clkIF+clkMEM;
}
コード例 #26
0
ファイル: ftl - Copy.c プロジェクト: wurikiji/tutorial2-dev
static BOOL32 check_format_mark(void)
{
	// This function reads a flash page from (bank #0, block #0) in order to check whether the SSD is formatted or not.

#ifdef __GNUC__
	extern UINT32 size_of_firmware_image;
	UINT32 firmware_image_pages = (((UINT32) (&size_of_firmware_image)) + BYTES_PER_FW_PAGE - 1) / BYTES_PER_FW_PAGE;
#else
	extern UINT32 Image$$ER_CODE$$RO$$Length;
	extern UINT32 Image$$ER_RW$$RW$$Length;
	UINT32 firmware_image_bytes = ((UINT32) &Image$$ER_CODE$$RO$$Length) + ((UINT32) &Image$$ER_RW$$RW$$Length);
	UINT32 firmware_image_pages = (firmware_image_bytes + BYTES_PER_FW_PAGE - 1) / BYTES_PER_FW_PAGE;
#endif

	UINT32 format_mark_page_offset = FW_PAGE_OFFSET + firmware_image_pages;
	UINT32 temp;

	flash_clear_irq();	// clear any flash interrupt flags that might have been set

	SETREG(FCP_CMD, FC_COL_ROW_READ_OUT);
	SETREG(FCP_BANK, REAL_BANK(0));
	SETREG(FCP_OPTION, FO_E);
	SETREG(FCP_DMA_ADDR, FTL_BUF_ADDR); 	// flash -> DRAM
	SETREG(FCP_DMA_CNT, BYTES_PER_SECTOR);
	SETREG(FCP_COL, 0);
	SETREG(FCP_ROW_L(0), format_mark_page_offset);
	SETREG(FCP_ROW_H(0), format_mark_page_offset);

	// At this point, we do not have to check Waiting Room status before issuing a command,
	// because scan list loading has been completed just before this function is called.
	SETREG(FCP_ISSUE, NULL);

	// wait for the FC_COL_ROW_READ_OUT command to be accepted by bank #0
	while ((GETREG(WR_STAT) & 0x00000001) != 0);

	// wait until bank #0 finishes the read operation
	while (BSP_FSM(0) != BANK_IDLE);

	// Now that the read operation is complete, we can check interrupt flags.
	temp = BSP_INTR(0) & FIRQ_ALL_FF;

	// clear interrupt flags
	CLR_BSP_INTR(0, 0xFF);

	if (temp != 0)
	{
		return FALSE;	// the page contains all-0xFF (the format mark does not exist.)
	}
	else
	{
		return TRUE;	// the page contains something other than 0xFF (it must be the format mark)
	}
}
コード例 #27
0
ファイル: v810.c プロジェクト: broftkd/historic-mess
static UINT32 opXORI(void)	// xori imm16,r1,r2
{
	UINT32 op1=GETREG(GET1);
	UINT32 op2=R_OP(PC);
	PC+=2;
	op2=UI16(op2);
	op2^=op1;
	CHECK_ZS(op2);
	SET_OV(0);
	SET_S(0);
	SETREG(GET2,op2);
	return clkIF;
}
コード例 #28
0
ファイル: ftl - Copy.c プロジェクト: wurikiji/tutorial2-dev
void ftl_read(UINT32 const lba, UINT32 const total_sectors)				//modified by GYUHWA
{
	UINT32 sect_offset, count,  next_read_buf_id;
	sect_offset = lba % SECTORS_PER_PAGE;					//sect_offset : offset of RD_BUFFER
	for(count = 0; count < total_sectors; count++)
	{
		ftl_read_sector(lba+count, sect_offset++);			//read one sector
		if(sect_offset == SECTORS_PER_PAGE )				//One page is read complete
		{
			next_read_buf_id = (g_ftl_read_buf_id + 1) % NUM_RD_BUFFERS;

			#if OPTION_FTL_TEST == 0
			while (next_read_buf_id == GETREG(SATA_RBUF_PTR));	// wait if the read buffer is full (slow host)
			#endif

			g_ftl_read_buf_id = (g_ftl_read_buf_id + 1) % NUM_RD_BUFFERS;
			while (GETREG(MON_CHABANKIDLE) != 0);	// This while() loop ensures that Waiting Room is empty and all the banks are idle.
				
		
			SETREG(BM_STACK_RDSET, next_read_buf_id);	// change bm_read_limit
			SETREG(BM_STACK_RESET, 0x02);				// change bm_read_limit
			sect_offset = 0;
		}
	}
	if(sect_offset != 0)								//no complete page -> make read command, example : only 4 sector read command
	{
		next_read_buf_id = (g_ftl_read_buf_id + 1) % NUM_RD_BUFFERS;

		#if OPTION_FTL_TEST == 0
		while (next_read_buf_id == GETREG(SATA_RBUF_PTR));	// wait if the read buffer is full (slow host)
		#endif
		g_ftl_read_buf_id = (g_ftl_read_buf_id + 1) % NUM_RD_BUFFERS;
			while (GETREG(MON_CHABANKIDLE) != 0);	// This while() loop ensures that Waiting Room is empty and all the banks are idle.
		
SETREG(BM_STACK_RDSET, next_read_buf_id);	// change bm_read_limit
			SETREG(BM_STACK_RESET, 0x02);				// change bm_read_limit			// change bm_read_limit
	}
}
コード例 #29
0
ファイル: uart_dev_imx.c プロジェクト: 2asoft/freebsd
static u_int
imx_uart_getbaud(struct uart_bas *bas)
{
	uint32_t rate, ubir, ubmr;
	u_int baud, blo, bhi, i;
	static const u_int predivs[] = {6, 5, 4, 3, 2, 1, 7, 1};
	static const u_int std_rates[] = {
		9600, 14400, 19200, 38400, 57600, 115200, 230400, 460800, 921600
	};

	/*
	 * Get the baud rate the hardware is programmed for, then search the
	 * table of standard baud rates for a number that's within 3% of the
	 * actual rate the hardware is programmed for.  It's more comforting to
	 * see that your console is running at 115200 than 114942.  Note that
	 * here we cannot make a simplifying assumption that the predivider and
	 * numerator are 1 (like we do when setting the baud rate), because we
	 * don't know what u-boot might have set up.
	 */
	i = (GETREG(bas, REG(UFCR)) & IMXUART_UFCR_RFDIV_MASK) >>
	    IMXUART_UFCR_RFDIV_SHIFT;
	rate = imx_ccm_uart_hz() / predivs[i];
	ubir = GETREG(bas, REG(UBIR)) + 1;
	ubmr = GETREG(bas, REG(UBMR)) + 1;
	baud = ((rate / 16 ) * ubir) / ubmr;

	blo = (baud * 100) / 103;
	bhi = (baud * 100) / 97;
	for (i = 0; i < nitems(std_rates); i++) {
		rate = std_rates[i];
		if (rate >= blo && rate <= bhi) {
			baud = rate;
			break;
		}
	}

	return (baud);
}
コード例 #30
0
ファイル: gc_ftl.c プロジェクト: woojj12/ftl_delta
// BSP interrupt service routine
void ftl_isr(void)
{
	UINT32 bank;
	UINT32 bsp_intr_flag;

	uart_print("BSP interrupt occured...");
	// interrupt pending clear (ICU)
	SETREG(APB_INT_STS, INTR_FLASH);

	for (bank = 0; bank < NUM_BANKS; bank++) {
		while (BSP_FSM(bank) != BANK_IDLE);
		// get interrupt flag from BSP
		bsp_intr_flag = BSP_INTR(bank);

		if (bsp_intr_flag == 0) {
			continue;
		}
		UINT32 fc = GETREG(BSP_CMD(bank));
		// BSP clear
		CLR_BSP_INTR(bank, bsp_intr_flag);

		// interrupt handling
		if (bsp_intr_flag & FIRQ_DATA_CORRUPT) {
			uart_printf("BSP interrupt at bank: 0x%x", bank);
			uart_print("FIRQ_DATA_CORRUPT occured...");
		}
		if (bsp_intr_flag & (FIRQ_BADBLK_H | FIRQ_BADBLK_L)) {
			uart_printf("BSP interrupt at bank: 0x%x", bank);
			if (fc == FC_COL_ROW_IN_PROG || fc == FC_IN_PROG || fc == FC_PROG) {
				uart_print("find runtime bad block when block program...");
			}
			else {
				uart_printf("find runtime bad block when block erase...vblock #: %d", GETREG(BSP_ROW_H(bank)) / PAGES_PER_BLK);
				ASSERT(fc == FC_ERASE);
			}
		}
	}
}