Einfache PWM mit Spannung ADC steuern (Attiny13)

Gast #1548645
Lesenswert?

Hallo,
ich bin neu im Bereich Mikrocontroller und habe mir ein Programm für den 
Attiny13 geschrieben das abhängig von der anliegenden Spannung über den 
ADC das verhältnis von LOW und HIGH des PWMs einstellt:

1
.include "tn13def.inc"
2

3

4
rjmp   Anfang
5
Anfang:
6
;Pins belegen
7
      ldi r16, 0b11111111
8
      out DDRB,r16
9
      ldi r16, 0x00
10
      out PORTB,r16
11
   
12
;ADC initialisieren
13
      ldi    r16, 0b00100010
14
    out    ADMUX, r16
15
    ldi    r16, 0b11000111
16
    out    ADCSRA, r16
17

18
 
19
Schleife:
20
      sbi    portb,0
21
adc0_wait:
22
    sbic   ADCSRA,ADSC
23
    rjmp   adc0_wait
24
    in     r18, ADCL
25
    in     r17, ADCH
26
    ldi    r16,255
27
    sub    r16,r17
28
Warten1:
29
      dec    r17
30
    brne   Warten1
31
    cbi    portb,0
32
Warten2:
33
      dec    r16
34
    brne   Warten2
35
rjmp Schleife

Nun habe ich das Problem, wenn ich ein 1MOhm-Poti anschließe, ändert 
sich die Helligkeit der Led nur wenn ich es voll in Einrichtung drehe 
und auch nur auf etwa 50%, wenn ich aber ein 500Ohm-Poti anlegen dann 
lässt sich die Led wunderschön von etwa 90% bis 0% dimmen.
Ich verstehe im Moment nicht so richtig das Problem, weil normalerweise 
ja ein größerer Poti die Schaltung weniger beeinflusst. Könnte es vllt 
sein das irgendein Pullup- oder pulldown-widerstand am Eingang 
eingeschaltet ist und somit das Poti die Spannung nicht alleine 
beeinflusst?

Ich hoffe ihr könnt mir weiterhelfen und falls ich noch mit 
irgendwelchen Infos helfen kann, einfach bescheid sagen.

Gruß Fr00sch
Gast #1548667
Lesenswert?

Hallo,

Auch wenn ich mit der ADC nicht sooo auskenne, würde ich mal behaupten 
das Dein Problem darin begründet ist, das Du zuerst ALLE PBx als 
Ausgänge definierst. Der ADC kann trotzdem werte von den Ports einlesen, 
aber Dein Poti muss "gegen" den Port, der als Ausgang geschaltet ist und 
damit Strom (bis 60mA!) liefert, "anarbeiten".
Über den 1MOhm Poti lacht der Augang nur, damit wirst Du kaum 
Spannungsänderung erziehlen.

Mein Vorschlag wäre: (zumal im Programm später eh nur PB0 geschaltet 
wird)

;Pins belegen
      ldi r16, 0b00000001
      out DDRB,r16
      ldi r16, 0x00
      out PORTB,r16

Habs nicht Probiert, klingt aber Plausibel...

Bis dann und viel Glück (!)  =^.^=
Gast #1548689
Lesenswert?

danke erstmal für die schnelle Antwort


Ich weis aber nicht wie ich ihn abschalte... am anfang definiere ich 
portB als Ausgang
1
ldi r16,0b11111111
2
out DDRB,r16
und gebe allen Pins keinen pullup
1
ldi r16, 0x00
2
out PORTB,r16
und im späteren verlauf definiere ich einen ausgang als adc-eingang ... 
meiner theorie nach müsste jetzt dort ein eingang ohne pullup sein, aber 
ist anscheinend nicht so ...

kann ich die pullups per MCUCR abschalten wieder?

ich hab nichts über einen 5k-Poti gefunden im Datenblatt,unter welcher 
rubrik soll das stehen?
#1548693
Lesenswert?

> am anfang definiere ich
> portB als Ausgang
> ....
> und im späteren verlauf definiere ich einen ausgang als adc-eingang ...
> meiner theorie nach müsste jetzt dort ein eingang ohne pullup sein, aber
> ist anscheinend nicht so ...

Das ist nur Deine Theorie.  Der Ausgang bleibt Ausgang.  Abhilfe ist, 
ihn gleich gar nicht als solchen zu definieren.
Gast #1548697
Lesenswert?

Das klingt logisch Mahnel und habe ich auch schon probiert, aus 
irgendeinem Grund gabs da aber Probleme, werds heute abend nochmal 
probieren und mich dann nochmal melden.

Zum Thema Poti habe ich was gefunden im Datenblatt:
Auf Seite 120 Thema 18.7 ADC Chrakteristiken steht unter Analog Input 
Resistance: 1MOhm
#1548706
Lesenswert?

> Zum Thema Poti habe ich was gefunden im Datenblatt:
> Auf Seite 120 Thema 18.7 ADC Chrakteristiken steht unter Analog Input
> Resistance: 1MOhm

Es lässt sich in 14.8 auch Folgendes finden:

The ADC is optimized for analog signals with an output impedance of 
approximately 10 kΩ or less.
Gast #1548708
Lesenswert?

Fr00sch schrieb:
> am anfang definiere ich
> portB als Ausgang
> ldi r16,0b11111111
> out DDRB,r16

Richtig, damit sind ALLE PBs als Ausgänge geschaltet.

> und gebe allen Pins keinen pullup
> ldi r16, 0x00
> out PORTB,r16

Nicht ganz richtig: damit hast Du ALLE PBs auf "0" geschaltet.
Wenn jetzt eine "Stromquelle" gegen "1" angelegt wird, wird der Strom 
über den MC/Port gegen "0" abfliessen.

...hoffe geholfen zu haben...
Gast #1549298
Lesenswert?

kA warum, aber deine Idee funktioniert nicht, das Drehen am Poti 
verändert nichts, die helligkeit der LED bleibt konstant bei etwa 50%!

Quellcode jetzt:

1
.include "tn13def.inc"
2

3

4
rjmp   Anfang
5
Anfang:
6
;Pins belegen
7
      sbi    DDRB,0
8

9
;ADC initialisieren
10
      ldi    r16, 0b00100010
11
    out    ADMUX, r16
12
    ldi    r16, 0b11000111
13
    out    ADCSRA, r16
14

15
 
16
Schleife:
17
      sbi    portb,0
18
adc0_wait:
19
    sbic   ADCSRA,ADSC
20
    rjmp   adc0_wait
21
    in     r18, ADCL
22
    in     r17, ADCH
23
    ldi    r16,255
24
    sub    r16,r17
25
Warten1:
26
      dec    r17
27
    brne   Warten1
28
    cbi    portb,0
29
Warten2:
30
      dec    r16
31
    brne   Warten2
32
rjmp Schleife
#1551652
Lesenswert?

Fr00sch schrieb:
> sbic   ADCSRA,ADSC
> startet in der schleife die conversion!

Nein.
Das wartet bis die Konvertierung fertig ist.
Aber wo wird sie erneut gestartet?

Dazu müsstest du das ADSC Bit irgendwo erneut setzen. Das tust du aber 
nicht! Mit sbic wird ein Bit abgefragt, aber nicht gesetzt.

  sbic     ... skip (next instruction, if) bit is clear

zusammen mit dem nachfolgendem rjmp ergibt das eine Schleife, die 
solange wartet, bis das ADSC Bit von 1 auf 0 wechselt, welches wiederrum 
laut Beschreibung anzeigt, dass der ADC fertig ist.
#1551657
Lesenswert?

Fr00sch schrieb:
> 7.)1 macht den ADC an,
> 6.)start die conversion,
> 5.)ADC Interrupt Flag keine,
> 4.)ADC Interrupt Enable aus,
> 2.)Prescaler Factor
> 1.)Prescaler Factor
> 0.)Prescaler Factor
>
> Seite 91 und 92 im Datenblatt

Worauf ich hinaus wollte:
Man kann die Binärzahl auch so schreiben, dass man die Bits beim Namen 
nennt.

http://www.mikrocontroller.net/articles/AVR-Tutorial:_ADC

Vergleich doch mal zb das hier
1
    ldi     temp1, (1<<ADEN) | (1<<ADPS2) | (1<<ADPS1) | (1<<ADPS0)
2
    out     ADCSRA, temp1
mit deiner Version. Wo sieht man eher, was Sache ist?

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