2017-03-21 6 views
0

Ich habe ein Modul für Code kompiliert für ARM mit -fpie, und ich möchte das BSS löschen, wenn es zuerst ausgeführt wird. Wenn ich jedoch die Linker-Skript-Symbole für den Anfang und das Ende des BSS-Abschnitts referenziere, erhalte ich Code, der absolute Adressen in lokalen Variablen enthält.Linker-definierte Symbole im positionsunabhängigen Code referenzieren

Hier ist meine Montage Einstiegspunkt:

.section entry_point 

code_entry: 
    # Save arguments to the stack 
    push {r0-r2} 

    # Loop over the BSS section, set it all to 0 
    mov  r0, #0 
    ldr  r1, =__bss_start 
    ldr  r2, =__bss_end 
loop_bss: 
    str  r0, [r1], #4 
    cmp  r1, r2 
    blt  loop_bss 

    # Pop arguments from the stack 
    pop  {r0-r2} 

    # Branch to C code (which will return to caller on its own) 
    b  startPICode 

Der Ausgang ist die folgende:

Disassembly of section .text: 

00180000 <code_entry>: 
    180000: e92d0007 push {r0, r1, r2} 
    180004: e3a00000 mov r0, #0 
    180008: e59f1014 ldr r1, [pc, #20] ; 180024 <loop_bss+0x14> 
    18000c: e59f2014 ldr r2, [pc, #20] ; 180028 <loop_bss+0x18> 

00180010 <loop_bss>: 
    180010: e4810004 str r0, [r1], #4 
    180014: e1510002 cmp r1, r2 
    180018: bafffffc blt 180010 <loop_bss> 
    18001c: e8bd0007 pop {r0, r1, r2} 
    180020: ea00189f b 1862a4 <startPICode> 
    180024: 00194360 andseq r4, r9, r0, ror #6 
    180028: 001950e8 andseq r5, r9, r8, ror #1 

readelf zeigt an, dass meine ELF-Datei keine Verlagerungen hat.

Bin ich richtig im Denken, dass die Linker-Symbole nur ganze Zahlen sind, die immer absolute Adressen sein werden? Wenn ja, gibt es eine Möglichkeit, die Adressen bei der Lade- oder Ausführungszeit zu reparieren? Oder gibt es eine andere Möglichkeit, die BSS für diesen Code zu löschen?

Bearbeiten: Hinzufügen einiger Readelf-s-Ausgabe. Hier ist die relevante .S-Datei und alles, was zum BSS gehört.

Symbol table '.symtab' contains 812 entries: 
    Num: Value Size Type Bind Vis  Ndx Name 
    0: 00000000  0 NOTYPE LOCAL DEFAULT UND 
    1: 00180000  0 SECTION LOCAL DEFAULT 1 
    2: 0019297c  0 SECTION LOCAL DEFAULT 2 
    3: 00192994  0 SECTION LOCAL DEFAULT 3 
    4: 001929b0  0 SECTION LOCAL DEFAULT 4 
    5: 00193808  0 SECTION LOCAL DEFAULT 5 
    6: 001942dc  0 SECTION LOCAL DEFAULT 6 
    7: 00194350  0 SECTION LOCAL DEFAULT 7 
    8: 00194358  0 SECTION LOCAL DEFAULT 8 
    9: 0019435c  0 SECTION LOCAL DEFAULT 9 
    10: 00194360  0 SECTION LOCAL DEFAULT 10 
    11: 00194360  0 SECTION LOCAL DEFAULT 11 
    12: 001950e8  0 SECTION LOCAL DEFAULT 12 
    13: 001970f0  0 SECTION LOCAL DEFAULT 13 
    14: 00000000  0 SECTION LOCAL DEFAULT 14 
    15: 00000000  0 SECTION LOCAL DEFAULT 15 
    16: 00000000  0 SECTION LOCAL DEFAULT 16 
    17: 00000000  0 SECTION LOCAL DEFAULT 17 
    18: 00000000  0 SECTION LOCAL DEFAULT 18 
    19: 00000000  0 SECTION LOCAL DEFAULT 19 
    20: 00000000  0 SECTION LOCAL DEFAULT 20 
    21: 00000000  0 SECTION LOCAL DEFAULT 21 
    22: 00000000  0 SECTION LOCAL DEFAULT 22 
    23: 00000000  0 SECTION LOCAL DEFAULT 23 
    24: 00000000  0 FILE LOCAL DEFAULT ABS ./src/entry.o 
    25: 00180000  0 NOTYPE LOCAL DEFAULT 1 code_entry 
    26: 00180000  0 NOTYPE LOCAL DEFAULT 1 $a 
    27: 00180010  0 NOTYPE LOCAL DEFAULT 1 loop_bss 
    28: 00180024  0 NOTYPE LOCAL DEFAULT 1 $d 
    29: 00000124  0 NOTYPE LOCAL DEFAULT 17 $d 

    484: 00194360  0 NOTYPE GLOBAL DEFAULT 10 __sbss_start 

    525: 00193804  0 NOTYPE GLOBAL DEFAULT 5 __sbss2_end 

    555: 001950e8  0 NOTYPE GLOBAL DEFAULT 11 __bss_end 

    565: 00194360  0 NOTYPE GLOBAL DEFAULT 10 __tbss_start 

    581: 00194360  0 NOTYPE GLOBAL DEFAULT 10 __sbss_end 

    599: 00193804  0 NOTYPE GLOBAL DEFAULT 5 __sbss2_start 

    667: 00194360  0 NOTYPE GLOBAL DEFAULT 11 __bss_start 

    753: 00194360  0 NOTYPE GLOBAL DEFAULT 10 __tbss_end 
+0

Können Sie readelf -s posten. Ist das Barmetall? – InfinitelyManic

+0

Ja, das ist Baremetall. Ich würde es vorziehen, kein vollständiges Readelf zu posten. Aber gibt es bestimmte Symbole, die hilfreich zum Posten sind? –

+0

alle mit * bss * – InfinitelyManic

Antwort

0

Ihr Recht, der Code, den Sie erstellt haben, ist nicht verschiebbar. Um es relokabel zu machen, werden Sie explizit die Adressen __bss_start und __bss_end relativ machen. Zum Beispiel:

.section entry_point 

bss_start_rel: 
    .word __bss_start__ - bss_start_rel 
bss_end_rel: 
    .word __bss_end__ - bss_start_rel 

.global code_entry 
code_entry: 
    # Save arguments to the stack 
    push {r0-r2} 

    # Loop over the BSS section, set it all to 0 
    mov  r0, #0 
    adr  r3, bss_start_rel 
    ldr  r1, bss_start_rel 
    ldr  r2, bss_end_rel 
    add  r1, r1, r3 
    add  r2, r2, r3 

    ... 

Die ADR pseudo-Instruktionsergebnisse in R3 mit der Adresse des PC unter Verwendung bss_start_rel relative arithmetischen geladen werden (zB sub r3, pc, #24.). Das wird als Basis verwendet, um den Ort von __bss_start__ und __bss_end__ zu berechnen, dessen relative Position bei bss_start_rel und bss_start_end gespeichert ist.

+0

Genau das, was ich brauchte, danke für die Hilfe! –

Verwandte Themen