GCC erzeugt zu kurze Interrupttabelle auf ATTiny24

Gast #1106605
Lesenswert?

Ich versuche seit Stunden verzweifelt folgenden, kleinen 
Programmabschnitt mit avr-gcc unter Windows auf einem ATtiny24V zum 
laufen zu kriegen:
1
#include <avr/interrupt.h>
2
#include <avr/io.h>
3
#include "Tools.h"
4

5
///<summary>ADC Interrupt</summary>
6
ISR(ADC_vect)
7
{
8
  volatile unsigned char ucDummy;
9
  BIT_SET(PINB, PB0);
10

11
  //-- ADCH immer auslesen, damit der AD-Wandler wieder bereit ist
12
  ucDummy=ADCH;      
13
}
14

15
///<summary>Hauptprogramm</summary>
16
__attribute__((noreturn)) void main ()
17
{
18
  //! DEBUG
19
  BIT_SET(DDRB, PB0);
20
  BIT_CLEAR(PORTB, PB0);
21

22
  //-- ADC konfigurieren
23
  ADMUX=0;                        //Eingangskanal 0  
24
  BIT_SET(ADMUX, REFS1);          //1,1V
25
  BIT_SET2(ADCSRA, ADPS1, ADPS2); //Prescaler /64
26
  BIT_SET2(ADCSRA, ADIE, ADEN);   //Interrupt Enable und ADC Enable
27
  
28
  //-- Interrupts freigeben
29
  sei();
30

31
  //-- AD-Wandler anwerfen
32
  BIT_SET(ADCSRA, ADSC);
33
}

Das Problem ist, das der Interrupt nie aufgerufen wird (die LED an PB0 
bleibt aus). Nun habe ich mir die disassembly des Compileroutputs 
angesehen und bin etwas stutzig geworden:
1
Disassembly of section .text:
2

3
00000000 <__vectors>:
4
   0:  0c c0         rjmp  .+24       ; 0x1a <__ctors_end>
5
   2:  27 c0         rjmp  .+78       ; 0x52 <__bad_interrupt>
6
   4:  26 c0         rjmp  .+76       ; 0x52 <__bad_interrupt>
7
   6:  25 c0         rjmp  .+74       ; 0x52 <__bad_interrupt>
8
   8:  24 c0         rjmp  .+72       ; 0x52 <__bad_interrupt>
9
   a:  23 c0         rjmp  .+70       ; 0x52 <__bad_interrupt>
10
   c:  22 c0         rjmp  .+68       ; 0x52 <__bad_interrupt>
11
   e:  21 c0         rjmp  .+66       ; 0x52 <__bad_interrupt>
12
  10:  20 c0         rjmp  .+64       ; 0x52 <__bad_interrupt>
13
  12:  1f c0         rjmp  .+62       ; 0x52 <__bad_interrupt>
14
  14:  1e c0         rjmp  .+60       ; 0x52 <__bad_interrupt>
15
  16:  1d c0         rjmp  .+58       ; 0x52 <__bad_interrupt>
16
  18:  1c c0         rjmp  .+56       ; 0x52 <__bad_interrupt>
17

18
0000001a <__ctors_end>:
19
  1a:  11 24         eor  r1, r1
20
  1c:  1f be         out  0x3f, r1  ; 63
21
  1e:  cf e5         ldi  r28, 0x5F  ; 95
22
  20:  d2 e0         ldi  r29, 0x02  ; 2
23
  22:  de bf         out  0x3e, r29  ; 62
24
  24:  cd bf         out  0x3d, r28  ; 61

Kann es sein, dass hier für meine ISR kein rjmp eingetragen ist. 
Ausserdem sind es viel zu wenig Interruptvektoren da der ATtiny24 17 
Interrupts hat und hier nur 13 vorhanden sind. Dafür fängt der Abschnitt 
__ctors_end zu früh an und belegt einen teil der Interrupttabelle.

Kann jemand das Problem nachvollziehen? Woran könnte das liegen? Mir 
fällt echt nichts mehr ein und ich bin für jeden Tip dankbar...
Gast #1106650
Lesenswert?

Falschen Controllertyp angegeben? Mit -mmcu=attiny24 sieht bei mir die
Tabelle so aus:
1
00000000 <__vectors>:
2
   0:  10 c0         rjmp  .+32       ; 0x22 <__ctors_end>
3
   2:  28 c0         rjmp  .+80       ; 0x54 <__bad_interrupt>
4
   4:  27 c0         rjmp  .+78       ; 0x54 <__bad_interrupt>
5
   6:  26 c0         rjmp  .+76       ; 0x54 <__bad_interrupt>
6
   8:  25 c0         rjmp  .+74       ; 0x54 <__bad_interrupt>
7
   a:  24 c0         rjmp  .+72       ; 0x54 <__bad_interrupt>
8
   c:  23 c0         rjmp  .+70       ; 0x54 <__bad_interrupt>
9
   e:  22 c0         rjmp  .+68       ; 0x54 <__bad_interrupt>
10
  10:  21 c0         rjmp  .+66       ; 0x54 <__bad_interrupt>
11
  12:  20 c0         rjmp  .+64       ; 0x54 <__bad_interrupt>
12
  14:  1f c0         rjmp  .+62       ; 0x54 <__bad_interrupt>
13
  16:  1e c0         rjmp  .+60       ; 0x54 <__bad_interrupt>
14
  18:  1d c0         rjmp  .+58       ; 0x54 <__bad_interrupt>
15
  1a:  1d c0         rjmp  .+58       ; 0x56 <__vector_13>
16
  1c:  1b c0         rjmp  .+54       ; 0x54 <__bad_interrupt>
17
  1e:  1a c0         rjmp  .+52       ; 0x54 <__bad_interrupt>
18
  20:  19 c0         rjmp  .+50       ; 0x54 <__bad_interrupt>
Gast #1106658
Lesenswert?

Hab mal eben deinen Code durch den GCC gejagt (da du weder die 
verwendete GCC-Version noch dein Makefile beigelegt hast hab ich die 
Defaults von Code::Blocks+GCC V4.2.2 im debug-Build benutzt).
1
00000000 <__vectors>:
2
   0:  10 c0         rjmp  .+32       ; 0x22 <__ctors_end>
3
   2:  28 c0         rjmp  .+80       ; 0x54 <__bad_interrupt>
4
   4:  27 c0         rjmp  .+78       ; 0x54 <__bad_interrupt>
5
   6:  26 c0         rjmp  .+76       ; 0x54 <__bad_interrupt>
6
   8:  25 c0         rjmp  .+74       ; 0x54 <__bad_interrupt>
7
   a:  24 c0         rjmp  .+72       ; 0x54 <__bad_interrupt>
8
   c:  23 c0         rjmp  .+70       ; 0x54 <__bad_interrupt>
9
   e:  22 c0         rjmp  .+68       ; 0x54 <__bad_interrupt>
10
  10:  21 c0         rjmp  .+66       ; 0x54 <__bad_interrupt>
11
  12:  20 c0         rjmp  .+64       ; 0x54 <__bad_interrupt>
12
  14:  1f c0         rjmp  .+62       ; 0x54 <__bad_interrupt>
13
  16:  1e c0         rjmp  .+60       ; 0x54 <__bad_interrupt>
14
  18:  1d c0         rjmp  .+58       ; 0x54 <__bad_interrupt>
15
  1a:  1d c0         rjmp  .+58       ; 0x56 <__vector_13>
16
  1c:  1b c0         rjmp  .+54       ; 0x54 <__bad_interrupt>
17
  1e:  1a c0         rjmp  .+52       ; 0x54 <__bad_interrupt>
18
  20:  19 c0         rjmp  .+50       ; 0x54 <__bad_interrupt>

Hier sind alle 17 Vektoren drin. Und der Vektor für den ADC-Interrupt 
scheint auch an der richtigen Stelle zu sein.

Wie rufst du den GCC den auf?
Gast #1106675
Lesenswert?

Zuerst einmal vielen Dank für eure Mühe.

Jetzt weiß ich wenigstens, dass es an den Paramtern (also an mir) und 
nicht am GCC liegt.

Die GCC Version ist gcc version 4.3.2 (WinAVR 20081205). Also der 
aktuellste WinAVR.

Nachfolgend mal die einzelnen Aufrufe, so wie sie das Makefile absetzt:
1
avr-gcc -c -mmcu=attiny24 -I. -gstabs -Os -DF_CPU=8000000UL -funsigned-char -funsigned-bitfields -fpack-struct -fshort-enums -Wall -Wstrict-prototypes -Wundef -Wa,-adhlns=./BUILD/test.lst  -std=gnu99 -MMD -MP -MF ./BUILD/test.o.d test.c -o BUILD/test.o 
2
test.c:28: warning: function declaration isn't a prototype
3
test.c:27: warning: return type of 'main' is not 'int'
4
avr-gcc -Wl,-Map=./BUILD/main.map,--cref      ./BUILD/test.o      -o ./BUILD/main.elf
5
avr-objcopy -O ihex -R .eeprom -R .fuse -R .lock BUILD/main.elf BUILD/main.hex
6
avr-objcopy -j .eeprom --set-section-flags=.eeprom="alloc,load" --change-section-lma .eeprom=0 --no-change-warnings -O ihex BUILD/main.elf BUILD/main.eep || exit 0
7
avr-objdump -h -S -z BUILD/main.elf > BUILD/main.lss
8
avr-nm -n BUILD/main.elf > BUILD/main.sym
Gast #1106794
Lesenswert?

Hallo yalu,

danke für den Tip. Manchmal sieht man den Wald vor lauter Bäumen nicht. 
Ich hab immer die Compilerparameter überprüft und den Linker ganz 
übersehen. Werd gleich mal das Makefile anpassen und nochmal Bescheid 
geben.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren