www.mikrocontroller.net

Forum: Compiler & IDEs Warum geht das nicht?


Autor: MrPink (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
sorry bin blutiger anfänger und werde aus dem toturial einfach nciht 
schlau, bzw die foren suche hilft mir auch nciht weiter.


ich habe das programmier board STK500 und nen ATMEGA8

ich möchte zwei eingangspins vergleichen und je nach ergebniss etwas auf 
nem ausgangs pin rausschmeissen.



#include <avr/io.h>

int main (void)
{

   DDRD = 0x00;
   DDRB = 0xff;

   while(1)
   {
    if (PIND1 == PIND2)
    {
      PORTB1 = 1;
    }
   }

   return 0;
}

ich stelle mir jetzt vor das ich SW1 oder SW2 drücke und dann sollte 
doch LED1 aus gehen oder nicht?

ich habe schon so viel rumprobiert aber ich bekomme das nicht hin.

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Weil da effektiv steht:
   if (1 == 2)

Autor: Mr Pink (mrpink)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
habs auch schon mit = versucht dem gefällt das

PORTB1 = 1;

nicht.

main.c:11: error: lvalue required as left operand of assignment
main.c:13: error: lvalue required as left operand of assignment


Kann ich Überhaupt mit PORTB1 die einzelnen beinchen ansprechen? bzw dei 
auf 1 oder 0 setzen?

Autor: Skua (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wenn beide Tasten gleich sind geht die LED an.
Aus geht sie nie da gibts keine Anweisung für.

Autor: Chris L. (kingkernel)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Schau dir mal das AVR-GCC-Tutorial hier auf der Seite an. Speziell das 
Ansprechen und Setzen von Ausgangsregistern!
Du musst so arbeiten PORTB |= 1 << PB1; für die ausgabe und PINB & (1 << 
PB0) für die eingabe.

Auf anhieb würde ich es so machen (ungetestet):
#include <avr/io.h>

int main (void)
{

   DDRD = 0x00;
   DDRB = 0xff;

   while(1)
   {
    if ((PIND & (1 << PD1)) == (PIND & (1 << PD2)))
    {
      PORTB |= 1 << PB1;
    }
   }

   return 0;
}
ausschalten kannst du die LED damit aber nicht mehr, dafür fehlt noch 
der entsprechende Code. Ausserdem geht die LED dann auch an, wenn beide 
Tasten NICHT gedrückt sind, es wird ja nur geprüft, ob beide Tasten die 
selbe Stellung haben!

Autor: Helmut Lenzen (helmi1)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>PORTB1 = 1;


PORTB |= 0x01;     sollte die LED anmachen
PORTB &= ~0x01;    sollte die LED ausmachen

Gruss Helmi

Autor: Mr Pink (mrpink)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ja ok stimmt

allerdings bekomme ich den fehler was die ausgangs port zuweisung an 
geht nicht weg.


in C würde ich das so schreiben aber die PORTB1 zuweisung gibt immer den 
fehler:



#include <avr/io.h>

int main (void)
{

   DDRD = 0x00;
   DDRB = 0xff;

   while(1)
   {
    if (PIND1 == PIND2)
    {
      PORTB1 = 1;   //main.c:13: error: lvalue required as left operand 
of assignment
    }

    if (PIND1 != PIND2)
    {
      PORTB1 = 0;   //main.c:18: error: lvalue required as left operand 
of assignment
    }
   }

   return 0;
}

Autor: Chris L. (kingkernel)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Oder das Direkte setzen des entsprechenden Bytes. In GCC ist es nicht 
möglich einzellne Pins eines Ports direkt anzusprechen!

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
PIND1 ist die Nummer des Portpins (und damit ziemlich blödsinnig). Nicht 
der Portpin selbst. Bei
  PORTB1 = 1;
steht also
  1 = 1;
da.

Was funktioniert:
  if (((PINB >> PINB1) ^ (PINB >> PINB2)) & 1)
    ...verschieden...
aber schön sieht es nicht aus.

Elegant wird das nur wenn die Portpins als Bitfeld definiert sind.

Autor: gerd (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,
das ist quatsch:

if (PIND1 == PIND2)
    {
      PORTB1 = 1;
    }


Du kannst "Einzelpins" so nicht ansprechen.

Versuche mal:

if ( (PIND&(1<<PD1)) & (PIND&(1<<PD2)) )
{
   PORTB|=(1<<PB1);
}

so wird abgefragt ob beide Pins PD1 & PD2 true sind.

Ich glaube beim STK500 schalten die Taster auf Masse und die LED´s 
leuchten wenn der PORT Low ist.
Also hier:


//vorher
PORTB|=(1<<PB1); //PIN 5V => LED aus


if ( (!(PIND&(1<<PD1)) & (!(PIND&(1<<PD2)) )
{
   PORTB&=~(1<<PB1);
}


Hier ist alles ganz genau erklärt: 
http://www.mikrocontroller.net/articles/AVR-GCC-Tutorial

Hier hilft als Anfänger nur lesen, lesen, probieren, lesen ;-)

gerd

Autor: Mr Pink (mrpink)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Erstmal danke für die hilfe (obwohl ich das auch im toturial hätte 
finden müssen)

denke auch ich habe es soweit verstanden

allerdings muss irgendwo noch ein logikfehler sein

SW1=0 SW2=1 LED0=0 (an)   ok
SW1=1 SW2=0 LED0=0 (an)   ok
SW1=1 SW2=1 LED0=1 (aus)  ok
SW1=0 SW2=0 LED0=0 (an)   nicht ok


#include <avr/io.h>

int main (void)
{

   DDRD = 0x00;
   DDRB = 0xff;

   while(1)
   {
    if ( ~((PIND&(1<<PD1)) ^ (PIND&(1<<PD2))) )
    {
      PORTB |= (1<<PB0);
    }

    if ( (PIND&(1<<PD1)) ^ (PIND&(1<<PD2)) )
    {
      PORTB &= ~(1<<PB0);
    }
   }
   return 0;

}

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
PIND&(1<<PD1) => Wert 0x00 oder 0x02
PIND&(1<<PD2) => Wert 0x00 oder 0x04

if ( ~((PIND&(1<<PD1)) ^ (PIND&(1<<PD2))) )
  läuft also auf
if ( ~(0x02 ^ 0x04) )
  raus. Wieder nix, weil dabei ~0x06 rauskommt. Wenn schon so, dann
if (((PIND&(1<<PD1)) != 0) == ((PIND&(1<<PD2)) != 0))

Autor: Mr Pink (mrpink)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
das ist doch nur die abfrage für (sw1=1 und sw2=1)  also "AND"       ... 
oder?

ich suche ein XNOR

X  Y  |  Q
 ----------
0  0  |  1
0  1  |  0
1  0  |  0
1  1  |  1

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wenn das eine Antwort auf mein Posting war: falsch.
  (PIND&(1<<PD1)) != 0) => 0 oder 1
  (PIND&(1<<PD2)) != 0) => 0 oder 1

Autor: Mr Pink (mrpink)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ok danke

irgendwie ist das board komisch ...

die LED leuchtet zwar die ganzezeit .... aber wenn ich SW1 oder SW2 
drücke leuchtet sie etwas heller, bzw geht aus wenn ich beide drücke 
..... der code muss aber richtig sein.

bei invertierter ausgabe funktioniert die schaltung

Autor: Lothar Miller (lkmiller) (Moderator) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> die LED leuchtet zwar die ganzezeit .... aber wenn ich SW1 oder SW2
> drücke leuchtet sie etwas heller, bzw geht aus wenn ich beide drücke

Dann wird sie ohne Tastendruck sehr schnell ein- und wieder 
ausgeschaltet. Mit 1 Taste dann ganz ein, mit beiden Tasten ganz aus. 
Warum, das kann man ohne den zugehörigen Code (der übrigens mit [/c] und 
[c] schön formatiert wird) nicht sagen.

> ..... der code muss aber richtig sein.
Ja, wie sagte der Programmierer selbstbewusst: "Mein Code läuft."

Autor: Peter Dannegger (peda)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Christian L. wrote:
> Oder das Direkte setzen des entsprechenden Bytes. In GCC ist es nicht
> möglich einzellne Pins eines Ports direkt anzusprechen!

Das ist Quatsch.

Natürlich kann man in GCC Bitvariablen definieren und damit einzelne 
Portpins ansprechen. Ich mache das schon lange so.
Dadurch sehen die Programme gleich viel übersichtlicher aus.

Die ultimative Lösung wurde 2006 von Volker gepostet:

Beitrag "Re: #define in C"


Sie wurde kürzlich erst in das AVR-Tutorial aufgenommen:

http://www.avrfreaks.net/index.php?name=PNphpBB2&f...


Peter

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.