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

Subversion Repositories or1k

[/] [or1k/] [branches/] [stable_0_2_x/] [or1ksim/] [peripheral/] [atahost.c] - Blame information for rev 876

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 876 rherveille
/*
2
    atahost.c -- ATA Host code simulation
3
    Copyright (C) 2002 Richard Herveille, rherveille@opencores.org
4
 
5
    This file is part of OpenRISC 1000 Architectural Simulator
6
 
7
    This program is free software; you can redistribute it and/or modify
8
    it under the terms of the GNU General Public License as published by
9
    the Free Software Foundation; either version 2 of the License, or
10
    (at your option) any later version
11
 
12
    This program is distributed in the hope that it will be useful,
13
    but WITHOUT ANY WARRANTY; without even the implied warranty of
14
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
    GNU General Public License for more details.
16
 
17
    You should have received a copy of the GNU General Public License
18
    along with this program; if not, write to the Free Software
19
    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20
*/
21
 
22
/* get a prototype for 'register_memoryarea()                         */
23
#include "abstract.h"
24
#include "sim-config.h"
25
#include "sched.h"
26
 
27
#include "atahost.h"
28
#include "atahost_define.h"
29
#include "messages.h"
30
 
31
static ata_host atas[MAX_ATAS];
32
 
33
/* reset and initialize ATA host core(s) */
34
void ata_reset(void)
35
{
36
   static int first_time=0;
37
 
38
   unsigned i;
39
   ata_host *ata;
40
 
41
   // for all ATA cores
42
   for (i=0; i < config.natas; i++)
43
   {
44
     ata = &(atas[i]);
45
 
46
     // reset the core registers
47
     ata->regs.ctrl  = 0x0001;
48
     ata->regs.stat  = (DEV_ID << 24) | (REV << 20);
49
     ata->regs.pctr  = (PIO_MODE0_TEOC << ATA_TEOC) | (PIO_MODE0_T4 << ATA_T4) | (PIO_MODE0_T2 << ATA_T2) | (PIO_MODE0_T1 << ATA_T1);
50
     ata->regs.pftr0 = (PIO_MODE0_TEOC << ATA_TEOC) | (PIO_MODE0_T4 << ATA_T4) | (PIO_MODE0_T2 << ATA_T2) | (PIO_MODE0_T1 << ATA_T1);
51
     ata->regs.pftr1 = (PIO_MODE0_TEOC << ATA_TEOC) | (PIO_MODE0_T4 << ATA_T4) | (PIO_MODE0_T2 << ATA_T2) | (PIO_MODE0_T1 << ATA_T1);
52
     ata->regs.dtr0  = (DMA_MODE0_TEOC << ATA_TEOC) | (DMA_MODE0_TD << ATA_TD) | (DMA_MODE0_TM << ATA_TM);
53
     ata->regs.dtr1  = (DMA_MODE0_TEOC << ATA_TEOC) | (DMA_MODE0_TD << ATA_TD) | (DMA_MODE0_TM << ATA_TM);
54
     ata->regs.txb   = 0;
55
 
56
     // copy the config settings
57
     ata->ata_number = i;
58
     ata->irq        = config.atas[i].irq;
59
     ata->baseaddr   = config.atas[i].baseaddr;
60
 
61
     ata->devices.device0.size   = config.atas[i].dev_size0;
62
     ata->devices.device0.type   = config.atas[i].dev_type0;
63
     ata->devices.device0.packet = config.atas[i].dev_packet0;
64
     ata->devices.device1.size   = config.atas[i].dev_size1;
65
     ata->devices.device1.type   = config.atas[i].dev_type1;
66
     ata->devices.device1.packet = config.atas[i].dev_packet1;
67
 
68
     /* initialize simulator & ata_devices                                */
69
     if (!first_time)
70
     {
71
       /* Connect ata_devices.                                            */
72
       ata_devices_init(&ata->devices, config.atas[i].dev_file0, config.atas[i].dev_file1);
73
 
74
       register_memoryarea(ata->baseaddr, ATA_ADDR_SPACE, 4, ata_read32, ata_write32);
75
     }
76
 
77
     /* the reset bit in the control register 'ctrl' is set, reset connect ata-devices */
78
     ata_devices_hw_reset(&ata->devices, 1);
79
   }
80
 
81
   first_time++;
82
}
83
/* ========================================================================= */
84
 
85
 
86
/* Convert a memory address to a device struct and relative address.
87
 * Return nonzero on success */
88
int ata_find_device( unsigned long addr, ata_host **ata, unsigned long *reladdr )
89
{
90
  unsigned i;
91
  *ata = NULL;
92
 
93
  for ( i = 0; i < config.natas && *ata == NULL; ++ i ) {
94
    if ( (addr >= atas[i].baseaddr) && (addr < atas[i].baseaddr + ATA_ADDR_SPACE) )
95
      *ata = &(atas[i]);
96
  }
97
 
98
  /* verify we found a device */
99
  if ( *ata == NULL )
100
    return 0;
101
 
102
  /* Verify legal address */
103
  if ( (addr - (*ata)->baseaddr) % 4 != 0 )
104
    return 0;
105
 
106
  *reladdr = addr - (*ata) -> baseaddr;
107
  return 1;
108
}
109
/* ========================================================================= */
110
 
111
 
112
/*
113
  Read a register
114
*/
115
unsigned long ata_read32( unsigned long addr )
116
{
117
    ata_host *ata;
118
 
119
    if ( !ata_find_device( addr, &ata, &addr ) )    {
120
        fprintf(stderr, "ata_read32( 0x%08lX ): Not in registered range(s)\n", addr );
121
        return 0;
122
    }
123
 
124
    /* determine if ata_host or ata_device addressed */
125
    if (is_ata_hostadr(addr))
126
        switch( addr ) {
127
            case ATA_CTRL :
128
                return ata -> regs.ctrl;
129
 
130
            case ATA_STAT :
131
                return ata -> regs.stat;
132
 
133
            case ATA_PCTR :
134
                return ata -> regs.pctr;
135
 
136
#if (DEV_ID > 1)
137
            case ATA_PFTR0:
138
                return ata -> regs.pftr0;
139
 
140
            case ATA_PFTR1:
141
                return ata -> regs.pftr1;
142
#endif
143
 
144
#if (DEV_ID > 2)
145
            case ATA_DTR0 :
146
                return ata -> regs.dtr0;
147
 
148
            case ATA_DTR1 :
149
                return ata -> regs.dtr1;
150
 
151
            case ATA_RXB  :
152
                return ata -> regs.rxb;
153
#endif
154
 
155
            default:
156
                return 0;
157
    }
158
    else
159
      return ata_devices_read(&ata->devices, addr & 0x7f);
160
}
161
/* ========================================================================= */
162
 
163
 
164
/*
165
  Write a register
166
*/
167
void ata_write32( unsigned long addr, unsigned long value )
168
{
169
    ata_host *ata;
170
 
171
    if ( !ata_find_device( addr, &ata, &addr ) )
172
    {
173
        fprintf(stderr, "ata_write32( 0x%08lX ): Not in registered range(s)\n", addr );
174
        return;
175
    }
176
 
177
    /* determine if ata_host or ata_device addressed */
178
    if (is_ata_hostadr(addr))
179
        switch( addr ) {
180
            case ATA_CTRL :
181
                ata -> regs.ctrl =  value;
182
 
183
                /* check if reset bit set, if so reset ata-devices    */
184
                if (value & ATA_RST)
185
                  ata_devices_hw_reset(&ata->devices, 1);
186
                else
187
                  ata_devices_hw_reset(&ata->devices, 0);
188
                break;
189
 
190
            case ATA_STAT :
191
                ata -> regs.stat = (ata -> regs.stat & ~ATA_IDEIS) | (ata -> regs.stat & ATA_IDEIS & value);
192
                break;
193
 
194
            case ATA_PCTR :
195
                ata -> regs.pctr = value;
196
                break;
197
 
198
            case ATA_PFTR0:
199
                ata -> regs.pftr0 = value;
200
                break;
201
 
202
            case ATA_PFTR1:
203
                ata -> regs.pftr1 = value;
204
                break;
205
 
206
            case ATA_DTR0 :
207
                ata -> regs.dtr0  = value;
208
                break;
209
 
210
            case ATA_DTR1 :
211
                ata -> regs.dtr1  = value;
212
                break;
213
 
214
            case ATA_TXB  :
215
                ata -> regs.txb   = value;
216
                break;
217
 
218
            default:
219
                /* ERROR-macro currently only supports simple strings. */
220
                /*
221
                  fprintf(stderr, "ERROR  : Unknown register for OCIDEC(%1d).\n", DEV_ID );
222
 
223
                  Tried to show some useful info here.
224
                  But when using 'DM'-simulator-command, the screen gets filled with these messages.
225
                  Thereby eradicating the usefulness of the message
226
                */
227
                break;
228
        }
229
    else
230
        ata_devices_write(&ata->devices, addr & 0x7f, value);
231
}
232
/* ========================================================================= */
233
 
234
 
235
/* Dump status */
236
void ata_status( void )
237
{
238
  unsigned i;
239
  ata_host *ata;
240
 
241
  for ( i = 0; i < config.natas; i++ ) {
242
      ata = &(atas[i]);
243
 
244
      if ( ata->baseaddr == 0 )
245
         continue;
246
 
247
       printf( "\nOCIDEC-%1d %u at: 0x%08X\n", DEV_ID, i, ata->baseaddr );
248
       printf( "ATA CTRL     : 0x%08lX\n", ata->regs.ctrl  );
249
       printf( "ATA STAT     : 0x%08lx\n", ata->regs.stat  );
250
       printf( "ATA PCTR     : 0x%08lx\n", ata->regs.pctr  );
251
 
252
#if (DEV_ID > 1)
253
       printf( "ATA FCTR0    : 0x%08lx\n", ata->regs.pftr0 );
254
       printf( "ATA FCTR1    : 0x%08lx\n", ata->regs.pftr1 );
255
#endif
256
 
257
#if (DEV_ID > 2)
258
       printf( "ATA DTR0     : 0x%08lx\n", ata->regs.dtr0  );
259
       printf( "ATA DTR1     : 0x%08lx\n", ata->regs.dtr1  );
260
       printf( "ATA TXD      : 0x%08lx\n", ata->regs.txb   );
261
       printf( "ATA RXD      : 0x%08lx\n", ata->regs.rxb   );
262
#endif
263
  }
264
}
265
/* ========================================================================= */

powered by: WebSVN 2.1.0

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