Example #1
0
void prtn_set_addr(byte* bootSec, dword partition_addr)
{
  int resSecs;  //# of reserved sectors
  byte numFATs; //# of FATs
  word max_root_entries; /* max# of root dir entries */
  word secs_per_FAT;
  byte secs_per_clus;
  
  secs_per_clus = bootSec[0x0d];
  resSecs = ((bootSec[0x0f]<<8)&0xFF00)|(bootSec[0x0e]&0x00FF);
  max_root_entries = ((bootSec[0x12]<<8)&0xFF00)|(bootSec[0x11]&0x00FF);
  numFATs = bootSec[0x10];
  secs_per_FAT = ((bootSec[0x17]<<8)&0xFF00)|(bootSec[0x16]&0x00FF);
  
  prtn.bytes_per_sec = ((bootSec[0x0c]<<8)&0xFF00)|(bootSec[0x0b]&0x00FF);
  prtn.root_dir_addr = partition_addr + ((long)resSecs + (long)secs_per_FAT*(long)numFATs)*(long)(prtn.bytes_per_sec);
  prtn.FAT_addr =  partition_addr + (long)resSecs*(long)(prtn.bytes_per_sec);
  prtn.data_addr = prtn.root_dir_addr + (max_root_entries*32);
  prtn.clus_size = prtn.bytes_per_sec * secs_per_clus;
  prtn.FAT_size = prtn.bytes_per_sec * secs_per_FAT;
  prtn.root_dir_size = max_root_entries * 16;
  
  #if DEBUG
  pmsg("Bytes per sector: "); disword_dec(prtn.bytes_per_sec); pmsg("\r\n");
  pmsg("Number of reserved sectors: "); disword_dec(resSecs); pmsg("\r\n");
  pmsg("root dir at: 0x"); disdword(prtn.root_dir_addr); pmsg("\r\n");
  pmsg("FAT at: 0x"); disdword(prtn.FAT_addr); pmsg("\r\n");
  pmsg("Data starts at: 0x"); disdword(prtn.data_addr); pmsg("\r\n");
  #endif
}
Example #2
0
byte read_block(byte* buf,dword addr)
{
  int i;
  byte c;
  byte r1;
  
  if (addr % 512 != 0)
  {
    #if DEBUG
    pmsg("read_block: Address 0x"); disdword(addr);
      pmsg("is not aligned to a 512 byte block!\r\n");
    #endif
    return 0;
  }
  
  #if DEBUG
  pmsg("Reading block at address 0x"); disdword(addr); pmsg("\r\n");
  #endif
  
  r1=CMD(17,addr);
  
  for (i=0;i<50;i++)     // wait until the data is found
  {
    if (r1==0x00) break;
    r1 = SPI_Byte(0xFF);
  }
  if (r1!=0x00)
  {
    #if DEBUG
    pmsg("Read block timed out!\r\n");
    #endif
    return 0; 
  }
  
  
  c = SPI_Byte(0xFF);
  while (c!=0xFE)
  {
    c=SPI_Byte(0xFF);
  } // wait for the "data follows" code
  for (i=0;i<512;i++)
  {    
    *(buf++)=SPI_Byte(0xFF); 
  }
  c=SPI_Byte(0xFF);
  c=SPI_Byte(0xFF);  // dummy bytes to clear any queues
  return 1;
}
Example #3
0
// returns address of first empty root dir entry
dword get_empty_dir_entry(byte* buf)
{
  byte i,j;
  byte b; 
  
  for (i=0;i<32;i++)
  {
    b = read_block(buf, prtn.root_dir_addr + i*512);
    for(j=0;j<16;j++)
    {
      if(buf[j*32] == 0x00 || buf[j*32] == 0xE5)
      {
        #if DEBUG
        pmsg("found empty direntry at addr: 0x"); disdword(prtn.root_dir_addr + i*512 + j*32); pmsg("\r\n");
        #endif
        return (prtn.root_dir_addr + i*512 + j*32);
      }
    }
  }
  
  #if DEBUG
  pmsg("Failed to find empty directory entry!\r\n");
  #endif
  return 0;
}
Example #4
0
byte create_dir_entry(dir_entry_t* de, char* filename, byte fn_length, byte* buf)
{
  dword dir_entry_addr;

  memmove(de->filename, filename, fn_length);
  de->attributes = NEW_FILE_ATTR;
  de->filesize = 0;
  memset(de->unused_attr, 0, 14);
  
  dir_entry_addr = get_empty_dir_entry(buf);
  #if DEBUG
  pmsg("get_direntry returned: 0x"); disdword(dir_entry_addr); pmsg("\r\n");
  #endif
  if (!dir_entry_addr) 
  {
    #if DEBUG
    pmsg("Couldn't find empty direntry!\r\n");
    #endif
    return 0;
  }
  de->entry_addr = dir_entry_addr;
  
  // when direntry is allocated cluster is not yet entered
  de->first_cluster = 0x0000;
  
  return 1;
}
Example #5
0
byte write_block(byte* data, dword addr)
{
  byte c;
  short i;
  
  if (addr % 512 != 0)
  {
    #if DEBUG
    pmsg("write_block: Address 0x"); disdword(addr);
      pmsg("is not aligned to a 512 byte block!\r\n");
    #endif
    return 0;
  }
  
  #if DEBUG
  pmsg("Writing block at address 0x"); disdword(addr); pmsg("\r\n");
  #endif
  
  if (CMD(24,addr) != 0) 
  {
    #if DEBUG
    pmsg("Failed to write block!\r\n");
    #endif 
    return 0;
  }
  c=SPI_Byte(0xFF); c=SPI_Byte(0xFF); c=SPI_Byte(0xFE); // lead in to actual data
  for (i=0;i<BLOCKSIZE;i++) c=SPI_Byte(data[i]);
  c=SPI_Byte(0xFF); c=SPI_Byte(0xFF); // dummy before response recieved
  c=SPI_Byte(0xFF); c&=0x1F; // bit mask for write error codes 
  // see http://elm-chan.org/docs/mmc/mmc_e.html
  if (c!=0x05)
  {
    #if DEBUG
    pmsg("Failed to write block!\r\n");
    #endif
    return 0; 
  }
  while (SPI_Byte(0xFF)!=0xFF);  // block until write finished
  
  return 1;
}
Example #6
0
byte initFAT(byte* buf)
{
  byte i;
  dword partition_addr;

  i = read_block(buf,0);
  if(!i){
    #if DEBUG
    pmsg("read timed out");
    #endif
    return 0;
  }
  
  if (buf[PARTENTRY1 + 0x04] != 0x04 && buf[PARTENTRY1 + 0x04] != 0x06)
  {
    #if DEBUG
    pmsg("drive is not FAT16!\r\n");
    #endif
    return 0;
  }
  
  partition_addr = ((dword)buf[PARTENTRY1 + 0x08] |
                    (dword)buf[PARTENTRY1 + 0x09] << 8 |
                    (dword)buf[PARTENTRY1 + 0x0a] << 16 |
                    (dword)buf[PARTENTRY1 + 0x0b] << 24) * 512;
  #if DEBUG
  pmsg("partition_addr is: "); disdword(partition_addr); pmsg("\r\n");
  #endif
  if (!read_block(buf, partition_addr))
  {
    #if DEBUG
    pmsg("couldn't read start of partition!\r\n"); 
    #endif
    return 0;
  }
  
  prtn_set_addr(buf, partition_addr);  
  return 1;
}