AVR GCC erzeugt unmengen an code?

OP #797272
Lesenswert?

Hi!

Ich habe die ganze zeit in Assembler programmiert und probiere nun mal 
C. Leider klappt es noch nicht so. Ich habe hier versucht eine LED zum 
blinken zu bringen. Die Blinkfrequenz sollte mit einem Potentiometer 
(Spannungsteiler) am ADC2 bestimmt werden. Hierzu muss der ADCwert als 
delay-Wert genommen werden.

Allerdings erzeugt mir dieser kleine Code 4kb?!

Program:    3956 bytes (193.2% Full)
(.text + .data + .bootloader)

Data:        266 bytes (207.8% Full)
(.data + .bss + .noinit)

Was habe ich da denn falsch gemacht? Wenn ich in delay einen normalen 
Wert eintrage funktioniert es. Wenn ich ADC zuerst in eine andere 
Variable einlese und dann in delay kopiere geht es wieder nicht. Wenn 
ich ADC direkt in die funktion _delay_ms(); einsetze funktioniert es 
auch nicht. Unabhängig vom Optimierungsgrad.

nutze AVRStudio und die neuste Version von GCC.

lg PoWl
1
#include <avr/io.h>
2
#include <stdint.h>
3
#include <util/delay.h>
4

5
uint16_t delay;
6

7
int main(void)
8
{
9
  ADMUX = (1 << REFS1) | (1 << REFS0) | (0b00010);
10
  ADCSR = (1 << ADEN) | (0b101);
11

12
  while(1)
13
  {
14
    ADCSR |= (1 << ADSC);
15
    loop_until_bit_is_set(ADCSR, ADIF);
16

17
    delay = ADC;
18

19
    _delay_ms(delay);
20
  }
21
}
OP #797290
Lesenswert?

Ja das mit Timern kommt noch, ist nur zum Probieren. Die LED, hier als 
"Heizung" gekennzeichnet, flackert allerdings bei niedrigen ADC-Werten 
bzw. wenn ich den Eingang auf Masse lege. Woran könnte das denn nur 
liegen?

//Edit: mit einem 100nF Kerko zwischen GND und AREF funktionierts 
besser, flackert aber immernoch etwas.

//Edit2: Des Rätsels Lösung: mein doofes Steckboard ist wiedermal dran 
schuld. Die eine Masseschiene ist nicht gut mit der anderen verbunden.
1
#include <avr/io.h>
2
#include <stdint.h>
3
#include <util/delay.h>
4

5
#define ControlDDR DDRA
6
#define ControlPORT PORTA
7

8
#define Motor 6
9
#define Heizung 7
10

11
uint16_t delay;
12

13
int main(void)
14
{
15
  ADMUX = (1 << REFS1) | (1 << REFS0) | (0b00010);
16
  ADCSR = (1 << ADEN) | (0b101);
17

18
  ControlDDR |= (1 << Heizung);
19

20
  while(1)
21
  {
22
    if(bit_is_set(ControlPORT, Heizung))
23
  {
24
    ControlPORT &= ~(1 << Heizung);
25
  }
26
  else
27
  {
28
      ControlPORT |= (1 << Heizung);
29
  }
30

31
    ADCSR |= (1 << ADSC);
32
  loop_until_bit_is_set(ADCSR, ADIF);
33

34
    delay = ADC;
35

36
    while(delay--)
37
  {
38
    _delay_ms(1);
39
    }
40
  }
41
}
#797297
Lesenswert?

Paul Hamacher wrote:
> Ja das mit Timern kommt noch, ist nur zum Probieren. Die LED, hier als
> "Heizung" gekennzeichnet, flackert allerdings bei niedrigen ADC-Werten
> bzw. wenn ich den Eingang auf Masse lege. Woran könnte das denn nur
> liegen?

Hast du den Optimizer eingeschaltet?
_delay_ms liefert nur dann einigermassen korrekte Zeiten,
wenn der Optimizer an ist.

Ansonsten:
Du solltest dir eher Sorgen um die langen Zeiten machen.
Der ADC liefert bei voller Aussteuerung einen Wert von 1023.
1023 mal 1ms macht weit über 1 Sekunde Zeit-Differnz zwischen
ein und aus der LED

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