source: soft/giet_vm/giet_drivers/mmc_driver.c @ 580

Last change on this file since 580 was 545, checked in by alain, 10 years ago

Cosmetic

File size: 6.4 KB
RevLine 
[258]1///////////////////////////////////////////////////////////////////////////////////
2// File     : mmc_driver.c
3// Date     : 23/05/2013
4// Author   : alain greiner
5// Copyright (c) UPMC-LIP6
6///////////////////////////////////////////////////////////////////////////////////
7
[481]8#include <hard_config.h>
[258]9#include <mmc_driver.h>
[456]10#include <tty0.h>
[496]11#include <kernel_locks.h>
[258]12#include <utils.h>
[481]13
[345]14#include <io.h>
[258]15
[263]16#if !defined(X_SIZE)
17# error: You must define X_SIZE in the hard_config.h file
[258]18#endif
19
[263]20#if !defined(Y_SIZE)
21# error: You must define X_SIZE in the hard_config.h file
[258]22#endif
23
[263]24#if !defined(X_WIDTH)
25# error: You must define X_WIDTH in the hard_config.h file
26#endif
27
28#if !defined(Y_WIDTH)
29# error: You must define X_WIDTH in the hard_config.h file
30#endif
31
[320]32#if !defined(SEG_MMC_BASE)
33# error: You must define SEG_MMC_BASE in the hard_config.h file
34#endif
35
[333]36#if !defined(PERI_CLUSTER_INCREMENT)
37# error: You must define PERI_CLUSTER_INCREMENT in the hard_config.h file
[320]38#endif
39
[345]40///////////////////////////////////////////////////////////////////////////////
[496]41// Distributed locks protecting MMC components (one per cluster)
42///////////////////////////////////////////////////////////////////////////////
43
44__attribute__((section(".kdata")))
45spin_lock_t  _mmc_lock[X_SIZE][Y_SIZE]  __attribute__((aligned(64)));
46
47///////////////////////////////////////////////////////////////////////////////
[456]48// This low level function returns the value contained in register
49// defined by the ("func" / "index") arguments,
[345]50// in the MMC component contained in cluster "cluster_xy"
51///////////////////////////////////////////////////////////////////////////////
52static
53unsigned int _mmc_get_register( unsigned int cluster_xy, // cluster index
54                                unsigned int func,       // function index
55                                unsigned int index )     // register index
56{
57    unsigned int vaddr =
58        SEG_MMC_BASE + 
59        (cluster_xy * PERI_CLUSTER_INCREMENT) +
60        (MMC_REG(func, index) << 2);
61
62    return ioread32( (void*)vaddr );
63}
64
65///////////////////////////////////////////////////////////////////////////////
[456]66// This low level function sets a new value in register
67// defined by the ("func" / "index") arguments,
[345]68// in the MMC component contained in cluster "cluster_xy"
69///////////////////////////////////////////////////////////////////////////////
70static
71void _mmc_set_register( unsigned int cluster_xy,       // cluster index
72                        unsigned int func,             // func index
73                        unsigned int index,            // register index
74                        unsigned int value )           // value to be written
75{
76    unsigned int vaddr =
77        SEG_MMC_BASE + 
78        (cluster_xy * PERI_CLUSTER_INCREMENT) +
79        (MMC_REG(func, index) << 2);
80       
81    iowrite32( (void*)vaddr, value );
82}
83
[437]84/////////////////////////////////////////
[297]85void _mmc_inval( paddr_t      buf_paddr,
86                 unsigned int buf_length )
[258]87{
[263]88    // compute cluster coordinates
89    unsigned int cluster_xy = (unsigned int)(buf_paddr>>(40-X_WIDTH-Y_WIDTH));
90    unsigned int x          = cluster_xy >> Y_WIDTH;
91    unsigned int y          = cluster_xy & ((1<<Y_WIDTH)-1);
[258]92
[263]93    // parameters checking
94    if ( (x >= X_SIZE) || (y >= Y_SIZE) )
95    {
[496]96        _puts("\n[GIET ERROR] in _mmc_inval() : illegal cluster coordinates\n");
[263]97        _exit();
98    }
99
[545]100    if ( buf_paddr & 0x3F )
101    {
102        _puts("\n[GIET ERROR] in _mmc_inval() : paddr not 64 bytes aligned\n");
103        _exit();
104    }
105
[496]106    // get the lock protecting exclusive access to MEMC
[481]107    _spin_lock_acquire( &_mmc_lock[x][y] );
[258]108
109    // write inval arguments
[496]110    _mmc_set_register(cluster_xy, 0, MEMC_ADDR_LO   , (unsigned int)buf_paddr );
111    _mmc_set_register(cluster_xy, 0, MEMC_ADDR_HI   , (unsigned int)(buf_paddr>>32) );
112    _mmc_set_register(cluster_xy, 0, MEMC_BUF_LENGTH, buf_length );
113    _mmc_set_register(cluster_xy, 0, MEMC_CMD_TYPE  , MEMC_CMD_INVAL );
[258]114
115    // release the lock
[481]116    _spin_lock_release( &_mmc_lock[x][y] );
[258]117}
[437]118
119///////////////////////////////////////
[297]120void _mmc_sync( paddr_t      buf_paddr,
121                unsigned int buf_length )
[258]122{
[263]123    // compute cluster coordinates
124    unsigned int cluster_xy = (unsigned int)(buf_paddr>>(40-X_WIDTH-Y_WIDTH));
125    unsigned int x          = cluster_xy >> Y_WIDTH;
126    unsigned int y          = cluster_xy & ((1<<Y_WIDTH)-1);
[258]127
[263]128    // parameters checking
129    if ( (x >= X_SIZE) || (y >= Y_SIZE) )
130    {
[496]131        _puts( "\n[GIET ERROR] in _mmc_sync() : illegal cluster coordinates");
[263]132        _exit();
133    }
134
[545]135    if ( buf_paddr & 0x3F )
136    {
137        _puts("\n[GIET ERROR] in _mmc_sync() : paddr not 64 bytes aligned\n");
138        _exit();
139    }
140
[496]141    // get the lock protecting exclusive access to MEMC
[481]142    _spin_lock_acquire( &_mmc_lock[x][y] );
[258]143
144    // write inval arguments
[345]145    _mmc_set_register(cluster_xy, 0, MEMC_ADDR_LO   , (unsigned int)buf_paddr);
146    _mmc_set_register(cluster_xy, 0, MEMC_ADDR_HI   , (unsigned int)(buf_paddr>>32));
147    _mmc_set_register(cluster_xy, 0, MEMC_BUF_LENGTH, buf_length);
148    _mmc_set_register(cluster_xy, 0, MEMC_CMD_TYPE  , MEMC_CMD_SYNC);
[258]149
[345]150    // release the lock
[481]151    _spin_lock_release( &_mmc_lock[x][y] );
[258]152}
153
[496]154/////////////////////////////////////////////
155unsigned int _mmc_instrument( unsigned int x, 
156                              unsigned int y,
157                              unsigned int reg )
158{
159    // parameters checking
160    if ( (x >= X_SIZE) || (y >= Y_SIZE) )
161    {
162        _puts( "\n[GIET ERROR] in _mmc_instrument() : illegal cluster coordinates");
163        _exit();
164    }
165
166    unsigned int cluster_xy = (x << Y_WIDTH) + y;
167    return( _mmc_get_register(cluster_xy , 1 , reg) );
168}
169
[437]170///////////////////////////////////////////////////////
[297]171void _mmc_isr( unsigned int irq_type,  // should be HWI
172               unsigned int irq_id,    // index returned by ICU
173               unsigned int channel )  // unused
174{
[426]175    unsigned int gpid       = _get_procid();
176    unsigned int cluster_xy = gpid >> P_WIDTH;
[298]177    unsigned int x          = cluster_xy >> Y_WIDTH;
178    unsigned int y          = cluster_xy & ((1<<Y_WIDTH)-1);
[437]179    unsigned int p          = gpid & ((1<<P_WIDTH)-1);
[298]180
[437]181    _puts("[GIET ERROR] MMC IRQ received by processor[");
182    _putd( x );
183    _puts(",");
184    _putd( y );
185    _puts(",");
186    _putd( p );
187    _puts("] but _mmc_isr() not implemented\n");
[297]188}
189
190
191
[258]192// Local Variables:
193// tab-width: 4
194// c-basic-offset: 4
195// c-file-offsets:((innamespace . 0)(inline-open . 0))
196// indent-tabs-mode: nil
197// End:
198// vim: filetype=c:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
199
Note: See TracBrowser for help on using the repository browser.