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

Subversion Repositories or1k_soc_on_altera_embedded_dev_kit

[/] [or1k_soc_on_altera_embedded_dev_kit/] [trunk/] [linux-2.6/] [linux-2.6.24/] [arch/] [m68knommu/] [platform/] [532x/] [config.c] - Blame information for rev 3

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 3 xianfeng
/***************************************************************************/
2
 
3
/*
4
 *      linux/arch/m68knommu/platform/532x/config.c
5
 *
6
 *      Copyright (C) 1999-2002, Greg Ungerer (gerg@snapgear.com)
7
 *      Copyright (C) 2000, Lineo (www.lineo.com)
8
 *      Yaroslav Vinogradov yaroslav.vinogradov@freescale.com
9
 *      Copyright Freescale Semiconductor, Inc 2006
10
 *      Copyright (c) 2006, emlix, Sebastian Hess <sh@emlix.com>
11
 *
12
 * This program is free software; you can redistribute it and/or modify
13
 * it under the terms of the GNU General Public License as published by
14
 * the Free Software Foundation; either version 2 of the License, or
15
 * (at your option) any later version.
16
 */
17
 
18
/***************************************************************************/
19
 
20
#include <linux/kernel.h>
21
#include <linux/param.h>
22
#include <linux/init.h>
23
#include <linux/interrupt.h>
24
#include <asm/dma.h>
25
#include <asm/machdep.h>
26
#include <asm/coldfire.h>
27
#include <asm/mcfsim.h>
28
#include <asm/mcfdma.h>
29
#include <asm/mcfwdebug.h>
30
 
31
/***************************************************************************/
32
 
33
void coldfire_reset(void);
34
 
35
extern unsigned int mcf_timervector;
36
extern unsigned int mcf_profilevector;
37
extern unsigned int mcf_timerlevel;
38
 
39
/***************************************************************************/
40
 
41
/*
42
 *      DMA channel base address table.
43
 */
44
unsigned int dma_base_addr[MAX_M68K_DMA_CHANNELS] = { };
45
unsigned int dma_device_address[MAX_M68K_DMA_CHANNELS];
46
 
47
/***************************************************************************/
48
 
49
void mcf_settimericr(unsigned int timer, unsigned int level)
50
{
51
        volatile unsigned char *icrp;
52
        unsigned int icr;
53
        unsigned char irq;
54
 
55
        if (timer <= 2) {
56
                switch (timer) {
57
                case 2:  irq = 33; icr = MCFSIM_ICR_TIMER2; break;
58
                default: irq = 32; icr = MCFSIM_ICR_TIMER1; break;
59
                }
60
 
61
                icrp = (volatile unsigned char *) (MCF_MBAR + icr);
62
                *icrp = level;
63
                mcf_enable_irq0(irq);
64
        }
65
}
66
 
67
/***************************************************************************/
68
 
69
int mcf_timerirqpending(int timer)
70
{
71
        unsigned int imr = 0;
72
 
73
        switch (timer) {
74
        case 1:  imr = 0x1; break;
75
        case 2:  imr = 0x2; break;
76
        default: break;
77
        }
78
        return (mcf_getiprh() & imr);
79
}
80
 
81
/***************************************************************************/
82
 
83
void config_BSP(char *commandp, int size)
84
{
85
        mcf_setimr(MCFSIM_IMR_MASKALL);
86
 
87
#if !defined(CONFIG_BOOTPARAM)
88
        /* Copy command line from FLASH to local buffer... */
89
        memcpy(commandp, (char *) 0x4000, 4);
90
        if(strncmp(commandp, "kcl ", 4) == 0){
91
                memcpy(commandp, (char *) 0x4004, size);
92
                commandp[size-1] = 0;
93
        } else {
94
                memset(commandp, 0, size);
95
        }
96
#endif
97
 
98
        mcf_timervector = 64+32;
99
        mcf_profilevector = 64+33;
100
        mach_reset = coldfire_reset;
101
 
102
#ifdef MCF_BDM_DISABLE
103
        /*
104
         * Disable the BDM clocking.  This also turns off most of the rest of
105
         * the BDM device.  This is good for EMC reasons. This option is not
106
         * incompatible with the memory protection option.
107
         */
108
        wdebug(MCFDEBUG_CSR, MCFDEBUG_CSR_PSTCLK);
109
#endif
110
}
111
 
112
/***************************************************************************/
113
/* Board initialization */
114
 
115
/********************************************************************/
116
/*
117
 * PLL min/max specifications
118
 */
119
#define MAX_FVCO        500000  /* KHz */
120
#define MAX_FSYS        80000   /* KHz */
121
#define MIN_FSYS        58333   /* KHz */
122
#define FREF            16000   /* KHz */
123
 
124
 
125
#define MAX_MFD         135     /* Multiplier */
126
#define MIN_MFD         88      /* Multiplier */
127
#define BUSDIV          6       /* Divider */
128
 
129
/*
130
 * Low Power Divider specifications
131
 */
132
#define MIN_LPD         (1 << 0)    /* Divider (not encoded) */
133
#define MAX_LPD         (1 << 15)   /* Divider (not encoded) */
134
#define DEFAULT_LPD     (1 << 1)        /* Divider (not encoded) */
135
 
136
#define SYS_CLK_KHZ     80000
137
#define SYSTEM_PERIOD   12.5
138
/*
139
 *  SDRAM Timing Parameters
140
 */
141
#define SDRAM_BL        8       /* # of beats in a burst */
142
#define SDRAM_TWR       2       /* in clocks */
143
#define SDRAM_CASL      2.5     /* CASL in clocks */
144
#define SDRAM_TRCD      2       /* in clocks */
145
#define SDRAM_TRP       2       /* in clocks */
146
#define SDRAM_TRFC      7       /* in clocks */
147
#define SDRAM_TREFI     7800    /* in ns */
148
 
149
#define EXT_SRAM_ADDRESS        (0xC0000000)
150
#define FLASH_ADDRESS           (0x00000000)
151
#define SDRAM_ADDRESS           (0x40000000)
152
 
153
#define NAND_FLASH_ADDRESS      (0xD0000000)
154
 
155
int sys_clk_khz = 0;
156
int sys_clk_mhz = 0;
157
 
158
void wtm_init(void);
159
void scm_init(void);
160
void gpio_init(void);
161
void fbcs_init(void);
162
void sdramc_init(void);
163
int  clock_pll (int fsys, int flags);
164
int  clock_limp (int);
165
int  clock_exit_limp (void);
166
int  get_sys_clock (void);
167
 
168
asmlinkage void __init sysinit(void)
169
{
170
        sys_clk_khz = clock_pll(0, 0);
171
        sys_clk_mhz = sys_clk_khz/1000;
172
 
173
        wtm_init();
174
        scm_init();
175
        gpio_init();
176
        fbcs_init();
177
        sdramc_init();
178
}
179
 
180
void wtm_init(void)
181
{
182
        /* Disable watchdog timer */
183
        MCF_WTM_WCR = 0;
184
}
185
 
186
#define MCF_SCM_BCR_GBW         (0x00000100)
187
#define MCF_SCM_BCR_GBR         (0x00000200)
188
 
189
void scm_init(void)
190
{
191
        /* All masters are trusted */
192
        MCF_SCM_MPR = 0x77777777;
193
 
194
        /* Allow supervisor/user, read/write, and trusted/untrusted
195
           access to all slaves */
196
        MCF_SCM_PACRA = 0;
197
        MCF_SCM_PACRB = 0;
198
        MCF_SCM_PACRC = 0;
199
        MCF_SCM_PACRD = 0;
200
        MCF_SCM_PACRE = 0;
201
        MCF_SCM_PACRF = 0;
202
 
203
        /* Enable bursts */
204
        MCF_SCM_BCR = (MCF_SCM_BCR_GBR | MCF_SCM_BCR_GBW);
205
}
206
 
207
 
208
void fbcs_init(void)
209
{
210
        MCF_GPIO_PAR_CS = 0x0000003E;
211
 
212
        /* Latch chip select */
213
        MCF_FBCS1_CSAR = 0x10080000;
214
 
215
        MCF_FBCS1_CSCR = 0x002A3780;
216
        MCF_FBCS1_CSMR = (MCF_FBCS_CSMR_BAM_2M | MCF_FBCS_CSMR_V);
217
 
218
        /* Initialize latch to drive signals to inactive states */
219
        *((u16 *)(0x10080000)) = 0xFFFF;
220
 
221
        /* External SRAM */
222
        MCF_FBCS1_CSAR = EXT_SRAM_ADDRESS;
223
        MCF_FBCS1_CSCR = (MCF_FBCS_CSCR_PS_16
224
                        | MCF_FBCS_CSCR_AA
225
                        | MCF_FBCS_CSCR_SBM
226
                        | MCF_FBCS_CSCR_WS(1));
227
        MCF_FBCS1_CSMR = (MCF_FBCS_CSMR_BAM_512K
228
                        | MCF_FBCS_CSMR_V);
229
 
230
        /* Boot Flash connected to FBCS0 */
231
        MCF_FBCS0_CSAR = FLASH_ADDRESS;
232
        MCF_FBCS0_CSCR = (MCF_FBCS_CSCR_PS_16
233
                        | MCF_FBCS_CSCR_BEM
234
                        | MCF_FBCS_CSCR_AA
235
                        | MCF_FBCS_CSCR_SBM
236
                        | MCF_FBCS_CSCR_WS(7));
237
        MCF_FBCS0_CSMR = (MCF_FBCS_CSMR_BAM_32M
238
                        | MCF_FBCS_CSMR_V);
239
}
240
 
241
void sdramc_init(void)
242
{
243
        /*
244
         * Check to see if the SDRAM has already been initialized
245
         * by a run control tool
246
         */
247
        if (!(MCF_SDRAMC_SDCR & MCF_SDRAMC_SDCR_REF)) {
248
                /* SDRAM chip select initialization */
249
 
250
                /* Initialize SDRAM chip select */
251
                MCF_SDRAMC_SDCS0 = (0
252
                        | MCF_SDRAMC_SDCS_BA(SDRAM_ADDRESS)
253
                        | MCF_SDRAMC_SDCS_CSSZ(MCF_SDRAMC_SDCS_CSSZ_32MBYTE));
254
 
255
        /*
256
         * Basic configuration and initialization
257
         */
258
        MCF_SDRAMC_SDCFG1 = (0
259
                | MCF_SDRAMC_SDCFG1_SRD2RW((int)((SDRAM_CASL + 2) + 0.5 ))
260
                | MCF_SDRAMC_SDCFG1_SWT2RD(SDRAM_TWR + 1)
261
                | MCF_SDRAMC_SDCFG1_RDLAT((int)((SDRAM_CASL*2) + 2))
262
                | MCF_SDRAMC_SDCFG1_ACT2RW((int)((SDRAM_TRCD ) + 0.5))
263
                | MCF_SDRAMC_SDCFG1_PRE2ACT((int)((SDRAM_TRP ) + 0.5))
264
                | MCF_SDRAMC_SDCFG1_REF2ACT((int)(((SDRAM_TRFC) ) + 0.5))
265
                | MCF_SDRAMC_SDCFG1_WTLAT(3));
266
        MCF_SDRAMC_SDCFG2 = (0
267
                | MCF_SDRAMC_SDCFG2_BRD2PRE(SDRAM_BL/2 + 1)
268
                | MCF_SDRAMC_SDCFG2_BWT2RW(SDRAM_BL/2 + SDRAM_TWR)
269
                | MCF_SDRAMC_SDCFG2_BRD2WT((int)((SDRAM_CASL+SDRAM_BL/2-1.0)+0.5))
270
                | MCF_SDRAMC_SDCFG2_BL(SDRAM_BL-1));
271
 
272
 
273
        /*
274
         * Precharge and enable write to SDMR
275
         */
276
        MCF_SDRAMC_SDCR = (0
277
                | MCF_SDRAMC_SDCR_MODE_EN
278
                | MCF_SDRAMC_SDCR_CKE
279
                | MCF_SDRAMC_SDCR_DDR
280
                | MCF_SDRAMC_SDCR_MUX(1)
281
                | MCF_SDRAMC_SDCR_RCNT((int)(((SDRAM_TREFI/(SYSTEM_PERIOD*64)) - 1) + 0.5))
282
                | MCF_SDRAMC_SDCR_PS_16
283
                | MCF_SDRAMC_SDCR_IPALL);
284
 
285
        /*
286
         * Write extended mode register
287
         */
288
        MCF_SDRAMC_SDMR = (0
289
                | MCF_SDRAMC_SDMR_BNKAD_LEMR
290
                | MCF_SDRAMC_SDMR_AD(0x0)
291
                | MCF_SDRAMC_SDMR_CMD);
292
 
293
        /*
294
         * Write mode register and reset DLL
295
         */
296
        MCF_SDRAMC_SDMR = (0
297
                | MCF_SDRAMC_SDMR_BNKAD_LMR
298
                | MCF_SDRAMC_SDMR_AD(0x163)
299
                | MCF_SDRAMC_SDMR_CMD);
300
 
301
        /*
302
         * Execute a PALL command
303
         */
304
        MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_IPALL;
305
 
306
        /*
307
         * Perform two REF cycles
308
         */
309
        MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_IREF;
310
        MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_IREF;
311
 
312
        /*
313
         * Write mode register and clear reset DLL
314
         */
315
        MCF_SDRAMC_SDMR = (0
316
                | MCF_SDRAMC_SDMR_BNKAD_LMR
317
                | MCF_SDRAMC_SDMR_AD(0x063)
318
                | MCF_SDRAMC_SDMR_CMD);
319
 
320
        /*
321
         * Enable auto refresh and lock SDMR
322
         */
323
        MCF_SDRAMC_SDCR &= ~MCF_SDRAMC_SDCR_MODE_EN;
324
        MCF_SDRAMC_SDCR |= (0
325
                | MCF_SDRAMC_SDCR_REF
326
                | MCF_SDRAMC_SDCR_DQS_OE(0xC));
327
        }
328
}
329
 
330
void gpio_init(void)
331
{
332
        /* Enable UART0 pins */
333
        MCF_GPIO_PAR_UART = ( 0
334
                | MCF_GPIO_PAR_UART_PAR_URXD0
335
                | MCF_GPIO_PAR_UART_PAR_UTXD0);
336
 
337
        /* Initialize TIN3 as a GPIO output to enable the write
338
           half of the latch */
339
        MCF_GPIO_PAR_TIMER = 0x00;
340
        MCF_GPIO_PDDR_TIMER = 0x08;
341
        MCF_GPIO_PCLRR_TIMER = 0x0;
342
 
343
}
344
 
345
int clock_pll(int fsys, int flags)
346
{
347
        int fref, temp, fout, mfd;
348
        u32 i;
349
 
350
        fref = FREF;
351
 
352
        if (fsys == 0) {
353
                /* Return current PLL output */
354
                mfd = MCF_PLL_PFDR;
355
 
356
                return (fref * mfd / (BUSDIV * 4));
357
        }
358
 
359
        /* Check bounds of requested system clock */
360
        if (fsys > MAX_FSYS)
361
                fsys = MAX_FSYS;
362
        if (fsys < MIN_FSYS)
363
                fsys = MIN_FSYS;
364
 
365
        /* Multiplying by 100 when calculating the temp value,
366
           and then dividing by 100 to calculate the mfd allows
367
           for exact values without needing to include floating
368
           point libraries. */
369
        temp = 100 * fsys / fref;
370
        mfd = 4 * BUSDIV * temp / 100;
371
 
372
        /* Determine the output frequency for selected values */
373
        fout = (fref * mfd / (BUSDIV * 4));
374
 
375
        /*
376
         * Check to see if the SDRAM has already been initialized.
377
         * If it has then the SDRAM needs to be put into self refresh
378
         * mode before reprogramming the PLL.
379
         */
380
        if (MCF_SDRAMC_SDCR & MCF_SDRAMC_SDCR_REF)
381
                /* Put SDRAM into self refresh mode */
382
                MCF_SDRAMC_SDCR &= ~MCF_SDRAMC_SDCR_CKE;
383
 
384
        /*
385
         * Initialize the PLL to generate the new system clock frequency.
386
         * The device must be put into LIMP mode to reprogram the PLL.
387
         */
388
 
389
        /* Enter LIMP mode */
390
        clock_limp(DEFAULT_LPD);
391
 
392
        /* Reprogram PLL for desired fsys */
393
        MCF_PLL_PODR = (0
394
                | MCF_PLL_PODR_CPUDIV(BUSDIV/3)
395
                | MCF_PLL_PODR_BUSDIV(BUSDIV));
396
 
397
        MCF_PLL_PFDR = mfd;
398
 
399
        /* Exit LIMP mode */
400
        clock_exit_limp();
401
 
402
        /*
403
         * Return the SDRAM to normal operation if it is in use.
404
         */
405
        if (MCF_SDRAMC_SDCR & MCF_SDRAMC_SDCR_REF)
406
                /* Exit self refresh mode */
407
                MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_CKE;
408
 
409
        /* Errata - workaround for SDRAM opeartion after exiting LIMP mode */
410
        MCF_SDRAMC_LIMP_FIX = MCF_SDRAMC_REFRESH;
411
 
412
        /* wait for DQS logic to relock */
413
        for (i = 0; i < 0x200; i++)
414
                ;
415
 
416
        return fout;
417
}
418
 
419
int clock_limp(int div)
420
{
421
        u32 temp;
422
 
423
        /* Check bounds of divider */
424
        if (div < MIN_LPD)
425
                div = MIN_LPD;
426
        if (div > MAX_LPD)
427
                div = MAX_LPD;
428
 
429
        /* Save of the current value of the SSIDIV so we don't
430
           overwrite the value*/
431
        temp = (MCF_CCM_CDR & MCF_CCM_CDR_SSIDIV(0xF));
432
 
433
        /* Apply the divider to the system clock */
434
        MCF_CCM_CDR = ( 0
435
                | MCF_CCM_CDR_LPDIV(div)
436
                | MCF_CCM_CDR_SSIDIV(temp));
437
 
438
        MCF_CCM_MISCCR |= MCF_CCM_MISCCR_LIMP;
439
 
440
        return (FREF/(3*(1 << div)));
441
}
442
 
443
int clock_exit_limp(void)
444
{
445
        int fout;
446
 
447
        /* Exit LIMP mode */
448
        MCF_CCM_MISCCR = (MCF_CCM_MISCCR & ~ MCF_CCM_MISCCR_LIMP);
449
 
450
        /* Wait for PLL to lock */
451
        while (!(MCF_CCM_MISCCR & MCF_CCM_MISCCR_PLL_LOCK))
452
                ;
453
 
454
        fout = get_sys_clock();
455
 
456
        return fout;
457
}
458
 
459
int get_sys_clock(void)
460
{
461
        int divider;
462
 
463
        /* Test to see if device is in LIMP mode */
464
        if (MCF_CCM_MISCCR & MCF_CCM_MISCCR_LIMP) {
465
                divider = MCF_CCM_CDR & MCF_CCM_CDR_LPDIV(0xF);
466
                return (FREF/(2 << divider));
467
        }
468
        else
469
                return ((FREF * MCF_PLL_PFDR) / (BUSDIV * 4));
470
}

powered by: WebSVN 2.1.0

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