⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 nand_util.c

📁 <B>SMSC USB2.0 Flash硬盘驱动源码</B>
💻 C
📖 第 1 页 / 共 4 页
字号:
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  
  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x10, 0x02,
  0xff, 0xff, 0xff, 0x10, 0x02, 0xaa, 0xaa, 0x97
};



void util_create_bad_128mb_media(void) reentrant
{
  trace0(0, util, 0, "Creating bad 128 mb media...") ;
  // safe-erase media
  util_safe_erase_media() ;

  // allocate a write block
  g_addr_rd_phy_blk = k_block_free ;
  g_addr_zone = 0 ;
  g_addr_log_blk = 0;
  g_addr_page=0 ;
  _media_data(sector_buffer) = g_sector_buffer ;
  
  map_alloc_wr_blk() ;

  // write log 0 pg 0
  memcpy(g_sector_buffer, k_tbl_sm_log_0_pg_0, 512) ;
  memcpy(x_sm_redt_data, k_tbl_sm_log_0_pg_0+512, 16) ;
  trace4(0, util, 0, "writing zone %d logical block %d, page %d, to phy block %d", g_addr_zone, g_addr_log_blk, g_addr_page, g_addr_wr_phy_blk) ;
  _media_write_sector() ;
  util_trace_buffer(g_sector_buffer, 512) ;
  util_trace_buffer(x_sm_redt_data, 16) ;

  // clear extra data and write log 0 pg 1-end of block
  memset(g_sector_buffer, 0xff, 512) ;
  _media_clear_extra_data() ;
  _media_bind_log2phy() ;
  for(g_addr_page=1;g_addr_page<_media_data(pages_per_block);g_addr_page++)
  {
    trace4(0, util, 0, "writing zone %d logical block %d, page %d, to phy block %d", g_addr_zone, g_addr_log_blk, g_addr_page, g_addr_wr_phy_blk) ;
    _media_write_sector() ;
    util_trace_buffer(g_sector_buffer, 512) ;
    util_trace_buffer(x_sm_redt_data, 16) ;
  }

  // write log 1 pg 0-14
  g_addr_log_blk=1 ;
  
  map_alloc_wr_blk() ;
  _media_clear_extra_data() ;
  _media_bind_log2phy() ;
  for(g_addr_page=0; g_addr_page<15; g_addr_page++)
  {
    trace4(0, util, 0, "writing zone %d logical block %d, page %d, to phy block %d", g_addr_zone, g_addr_log_blk, g_addr_page, g_addr_wr_phy_blk) ;
    _media_write_sector() ;
    util_trace_buffer(g_sector_buffer, 512) ;
    util_trace_buffer(x_sm_redt_data, 16) ;
  }

  // write log 1 pg 15
  memcpy(g_sector_buffer, k_tbl_sm_log_1_pg_15, 512) ;
  memcpy(x_sm_redt_data, k_tbl_sm_log_1_pg_15+512, 16) ;
  g_addr_page=15 ;
  trace4(0, util, 0, "writing zone %d logical block %d, page %d, to phy block %d", g_addr_zone, g_addr_log_blk, g_addr_page, g_addr_wr_phy_blk) ;
  _media_write_sector() ;
  util_trace_buffer(g_sector_buffer, 512) ;
  util_trace_buffer(x_sm_redt_data, 16) ;

  // write log 1 pg 16
  memcpy(g_sector_buffer, k_tbl_sm_log_1_pg_16, 512) ;
  memcpy(x_sm_redt_data, k_tbl_sm_log_1_pg_16+512, 16) ;
  g_addr_page=16 ;
  trace4(0, util, 0, "writing zone %d logical block %d, page %d, to phy block %d", g_addr_zone, g_addr_log_blk, g_addr_page, g_addr_wr_phy_blk) ;
  _media_write_sector() ;
  util_trace_buffer(g_sector_buffer, 512) ;
  util_trace_buffer(x_sm_redt_data, 16) ;

  memset(g_sector_buffer, 0x00, 512) ;
  _media_clear_extra_data() ;
  _media_bind_log2phy() ;
  for(g_addr_page=17; g_addr_page<_media_data(pages_per_block);g_addr_page++)
  {
    trace4(0, util, 0, "writing zone %d logical block %d, page %d, to phy block %d", g_addr_zone, g_addr_log_blk, g_addr_page, g_addr_wr_phy_blk) ;
    _media_write_sector() ;
    util_trace_buffer(g_sector_buffer, 512) ;
    util_trace_buffer(x_sm_redt_data, 16) ;
  }

  // write log 2,3 pgs 0-31
  for(g_addr_log_blk=2;g_addr_log_blk<=3;g_addr_log_blk++)
  {
    map_alloc_wr_blk() ;
    _media_bind_log2phy() ;
    for(g_addr_page=0 ;g_addr_page < _media_data(pages_per_block);g_addr_page++)
    {
      trace4(0, util, 0, "writing zone %d logical block %d, page %d, to phy block %d", g_addr_zone, g_addr_log_blk, g_addr_page, g_addr_wr_phy_blk) ;
      _media_write_sector() ;
      util_trace_buffer(g_sector_buffer, 512) ;
      util_trace_buffer(x_sm_redt_data, 16) ;
    }
  }

  // done
  trace0(0, util, 0, "create bad media:  done") ;
  trace0(0, util, 0, "dumping phy blocks 0-5") ;
  for(g_addr_rd_phy_blk=0; g_addr_rd_phy_blk<5; g_addr_rd_phy_blk++)
  {
    util_trace_phy_block() ;
  }

  trace0(0, util, 0, "done") ;
}
#endif // ghosting an optimized format onto blank media
// --------------------------------------------------------------------
// --------------------------------------------------------------------

#define kbm_map_soft_l2p_binding (0x8000)
#define kbm_map_l2p_bits         (0x03FF)
#if 0 

void map_debug(uint8 zone) reentrant
{
  _l2p_map = _log_map(zone);
  _a_map = _assign_map(zone);
#ifdef k_opt_erase_cache
  if( _media_data(options)&kbm_media_data_opt_erase_cache)
  {
    _e_map = _erase_cache(zone);
  }
  else
#endif
  {
    // this simplifies the clearing of the data below
    _e_map = _a_map;
  }

  trace1(0, map, 0, "&_l2p_map    :%04x", ((uint16)_l2p_map)); 
  trace1(0, map, 0, "&_a_map      :%04x", ((uint16)_a_map));
  trace1(0, map, 0, "&_e_map      :%04x", ((uint16)_e_map));

  for(g_addr_wr_phy_blk=0;g_addr_wr_phy_blk<1024;g_addr_wr_phy_blk++)
  {
    g_addr_rd_phy_blk=k_block_free;
    for(g_addr_log_blk=0;g_addr_log_blk<1000;g_addr_log_blk++)
    {
      if( (_l2p_map[g_addr_log_blk]&kbm_map_l2p_bits) ==g_addr_wr_phy_blk)
      {
        g_addr_rd_phy_blk=g_addr_log_blk; 
        break;
      }
    }
    trace4(0, map, 0, "phy_blk:%d - in_use:%c in_cache:%c log_binding:%d", g_addr_wr_phy_blk, (_map_is_phy_blk_used(_a_map,g_addr_wr_phy_blk)?'Y':'N'), (_map_is_phy_blk_used(_e_map,g_addr_wr_phy_blk)?'Y':'N'), g_addr_log_blk);
    for(g_addr_log_blk++;g_addr_log_blk<1000;g_addr_log_blk++)
    {
      if((_l2p_map[g_addr_log_blk]&kbm_map_l2p_bits)==g_addr_wr_phy_blk)
      {
        trace1(0, map, 0, "           - *** also bound to log:%d", g_addr_log_blk);
      }
    }
  }
}
#endif




void util_read_lba(uint32 lba) reentrant
{
  map_lba2addr_rd(lba) ;
  _media_data(sector_buffer)=g_sector_buffer;
  _media_read_sector();
}

xdata _tmp_buf[16];
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
void util_write_lba(uint32 lba) reentrant
{
  memcpy(_tmp_buf, x_sm_redt_data, 16);
  map_write_begin(lba);
  _media_data(sector_buffer)=g_sector_buffer;
  memcpy(x_sm_redt_data, _tmp_buf, 16);
  _media_write_sector();
  map_write_flush();
}

//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
void util_test_hardware_ecc(uint32 lba, uint16 ix_bit) reentrant
{
  trace2(0, util, 0, "util_test_hardware_ecc() - creating 1-bit error in lba %d bit %d", lba, ix_bit) ;
  util_read_lba(lba);
  // there's a bug in _flipbit that won't go higher than 256 bytes.  should be a non-issue for mapper
  if(ix_bit<2048)
  {
    _flpbit((g_sector_buffer), ix_bit);
  }
  else
  {
    _flpbit(((g_sector_buffer)+100), ix_bit);
  }
  util_write_lba(lba);
}

void util_create_2bit_error(uint32 lba) reentrant
{
  util_read_lba(lba);
  _flpbit(g_sector_buffer,0);
  _flpbit(g_sector_buffer,1);
  util_write_lba(lba);
}

void util_create_1bit_error(uint32 lba) reentrant
{
  util_read_lba(lba);
  _flpbit(g_sector_buffer,0);
  util_write_lba(lba);
}


#if 0 
xdata uint8 buffer1[528];
xdata uint8 buffer2[528];
void util_compare_blocks(uint16 blk1, uint16 blk2) reentrant
{
  uint16 offset;

  trace0(0, util, 0, "Compare Block Data") ;
  trace1(0, util, 0, "block 1: %d",blk1) ;
  trace1(0, util, 0, "block 2: %d",blk2) ;
  for(g_addr_page=0;g_addr_page<_media_data(pages_per_block);g_addr_page++)
  {
    trace1(0, util, 0, "--- page %d ---", g_addr_page);
    g_addr_rd_phy_blk=blk1;
    _media_data(sector_buffer)=buffer1;
    _media_read_sector();
    memcpy(buffer1+512, x_sm_redt_data, 16);

    g_addr_rd_phy_blk=blk2;
    _media_data(sector_buffer)=buffer2;
    _media_read_sector();
    memcpy(buffer2+512, x_sm_redt_data, 16);

    if(memcmp(buffer1, buffer2, 512))
    {
      for(offset=0; offset<512;offset++)
      {
        if(buffer1[offset]!=buffer2[offset])
        {
          trace5(0, util, 0, "page data difference at offset %d -- block %d:%02X block %d:%02X", offset, blk1, buffer1[offset], blk2, buffer2[offset]);
        }
      }
    }
    else
    {
      trace0(0, util, 0, "page data identical") ;
    }
    if(memcmp(buffer1+512, buffer2+512, 16))
    {
      trace0(0, util, 0, "extra data differs");
      for(offset=0;offset<16;offset++)
      {
        if(buffer1[offset+512]!=buffer2[offset+512])
        {
          trace5(0, util, 0, "extra data difference at offset %d -- block %d:%02X block %d:%02X", offset, blk1, buffer1[offset+512], blk2, buffer2[offset+512]);
        }
      }
    }
    else
    {
      trace0(0, util, 0, "extra data identical") ;
    }
  }

}




//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
void util_test_copy_double_bit_ecc(uint32 lba) reentrant
{
  uint16 first_rd_blk;
  uint16 org_rd_blk;
  uint16 err_rd_blk;
  trace0(0, util, 0, "------------ 2-bit during copy head (copy before starting user data)") ;
  
  
  map_lba2addr_rd(lba) ;
  trace5(0, util, 0, "------------ creating 2-bit error on block %d:%d[r%d|w%d]:%d", g_addr_zone, g_addr_log_blk, g_addr_rd_phy_blk, g_addr_wr_phy_blk, g_addr_page);
  trace0(0, util, 0, "------------ original data/redundant") ;
  first_rd_blk=org_rd_blk = g_addr_rd_phy_blk;
  util_trace_page();
  
  util_create_2bit_error(lba);

  trace0(0, util, 0, "------------ compare org blk to err blk to verify only difference is 2-bit error");
  map_lba2addr_rd(lba);
  err_rd_blk=g_addr_rd_phy_blk;
  util_compare_blocks(org_rd_blk, err_rd_blk);

  // read n write a block back to simulate "user" data
  trace0(0, util, 0, "------------ writing 'user data'") ;
  util_read_lba(lba+1);
  util_write_lba(lba+1);
  
  trace0(0, util, 0, "------------ compare err blk w/ new blk(verify blk status 'bad' in err blk, verify data status 'bad' in error page, verify ecc data updated in error page, verify page data identical for ALL pages)"); 
  map_lba2addr_rd(lba);
  util_compare_blocks(err_rd_blk, g_addr_rd_phy_blk);

  trace0(0, util, 0, "------------ compare org blk w/ new blk (verify only differnce is in page that has error)") ;
  map_lba2addr_rd(lba);
  util_compare_blocks(org_rd_blk, g_addr_rd_phy_blk);
  

  map_lba2addr_rd(lba+2) ;
  trace5(0, util, 0, "------------ creating 2-bit error on block %d:%d[r%d|w%d]:%d", g_addr_zone, g_addr_log_blk, g_addr_rd_phy_blk, g_addr_wr_phy_blk, g_addr_page);
  org_rd_blk = g_addr_rd_phy_blk;

  util_create_2bit_error(lba+2);

  trace0(0, util, 0, "------------ compare org blk to err blk to verify only difference is 2-bit error");
  map_lba2addr_rd(lba);
  err_rd_blk = g_addr_rd_phy_blk;
  util_compare_blocks(org_rd_blk, err_rd_blk);


  trace0(0, util, 0, "------------ causing copy-tail 2-bit ecc error") ;
  // do a read/write before the 2-bit error to cause problem in copy-tail
  util_read_lba(lba+1);
  util_write_lba(lba+1);
  
  trace0(0, util, 0, "------------ compare err blk w/ new blk(verify blk status 'bad' in err blk, verify data status 'bad' in error page, verify ecc data updated in error page, verify page data identical for ALL pages)"); 
  map_lba2addr_rd(lba+2);
  util_compare_blocks(err_rd_blk, g_addr_rd_phy_blk);

  trace0(0, util, 0, "------------ compare org blk w/ new blk (verify only differnce is in page that has error)") ;
  map_lba2addr_rd(lba+2);
  util_compare_blocks(org_rd_blk, g_addr_rd_phy_blk);

  trace0(0, util, 0, "------------ dump of Final Logical Block") ;
  util_trace_phy_block();
  
  trace0(0, util, 0, "------------ dump of First Logical Block") ;
  g_addr_rd_phy_blk=first_rd_blk;
  util_trace_phy_block();


  if( _media_data(options)&kbm_media_data_opt_erase_cache)
  {
    trace0(0, nand, 0, "flushing erase cache()") ;
    map_erase_cache_flush_all();
  }
  
  mcu_halt();
}

#endif



⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -