OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [tags/] [rel-0-3-0-rc2/] [or1ksim/] [peripheral/] [atadevice-cmdi.c] - Diff between revs 1748 and 1751

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 1748 Rev 1751
Line 32... Line 32...
 
 
/* Package includes */
/* Package includes */
#include "atadevice-cmdi.h"
#include "atadevice-cmdi.h"
#include "atahost.h"
#include "atahost.h"
#include "atacmd.h"
#include "atacmd.h"
#include "debug.h"
 
#include "sched.h"
#include "sched.h"
 
 
 
 
DEFAULT_DEBUG_CHANNEL (ata);
 
 
 
/* FIXME: If device0 is not selected and then an interrupt occurs and
/* FIXME: If device0 is not selected and then an interrupt occurs and
 * then it is selected, the interrupt should be delivered, but I just drop it
 * then it is selected, the interrupt should be delivered, but I just drop it
 * (same goes for device 1). */
 * (same goes for device 1). */
static void
static void
ata_cmd_complete (void *dat)
ata_cmd_complete (void *dat)
{
{
  struct ata_device *dev = dat;
  struct ata_device *dev = dat;
 
 
  TRACE ("Cmd completed intrq: %i, dev: %i\n", dev->sigs.intrq,
 
         dev->internals.dev ? 1 : 0);
 
 
 
  dev->regs.status &= ~ATA_SR_BSY;
  dev->regs.status &= ~ATA_SR_BSY;
 
 
  if (dev->regs.device_control & ATA_DCR_IEN)
  if (dev->regs.device_control & ATA_DCR_IEN)
    return;
    return;
 
 
Line 123... Line 117...
ata_read_sect (struct ata_device *dev)
ata_read_sect (struct ata_device *dev)
{
{
  if (!dev->internals.nr_sect)
  if (!dev->internals.nr_sect)
    return;
    return;
 
 
  TRACE ("Reading sector from %" PRId32 "\n", dev->internals.lba);
 
 
 
  /* set the file-positon pointer to the start of the sector    */
  /* set the file-positon pointer to the start of the sector    */
  fseek (dev->conf.stream, dev->internals.lba, SEEK_SET);
  fseek (dev->conf.stream, dev->internals.lba, SEEK_SET);
 
 
  /* get the bytes from the stream                              */
  /* get the bytes from the stream                              */
  fread (dev->internals.dbuf, BYTES_PER_SECTOR, 1, dev->conf.stream);
  fread (dev->internals.dbuf, BYTES_PER_SECTOR, 1, dev->conf.stream);
Line 154... Line 146...
    {
    {
      dev->regs.status = ATA_SR_DRDY;
      dev->regs.status = ATA_SR_DRDY;
      return;
      return;
    }
    }
 
 
  TRACE ("Writeing sector to %" PRId32 "\n", dev->internals.lba);
 
 
 
  /* set the file-positon pointer to the start of the sector    */
  /* set the file-positon pointer to the start of the sector    */
  fseek (dev->conf.stream, dev->internals.lba, SEEK_SET);
  fseek (dev->conf.stream, dev->internals.lba, SEEK_SET);
 
 
  /* get the bytes from the stream                              */
  /* get the bytes from the stream                              */
  fwrite (dev->internals.dbuf, BYTES_PER_SECTOR, 1, dev->conf.stream);
  fwrite (dev->internals.dbuf, BYTES_PER_SECTOR, 1, dev->conf.stream);
Line 211... Line 201...
  A T A _ E X E C U T E _ D E V I C E _ D I A G N O S T I C S
  A T A _ E X E C U T E _ D E V I C E _ D I A G N O S T I C S
*/
*/
void
void
ata_execute_device_diagnostics_cmd (struct ata_device *device)
ata_execute_device_diagnostics_cmd (struct ata_device *device)
{
{
  /* print debug information                                          */
 
  TRACE ("executing command 'execute_device_diagnostics'\n");
 
 
 
  /* clear SRST bit, if set                                           */
  /* clear SRST bit, if set                                           */
  device->regs.device_control &= ~ATA_DCR_RST;
  device->regs.device_control &= ~ATA_DCR_RST;
 
 
  /* content of features register is undefined                        */
  /* content of features register is undefined                        */
 
 
Line 264... Line 251...
  A T A _ D E V I C E _ R E S E T
  A T A _ D E V I C E _ R E S E T
*/
*/
static void
static void
ata_device_reset_cmd (struct ata_device *device)
ata_device_reset_cmd (struct ata_device *device)
{
{
  /* print debug information                                          */
 
  TRACE ("executing command 'device reset'\n");
 
 
 
  if (!device->conf.packet)
  if (!device->conf.packet)
    WARN ("executing DEVICE_RESET on non-packet device.");
    {
 
      fprintf( stderr, "Warning: executing DEVICE_RESET on non-packet "
 
               "device\n");
 
    }
 
 
  ata_execute_device_diagnostics_cmd (device);
  ata_execute_device_diagnostics_cmd (device);
}
}
 
 
 
 
Line 285... Line 272...
  unsigned char *chksum_buf, chksum;
  unsigned char *chksum_buf, chksum;
  unsigned short *buf;
  unsigned short *buf;
  int n;
  int n;
  unsigned int tmp;
  unsigned int tmp;
 
 
  /* print debug information                                          */
 
  TRACE ("ata_device executing command 'identify device'\n");
 
 
 
  /* reset databuffer                                                 */
  /* reset databuffer                                                 */
  device->internals.dbuf_cnt = 256;
  device->internals.dbuf_cnt = 256;
  device->internals.dbuf_ptr = device->internals.dbuf;
  device->internals.dbuf_ptr = device->internals.dbuf;
  device->internals.end_t_func = NULL;
  device->internals.end_t_func = NULL;
 
 
Line 360... Line 344...
      /*
      /*
         This is a PACKET device.
         This is a PACKET device.
         Respond by placing PACKET Command feature set signature in block registers.
         Respond by placing PACKET Command feature set signature in block registers.
         Abort command.
         Abort command.
       */
       */
      TRACE ("'identify_device' command: This is a PACKET device\n");
 
 
 
      ata_set_device_signature (device, 1);
      ata_set_device_signature (device, 1);
      device->regs.status = ATA_SR_ERR;
      device->regs.status = ATA_SR_ERR;
      device->regs.error = ATA_ERR_ABT;
      device->regs.error = ATA_ERR_ABT;
    }
    }
Line 928... Line 911...
  A T A _ I N I T I A L I Z E _ D E V I C E _ P A R A M E T E R S
  A T A _ I N I T I A L I Z E _ D E V I C E _ P A R A M E T E R S
*/
*/
static void
static void
ata_initialize_device_parameters_cmd (struct ata_device *device)
ata_initialize_device_parameters_cmd (struct ata_device *device)
{
{
  /* print debug information                                          */
 
  TRACE ("executing command 'initialize device parameters'\n");
 
 
 
  device->internals.sectors_per_track = device->regs.sector_count;
  device->internals.sectors_per_track = device->regs.sector_count;
  device->internals.heads_per_cylinder = device->regs.device_head & ATA_DHR_H;
  device->internals.heads_per_cylinder = device->regs.device_head & ATA_DHR_H;
 
 
  /* set status register bits                                         */
  /* set status register bits                                         */
  device->regs.status = ATA_SR_BSY | ATA_SR_DRDY;
  device->regs.status = ATA_SR_BSY | ATA_SR_DRDY;
Line 948... Line 928...
ata_read_sectors_cmd (struct ata_device *device)
ata_read_sectors_cmd (struct ata_device *device)
{
{
  size_t sector_count;
  size_t sector_count;
  uint32_t lba;
  uint32_t lba;
 
 
  /* print debug information                                          */
 
  TRACE ("executing command 'read sectors'\n");
 
 
 
  /* check if this is a NON-PACKET device                             */
  /* check if this is a NON-PACKET device                             */
  if (device->conf.packet)
  if (device->conf.packet)
    {
    {
      /*
      /*
         This is a PACKET device.
         This is a PACKET device.
         Respond by placing PACKET Command feature set signature in block registers.
         Respond by placing PACKET Command feature set signature in block registers.
         Abort command.
         Abort command.
       */
       */
      TRACE ("'identify_device' command: This is a PACKET device\n");
 
 
 
      ata_set_device_signature (device, 1);
      ata_set_device_signature (device, 1);
      device->regs.status = ATA_SR_ERR | ATA_SR_DRDY;
      device->regs.status = ATA_SR_ERR | ATA_SR_DRDY;
      device->regs.error = ATA_ERR_ABT;
      device->regs.error = ATA_ERR_ABT;
      return;
      return;
    }
    }
Line 975... Line 950...
  else
  else
    sector_count = device->regs.sector_count;
    sector_count = device->regs.sector_count;
 
 
  lba = ata_calc_lba (device);
  lba = ata_calc_lba (device);
 
 
  TRACE ("Reading from lba %i, %i sectors\n", lba, sector_count);
 
 
 
  /* check if sector within bounds                                  */
  /* check if sector within bounds                                  */
  if (lba >= device->conf.size_sect)
  if (lba >= device->conf.size_sect)
    {
    {
      /* invalid sector address                                     */
      /* invalid sector address                                     */
      /* set the status & error registers                           */
      /* set the status & error registers                           */
      TRACE ("Sector read out-of-bounds: %i >= %i\n", lba,
 
             device->conf.size_sect);
 
      device->regs.status = ATA_SR_DRDY | ATA_SR_ERR;
      device->regs.status = ATA_SR_DRDY | ATA_SR_ERR;
      device->regs.error = ATA_ERR_IDNF;
      device->regs.error = ATA_ERR_IDNF;
      return;
      return;
    }
    }
 
 
Line 1007... Line 978...
  A T A _ R E A D _ N A T I V E _ M A X _ A D D R
  A T A _ R E A D _ N A T I V E _ M A X _ A D D R
*/
*/
static void
static void
ata_read_native_max_addr (struct ata_device *dev)
ata_read_native_max_addr (struct ata_device *dev)
{
{
  TRACE ("executing command 'read native max addr'\n");
 
  // FIXME: Left shift????
  // FIXME: Left shift????
  ata_set_sect (dev, dev->conf.size << 11);
  ata_set_sect (dev, dev->conf.size << 11);
 
 
  dev->regs.status = ATA_SR_DRDY | ATA_SR_BSY;
  dev->regs.status = ATA_SR_DRDY | ATA_SR_BSY;
}
}
Line 1023... Line 993...
ata_write_sectors (struct ata_device *dev)
ata_write_sectors (struct ata_device *dev)
{
{
  size_t sector_count;
  size_t sector_count;
  uint32_t lba;
  uint32_t lba;
 
 
  TRACE ("executing command 'write sectors'\n");
 
 
 
  if (dev->conf.packet)
  if (dev->conf.packet)
    {
    {
      ata_set_device_signature (dev, 1);
      ata_set_device_signature (dev, 1);
      dev->regs.status = ATA_SR_ERR | ATA_SR_DRDY;
      dev->regs.status = ATA_SR_ERR | ATA_SR_DRDY;
      dev->regs.error = ATA_ERR_ABT;
      dev->regs.error = ATA_ERR_ABT;
Line 1041... Line 1009...
  else
  else
    sector_count = dev->regs.sector_count;
    sector_count = dev->regs.sector_count;
 
 
  lba = ata_calc_lba (dev);
  lba = ata_calc_lba (dev);
 
 
  TRACE ("Writeing to lba %i, %i sectors\n", lba, sector_count);
 
 
 
  /* check if sector within bounds                                  */
  /* check if sector within bounds                                  */
  if (lba >= dev->conf.size_sect)
  if (lba >= dev->conf.size_sect)
    {
    {
      /* invalid sector address                                     */
      /* invalid sector address                                     */
      /* set the status & error registers                           */
      /* set the status & error registers                           */
      TRACE ("Sector read out-of-bounds: %i >= %i\n", lba,
 
             dev->conf.size_sect);
 
      dev->regs.status = ATA_SR_DRDY | ATA_SR_ERR;
      dev->regs.status = ATA_SR_DRDY | ATA_SR_ERR;
      dev->regs.error = ATA_ERR_IDNF;
      dev->regs.error = ATA_ERR_IDNF;
      return;
      return;
    }
    }
 
 
Line 1080... Line 1044...
      switch (dev->regs.sector_count >> 3)
      switch (dev->regs.sector_count >> 3)
        {
        {
        case 0:          /* Set default */
        case 0:          /* Set default */
          break;
          break;
        case 1:         /* Set PIO mode */
        case 1:         /* Set PIO mode */
          TRACE ("Setting device pio mode %d\n",
 
                 dev->regs.sector_count & 0x7);
 
          break;
          break;
        case 4:         /* Set DMA mode */
        case 4:         /* Set DMA mode */
          FIXME ("Set DMA mode to %d\n", dev->regs.sector_count & 0x7);
          /* FIXME */
 
          fprintf (stderr, "Fixme: Set DMA mode to %d\n",
 
                   dev->regs.sector_count & 0x7);
          break;
          break;
        case 8:         /* Set UDMA mode */
        case 8:         /* Set UDMA mode */
          FIXME ("Set UDMA mode to %d\n", dev->regs.sector_count & 0x7);
          /* FIXME */
 
          fprintf (stderr, "Fixme: Set UDMA mode to %d\n",
 
                   dev->regs.sector_count & 0x7);
          break;
          break;
        }
        }
      dev->regs.status = ATA_SR_DSC | ATA_SR_DRDY | ATA_SR_BSY;
      dev->regs.status = ATA_SR_DSC | ATA_SR_DRDY | ATA_SR_BSY;
      break;
      break;
    default:
    default:
      dev->regs.error = ATA_ERR_ABT;
      dev->regs.error = ATA_ERR_ABT;
      dev->regs.status = ATA_SR_ERR | ATA_SR_BSY | ATA_SR_DRDY;
      dev->regs.status = ATA_SR_ERR | ATA_SR_BSY | ATA_SR_DRDY;
      FIXME ("Unknown set features sub-command %x\n", dev->regs.features);
      /* FIXME */
 
      fprintf (stderr, "Fixme: Unknown set features sub-command %x\n",
 
               dev->regs.features);
    }
    }
}
}
 
 
 
 
int
int
ata_device_execute_cmd (struct ata_device *device)
ata_device_execute_cmd (struct ata_device *device)
{
{
  /*display debug information                                         */
 
  TRACE ("command: 0x%02X\n", device->regs.command);
 
 
 
  /* execute the commands */
  /* execute the commands */
  switch (device->regs.command)
  switch (device->regs.command)
    {
    {
    case DEVICE_RESET:
    case DEVICE_RESET:
      ata_device_reset_cmd (device);
      ata_device_reset_cmd (device);
Line 1154... Line 1119...
      return 0;
      return 0;
 
 
    default:
    default:
      device->regs.error = ATA_ERR_ABT;
      device->regs.error = ATA_ERR_ABT;
      device->regs.status = ATA_SR_ERR | ATA_SR_BSY | ATA_SR_DRDY;
      device->regs.status = ATA_SR_ERR | ATA_SR_BSY | ATA_SR_DRDY;
      FIXME ("Unknown command %x\n", device->regs.command);
      /* FIXME */
 
      fprintf (stderr, "Fixme: Unknown command %x\n", device->regs.command);
      SCHED_ADD (ata_cmd_complete, device, 40000);
      SCHED_ADD (ata_cmd_complete, device, 40000);
      return -1;
      return -1;
    }
    }
}
}
 
 
 No newline at end of file
 No newline at end of file

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.