All of lore.kernel.org
 help / color / mirror / Atom feed
From: Heiko Schocher <hs@denx.de>
To: u-boot@lists.denx.de
Subject: [U-Boot] Problem with ll_entry_* before relocation
Date: Fri, 01 Feb 2013 10:53:50 +0100	[thread overview]
Message-ID: <510B90AE.4040409@denx.de> (raw)

Hello,

I am currently trying to get rid of some externs in the new i2c
multibus approach, specially this externs:

http://git.denx.de/?p=u-boot/u-boot-i2c.git;a=blob;f=drivers/i2c/i2c_core.c;h=2a559c9d81a945f219eab49d11e70c0ac4a6d6a4;hb=83ffd31c590dd5aedfef0c195b1ffc406e6d0e37#l31

I tried to use the ll_entry_* defines see:
include/linker_lists.h
so the compiler will collect all i2c adapter(s), and no
need to declare in the config file a list of used adapters.
This approach works fine for using i2c after relocation, but
did not work before, which is a must have for i2c ...
Therefore I describe (Sorry, for the long EMail) here, whats
I see on an arm926ejs based board, using eldk 5.2 with

[hs at pollux u-boot]$ arm-linux-gnueabi-gcc --version
arm-linux-gnueabi-gcc (GCC) 4.6.4 20120303 (prerelease)

and hope someone has an idea or at least an explanation,
why it is not working ...

First the defines I used for include/i2c.h (here shortened
the defines just using one unsigned long var, not the
"struct i2c_adap"):

#define U_BOOT_I2C_MKENT_COMPLETE_TRY(_hwadapnr) \
        _hwadapnr;

#define U_BOOT_I2C_ADAP_COMPLETE_TRY(_name, _hwadapnr) \
        ll_entry_declare(unsigned long, _name, try, try) = \
        U_BOOT_I2C_MKENT_COMPLETE_TRY( _hwadapnr);

which i can use in drivers/i2c/soft_i2c.c as

U_BOOT_I2C_ADAP_COMPLETE_TRY(soft0, 0)
U_BOOT_I2C_ADAP_COMPLETE_TRY(soft1, 1)

Following printf in for example i2c_set_bus_num():

int i2c_set_bus_num(unsigned int bus)
{
        extern unsigned long _u_boot_list_try__start;

printf("%08lx  %08lx\n", (unsigned long)_u_boot_list_try__start,
(unsigned long)&_u_boot_list_try__start);

results in an output:
before relocation
e59ff00c  00000000
          ^
          wrong address (Explanation see below)
after relocation:
00000000  a7fb5d08
          ^
          correct address

so, "&_u_boot_list_try__start" is only valid after relocation!

Debugging deeper in it ...
Objdump:

000000a4 <i2c_set_bus_num>:
        extern unsigned long _u_boot_list_try__start;

printf("%08lx  %08lx\n", (unsigned long)_u_boot_list_try__start,
(unsigned long)&_u_boot_list_try__start);
  a4:   e59f2014        ldr     r2, [pc, #20]   ; c0 <i2c_set_bus_num+0x1c>
 *      bus - bus index, zero based
 *
 *      Returns: 0 on success, not 0 on failure
 */
int i2c_set_bus_num(unsigned int bus)
{
  a8:   e92d4008        push    {r3, lr}
        extern unsigned long _u_boot_list_try__start;

printf("%08lx  %08lx\n", (unsigned long)_u_boot_list_try__start,
(unsigned long)&_u_boot_list_try__start);
  ac:   e5921000        ldr     r1, [r2]
  b0:   e59f000c        ldr     r0, [pc, #12]   ; c4 <i2c_set_bus_num+0x20>
  b4:   ebfffffe        bl      0 <printf>
        i2c_mux_set_all();

breakpoint in i2c_set_bus_num

System.map:
c001221c T i2c_set_bus_num

Core#0>bi 0xc001221c
Breakpoint identification is 0
Core#0>g
- TARGET: core #0 has entered debug mode
Core#0>i
    Core number       : 0
    Core state        : debug mode (ARM)
    Debug entry cause : Breakpoint
    Current PC        : 0xc001221c
    Current CPSR      : 0x600000d3 (Supervisor)
Core#0>r
GPR00: 00000000 c0030aeb 00000060 c001f028
GPR04: c0038ea4 fffffffc a7fb46c4 c0000b70
GPR08: a0000f00 00000001 c0000164 00000001
GPR12: 00000000 a0000ee0 c0000b80 c001221c
PC   : c001221c    CPSR: 600000d3
Core#0>md 0xc001221c
c001221c : e59f2014 e92d4008 e5921000 e59f000c  . ... at -.........
c001222c : ebffe57c e3a00000 e8bd8008 00000000  |...............
                                      ^
                                      wrong should be
                                      c003bd08
c001223c : c003674c e92d4008 ebffc80c e3a00000  Lg... at -.........
c001224c : e8bd4008 eafffff1 e92d40f8 e598307c  . at .......@-.|0..
[...]
Core#0>r
GPR00: 00000000 c0030aeb 00000060 c001f028
GPR04: c0038ea4 fffffffc a7fb46c4 c0000b70
GPR08: a0000f00 00000001 c0000164 00000001
GPR12: 00000000 a0000ee0 c0000b80 c001221c
PC   : c001221c    CPSR: 600000d3

from objdump pc @ 0xc001221c:
  a4:	e59f2014 	ldr	r2, [pc, #20]	; c0 <i2c_set_bus_num+0x1c>

load r2   with c001221c + 1c (0xc0012238) = 0 ....

thats wrong, as _u_boot_list_try__start is c003bd08 ...

System.map:
c003bd08 D _u_boot_list_i2c__end
c003bd08 D _u_boot_list_try__start
c003bd08 D _u_boot_list_try_soft0
c003bd0c D _u_boot_list_try_soft1
c003bd10 A __image_copy_end
[...]

After relocation:

relo addr from i2c_set_bus_num:

c001221c + 0xE7F7A000 = a7f8c21c

Core#0>bi 0xa7f8c21c
Breakpoint identification is 0
Core#0>g
- TARGET: core #0 has entered debug mode
Core#0>i
    Core number       : 0
    Core state        : debug mode (ARM)
    Debug entry cause : Breakpoint
    Current PC        : 0xa7f8c21c
    Current CPSR      : 0x600000d3 (Supervisor)
Core#0>r
GPR00: 00000000 a7ec8e50 00000060 00000083
GPR04: 00000000 a7fb5940 00000000 a7ec9ec8
GPR08: a7ec9f60 00000000 00000003 a7ec92d1
GPR12: 00000034 a7ec9280 a7f7dcf8 a7f8c21c
PC   : a7f8c21c    CPSR: 600000d3
Core#0>

Core#0>md 0xa7f8c21c
a7f8c21c : e59f2014 e92d4008 e5921000 e59f000c  . ... at -.........
a7f8c22c : ebffe57c e3a00000 e8bd8008 a7fb5d08  |............]..
                                      ^
a7f8c23c : a7fb074c e92d4008 ebffc80c e3a00000  L.... at -.........
a7f8c24c : e8bd4008 eafffff1 e92d40f8 e598307c  . at .......@-.|0..
a7f8c25c : e3a0601c e0030396 e59f5028 e1a07000  .`......(P...p..
[...]
Core#0>

  a4:	e59f2014 	ldr	r2, [pc, #20]	; c0 <i2c_set_bus_num+0x1c>

load r2 with pc:0xa7f8c21c + 1c = 0xa7f8c238 = a7fb5d08 ....
thats the correct value ... because:

c003bd08 + 0xE7F7A000 = 1a7fb5d08 relocated addr from
_u_boot_list_try__start

with:
c003bd08 D _u_boot_list_try__start
c003bd08 D _u_boot_list_try_soft0
c003bd0c D _u_boot_list_try_soft1
c003bd10 A __image_copy_end

So, the question is, why is in the u-boot image the
wrong value 0 for _u_boot_list_try__start?

Additionally, if I print "_u_boot_list_try_soft0" with

printf("%08lx  %08lx\n", (unsigned long)_u_boot_list_try_soft0,
(unsigned long)&_u_boot_list_try_soft0);

It has the correct value before and after relocation ... !!

objdump:
printf("%08lx  %08lx\n", (unsigned long)_u_boot_list_try__start,
(unsigned long)&_u_boot_list_try__start);
  a8:   e59f2024        ldr     r2, [pc, #36]   ; d4 <i2c_set_bus_num+0x30>
  ac:   e59f4024        ldr     r4, [pc, #36]   ; d8 <i2c_set_bus_num+0x34>
  b0:   e5921000        ldr     r1, [r2]
  b4:   e1a00004        mov     r0, r4
  b8:   ebfffffe        bl      0 <printf>
printf("%08lx  %08lx\n", (unsigned long)_u_boot_list_try_soft0,
(unsigned long)&_u_boot_list_try_soft0);
  bc:   e59f2018        ldr     r2, [pc, #24]   ; dc <i2c_set_bus_num+0x38>
  c0:   e1a00004        mov     r0, r4
  c4:   e5921000        ldr     r1, [r2]
  c8:   ebfffffe        bl      0 <printf>
        i2c_mux_set_all();

_u_boot_list_try_soft0 in line bc:
load to r2 from c001221c + 0x38 = 0xc0012254

and c0012254 contain c003bd20, which is the correct value
for _u_boot_list_try_soft0 !!

System.map for this case:
c003bd20 D _u_boot_list_try__start
c003bd20 D _u_boot_list_try_soft0
c003bd24 D _u_boot_list_try_soft1
c003bd28 A __image_copy_end

Core#0>r
GPR00: 00000000 c0030b03 00000060 c001f040
GPR04: c0038ebc fffffffc a7fb46dc c0000b70
GPR08: a0000f00 00000001 c0000164 00000001
GPR12: 00000000 a0000ee0 c0000b80 c001221c
PC   : c001221c    CPSR: 600000d3
Core#0>md 0xc001221c
c001221c : e92d4010 e59f2024 e59f4024 e5921000  . at -.$ ..$@......
c001222c : e1a00004 ebffe57b e59f2018 e1a00004  ....{.... ......
c001223c : e5921000 ebffe577 e3a00000 e8bd8010  ....w...........
c001224c : 00000000 c0036764 c003bd20 e92d4008  ....dg.. .... at -.
           ^                 ^
           ^                 correct value for _u_boot_list_try_soft0
           again, wrong value for _u_boot_list_try__start

So the question is, whats the difference between _u_boot_list_try_soft0
and _u_boot_list_try__start ... any ideas?

Thanks in advance.

bye,
Heiko
-- 
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany

             reply	other threads:[~2013-02-01  9:53 UTC|newest]

Thread overview: 4+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-02-01  9:53 Heiko Schocher [this message]
2013-02-01  9:00 ` [U-Boot] Problem with ll_entry_* before relocation Marek Vasut
2013-02-02 11:05   ` Albert ARIBAUD
2013-02-02 12:16     ` Albert ARIBAUD

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=510B90AE.4040409@denx.de \
    --to=hs@denx.de \
    --cc=u-boot@lists.denx.de \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.