Hallo ich finde in meinem quellcode den fehler nicht, und der tiny gibt
mir einfach an den ausgängen nichts aus, egal welche spannung ich an PB4
anlege, hab ich etwas vergessen?
An PB4 lege ich eine externe spannung an die gemessen werden soll
an PB0-3 sind einfach leds mit widerstand an gnd angeschlossen
quellcode:
1
#include<avr/io.h>
2
#include<inttypes.h>
3
#ifndef F_CPU
4
#warning "F_CPU war noch nicht definiert, wird nun mit 1000000 definiert"
5
#define F_CPU 1000000 /* Quarz mit 1 Mhz */
6
#endif
7
#include<util/delay.h> /* bei alter avr-libc: #include <avr/delay.h> */
Hallo,
zumindest mein WinAVR kann das nicht...
../main.c:1: error: MCU 'attiny15' supported for assembler only
c:/winavr-20090313/lib/gcc/../../avr/include/avr/iotn15.h:51:4: warning:
#warning "MCU not supported by the C compiler"
Gruß aus Berlin
Michael
NickJag wrote:
> An PB4 lege ich eine externe spannung an die gemessen werden soll> an PB0-3 sind einfach leds mit widerstand an gnd angeschlossenAVRs haben OC-Ausgänge. Hänge die LED daher zwischen Vcc und Port.
Ansonsten könnte es mit ramlosen AVRs schon funktionieren, wenn die
Variablen sauber in die Register passen. Kommt aber auf den Compiler
drauf an. Zur Sicherheit vor den Variablendefinitionen "register" davor
hängen.
1
uint16_tReadChannel(uint8_tmux)
2
{
3
registeruint8_ti;
4
registeruint16_tresult;
und
1
while(1)
2
{
3
registeruint16_twert;
Außerdem:
1
staticuint16_tLED1=0x00C8;
2
staticuint16_tLED2=0x0190;
3
...
Hier sollte aber zur Sicherheit überall ein "static" davor stehen.
Eventuell erkennt es der Compiler aber selber, dass diese Variablen nie
verändert werden und trägt sie als konstant in den Code ein.
Christian
Christian Harf wrote:
> NickJag wrote:>> An PB4 lege ich eine externe spannung an die gemessen werden soll>> an PB0-3 sind einfach leds mit widerstand an gnd angeschlossen>> AVRs haben OC-Ausgänge. Hänge die LED daher zwischen Vcc und Port.
Unsinn. AVRs haben Push-Pull-Ausgänge und dementsprechend ist es in den
meisten Fällen wurscht, ob man LEDs High- oder Low-Side anschließt.
> Ansonsten könnte es mit ramlosen AVRs schon funktionieren, wenn die> Variablen sauber in die Register passen. Kommt aber auf den Compiler> drauf an. Zur Sicherheit vor den Variablendefinitionen "register" davor> hängen.
Auch das bringt nichts. Erstens funktioniert es sowieso nur dann, wenn
der Compiler die besagten Controller überhaupt unterstützt. Und wenn
er sie unterstützt, dann legt er sich die Variablen schon selber zurecht
(also da hin, wo Platz ist)!
Der Typqualifizierer register bringt hier nicht nur nichts, der
Compiler ist auch generell nicht daran gebunden. Und ein Compiler, der
die RAM-losen AVRs unterstützt, weiß selber, dass er Variablen in
Register legen muss. Wohin auch sonst?
> Hier sollte aber zur Sicherheit überall ein "static" davor stehen.> Eventuell erkennt es der Compiler aber selber, dass diese Variablen nie> verändert werden und trägt sie als konstant in den Code ein.
Hä? Bitte nimm Dir ein gutes C-Buch zur Hand und lies es gründlich
durch! static hat ausschließlich einen Einfluss auf den
Gültigkeitsbereich (Scope) einer Variablen. Es hat weder etwas mit
"konstant" noch mit dem "Verändern" von Variablen zu tun! Außerdem trägt
der Compiler nirgends etwas als "konstant" ein.
Bei wenig Speicherressourcen sollte man auf lokale /static/-Variablen
eher verzichten, weil die genau wie globale Variablen permanent den
ihnen zugeteilten Speicher belegen!
Eine Variable, die sich nicht verändert, gehört übrigens in den
Flash-Speicher und nicht ins RAM und erst recht nicht in ein Register...
zum einen:
> /* nach Aktivieren des ADC wird ein "Dummy-Readout" empfohlen, man liest> also einen Wert und verwirft diesen, um den ADC "warmlaufen zu lassen" >*/
das ist nur 1x nach Reset notwendig
und zum anderen was zumindest ein wichtiger Fehler ist:
> if ((wert >= LED1) & (wert < LED2))
du meintest vermutlich && statt &
Hallo,
hab auch mal ne Spannungsanzeige auf nen atmega8 gemacht. Weil es aber
mehr als 5V waren, hab ich einfach 3x10k widerstände in reihe geschaltet
und von einem die Spannung abgenommen.
(in basic)
dim A(und B) as Single
A = 5 / 1024 // für 5V und 10-bit
B = (ADC-Wert * A) * 3 // * 3 wegen spannungsteiler
und dann mit Fusing b so umwandeln dass es ausgegeben werden kann (vlt.
gehts in C auch so)
mfg
Walter wrote:
> zum einen:>> /* nach Aktivieren des ADC wird ein "Dummy-Readout" empfohlen, man liest>> also einen Wert und verwirft diesen, um den ADC "warmlaufen zu lassen" >*/> das ist nur 1x nach Reset notwendig
Nein, das ist nach dem Aktivieren des ADC über ADEN notwendig. Und wenn
man den ADC nach jeder Wandlung ausschaltet, sollte man auch bei jedem
Wiedereinschalten einen Dummy-Read-Out machen. Allerdings ist es in den
meisten Fällen sinnvoll, den ADC einfach anzulassen. Nur wenn man
wirklich Strom sparen muss und nur sporadisch wandelt, sollte man den
ADC nach einer Messung ausschalten.
> und zum anderen was zumindest ein wichtiger Fehler ist:>> if ((wert >= LED1) & (wert < LED2))> du meintest vermutlich && statt &
Ist in dem Fall aber egal. Beide Teilausdrücke können nur 0 oder 1 sein,
und da klappt es auch mit nem bitweisen UND.
Johannes M. wrote:
> Unsinn. AVRs haben Push-Pull-Ausgänge und dementsprechend ist es in den> meisten Fällen wurscht, ob man LEDs High- oder Low-Side anschließt.
Hmm, stimmt. Habe gerade nochmal in der Doku nachgeschaut. Sorry, dann
war ich bisher immer falsch informiert. Ich meinte, mal sowas gelesen zu
haben.
Danke für den Hinweis.
> Der Typqualifizierer register bringt hier nicht nur nichts, der> Compiler ist auch generell nicht daran gebunden. Und ein Compiler, der> die RAM-losen AVRs unterstützt, weiß selber, dass er Variablen in> Register legen muss. Wohin auch sonst?
Kommt auf den Compiler an. Wenn er nichts davon weiß, ob Ram oder kein
Ram, dann ist "register" notwendig. Ich weiß natürlich nicht, was hier
für ein Compiler verwendet wird.
"Normally, the compiler determines what data is to be stored in the
registers of the CPU at what times. However, the C language provides the
storage class register so that the programmer can ``suggest'' to the
compiler that particular automatic variables should be allocated to CPU
registers, if possible. Thus, register variables provide a certain
control over efficiency of program execution. Variables which are used
repeatedly or whose access times are critical, may be declared to be of
storage class register."
> Hä? Bitte nimm Dir ein gutes C-Buch zur Hand und lies es gründlich> durch! static hat ausschließlich einen Einfluss auf den> Gültigkeitsbereich (Scope) einer Variablen. Es hat weder etwas mit> "konstant" noch mit dem "Verändern" von Variablen zu tun! Außerdem trägt> der Compiler nirgends etwas als "konstant" ein.
Sorry, habe schon zielich lange nicht mehr in C programmiert. Hatte C&R
das auch schon so gesehen? Ich muß bei Zeiten meine C-Kenntnisse nochmal
auffrischen.
Jaja, mann sollte keine Java-Konstrukte in C zurückführen und dann noch
die Hälfte ("final") vergessen. Ich nehme alles zurück und behaupte das
Gegenteil.
> Bei wenig Speicherressourcen sollte man auf lokale /static/-Variablen> eher verzichten, weil die genau wie globale Variablen permanent den> ihnen zugeteilten Speicher belegen!
Meist optimiert der Compiler nur einmalig benutzte und nicht veänderte
Variablen sowieso weg.
Was ich eigentlich meinte, war ein "#define". Also statt "uint16_t LED1
= 0x00C8;" schreibt man besser "#define LED1 0x00C8". Das ist dann aber
nichts für den C-Compiler, sondern für den Präprozessor.
> Eine Variable, die sich nicht verändert, gehört übrigens in den> Flash-Speicher und nicht ins RAM und erst recht nicht in ein Register...
Das habe ich auch nie gesagt. Ich wollte nur, dass der Compiler die
konstanten "Variablen" wegoptimiert. Ins Register gehören natürlich alle
kurzlebigen Variablen. Wenn diese knapp werden, muss man halt ins RAM
auslagern (wenn vorhanden).