|
|
DDR通过检查最大有效地址来识别容量,具体请看uboot的common/memsize.c文件中的检查代码,也可以看如下:
$ e( A9 r2 b/ [5 }3 M& b1 D/*7 Q3 C( v& S6 _
* Check memory range for valid RAM. A simple memory test determines: j) z' `1 i8 \. \/ g/ C' ^
* the actually available RAM size between addresses `base' and
8 ?6 |$ ^+ E; u9 k0 E% S; C2 E* `base + maxsize'.
, A1 a3 d6 N. k# _ ~& F*/' P8 ~4 `6 V1 E% k. D5 z
long get_ram_size(long *base, long maxsize)
& {( T: H1 ^1 @# n{- f( ~# b0 @3 z! D' j
volatile long *addr;! }( Z. ^) X- R5 t- x( X% V8 y0 @
long save[32];5 Q2 Z7 Q, k/ F- m* b9 @, y
long cnt;
: q% j1 j/ r0 d long val;
6 T( R8 d; K; _ long size;
/ A3 m9 w: i! X9 z( ~6 w int i = 0;" M9 K& F* t; ?' j8 G
B" |6 ~3 e) \% Y6 e' y7 c
for (cnt = (maxsize / sizeof (long)) >> 1; cnt > 0; cnt >>= 1) {
* S- ?5 |5 J( v addr = base + cnt; /* pointer arith! */$ @5 d' X9 j0 f- \) N
sync ();
2 C! `% w- m- S% j+ c2 U, Q" v save[i++] = *addr;# @. a$ j M0 G. t
sync ();$ U8 c s. P ]. |
*addr = ~cnt;
2 d/ \! Y" n' P! f* F. E/ p }: x. H; _0 y, |- F- Z
7 \; Q8 |4 A1 C/ ~" }6 Q9 }
addr = base;
( N# H7 X Q1 n* J sync ();- ]- p* ^6 h1 F# K) b( _
save = *addr;6 A- u) C- u8 Y. F8 w* \
sync ();
0 ~5 {, Y+ j$ A( N/ A *addr = 0;
) _# N* P% l8 R6 J( e: x% s C$ b7 d8 P" {% F; u5 U
sync ();; w. K( r3 ]/ U7 i- u4 X
if ((val = *addr) != 0) {
& e+ e# j# N- H% ^ /* Restore the original data before leaving the function.
: }" N& L$ U: J' W7 t4 v */
/ T7 M7 F- r; [+ k& i sync ();( j1 i1 K _; B r
*addr = save;
9 e0 r) W) o4 g2 C6 G3 k' @" F for (cnt = 1; cnt < maxsize / sizeof(long); cnt <<= 1) {8 h7 I8 l" L4 |* o" R3 l
addr = base + cnt;* ~& b2 f$ r1 ?9 c& k: G
sync ();) Q4 Q5 \. | F' [: u+ q
*addr = save[--i];) e8 U& y1 {8 d3 b8 S
}
. ~! Q1 P; r8 n* e2 J7 H5 V return (0);8 j# n" C0 s2 I. j! j, R0 Z
}
7 z. O8 T8 g7 m- Y+ y4 F7 F
& `0 F# U4 O9 s1 {- }% W! L for (cnt = 1; cnt < maxsize / sizeof (long); cnt <<= 1) {1 Y) P, t! P# R9 O. J, q$ y
addr = base + cnt; /* pointer arith! */7 }" Z5 F! i4 ~: m* R$ _+ P
val = *addr;2 h" I3 K. g" d$ Z3 y3 {! x
*addr = save[--i];) p! l$ M5 ~/ a1 D5 J6 v0 u3 h8 f
if (val != ~cnt) {
1 T0 a" B. w& x. w( ? y size = cnt * sizeof (long);
- k" r& l% _1 Y; k! K /* Restore the original data before leaving the function.
, }- a, y% ?1 w, G *// l) C! `) G8 W. l# T( ?! ?
for (cnt <<= 1; cnt < maxsize / sizeof (long); cnt <<= 1) {
$ z; ~ K% r0 i2 q3 {8 [9 |" a addr = base + cnt;
, b% d; J6 o$ m. ? *addr = save[--i];: }" Q, I- } n1 O/ Z" R
}
0 O) l) h6 H1 O. M. a% } return (size);
3 D- r) {, u/ ^" F2 [& _2 ^: n }2 |( p' K1 A6 d' M
}
+ x# u7 o- d+ z8 w% ? M; M# [; Z$ F$ p3 W! O& S9 F h
return (maxsize);
+ r8 y9 K. ]; H: C/ E* D}* [% L: m1 p Z3 V
int dram_init(void)
, C5 L) k9 D, a* e% ^5 j1 S! a{
) K% l2 S, y" D. E. u /* dram_init must store complete ramsize in gd->ram_size */4 R+ q& O% w8 P/ V( e* X
gd->ram_size = get_ram_size(( Y" P6 y# l- Z6 X
(void *)CONFIG_SYS_SDRAM_BASE,
1 D# A# T) t6 `1 e& N: P) Q CONFIG_MAX_RAM_BANK_SIZE);
: E4 [' r5 Q# k9 B# }3 o& R return 0;
' D( ~: j) E+ `}( ^% W2 _4 ^6 K: b5 i
5 J* R) m: @* M! l1 c; _0 A0 a: g% x n4 S- R8 _
B/ p8 x, m4 e8 ~ C2 m8 }# `9 z* W( \6 \# k" n1 Z. J8 W
FLASH是通过检查FLASH内部的ID识别容量,希望对您有帮助!
" ~! Q; O0 B, O# K" Q; @3 H
3 Q3 _$ G, l: v9 _, [: j! ]* A3 Y8 {( g, ^0 o0 w. N7 o, [
7 ^# a5 S' L: z# ` |
|