Forum: Mikrocontroller und Digitale Elektronik Übertragung von High- und Low-Signalen zwischen zwei AVR


von Chris K. (ati13)


Lesenswert?

Hallo,

ich möchte gerne High- bzw. Low-Pegel von einem AVR zu einem anderen 
übertragen. Leider habe ich Probleme mit der Realisierung. Beide 
Programme (Ausgabe der "einsen" bzw. "nullen" auf der einen Seite, 
einlesen der "einsen" mit Hilfe von Tastern und Pull-Ups auf der 
anderen) hab ich natürlich bereits einzeln getestet. -> Fehler in den 
Programmen sind ausgeschlossen, es muss an der Beschaltung oder 
ähnlichem liegen.
Bis jetzt habe ich einfach Aus- und Eingänge der AVR direkt verbunden, 
beide Massen ebenfalls. Die internen Pull-Ups habe ich nicht aktiviert, 
weil ja theoretisch zu jedem Zeitpunkt ein definierter Zustand an den 
Eingangspins anliegen sollte (richtig?).
Wo liegt also der (Denk-) Fehler?

Vorab schonmal danke!
Chris

von Max H. (hartl192)


Lesenswert?

Chris K. schrieb:
> es muss an der Beschaltung oder
> ähnlichem liegen.
Dann zeig uns die mal, am besten zusammen mit dem Quellcode.

von spess53 (Gast)


Lesenswert?

Hi

>Wo liegt also der (Denk-) Fehler?

da

>Fehler in den Programmen sind ausgeschlossen, ...

MfG Spess

von Kaj (Gast)


Lesenswert?

Chris K. schrieb:
> Fehler in den
> Programmen sind ausgeschlossen,
Warum faehrt das Auto nicht mehr?
Am Benzin kann's jeden falls nicht liegen, is naemlich keins drin.

von Chris K. (ati13)


Angehängte Dateien:

Lesenswert?

Ist ja gut, wenn's sein muss poste ich den Code...
Vorher möchte ich aber meine eigentliche Frage beantwortet haben.
(-> siehe Schaltung)
Es geht mir nur um's Prinzip! Also:
Wenn ich dem AVR1 sage
1
portB = 0b00001111; // PortB, Pin0..3 auf "1"setzen
und beim AVR2 abfrage
1
if(portB = 0b00001111){/*mach was*/} // Signale an PortB, Pin0..3 abfragen
...würde dies so funktionieren (mit dieser Art von Schaltung) oder 
müsste ich etwas verändern?

Falls ihr mir noch nicht richtig folgen könnt oder den Fehler im 
Programm vermutet, kann ich auch den kompletten Code posten. (der aber 
recht umfangreich ist...)

PS: Die Abfrage gestalte ich in Wirklichkeit etwas anders, k.A. ob die 
Beispiel-Syntax so stimmt oder nicht. Es geht nur um's Prinzip!

von asterix (Gast)


Lesenswert?

es geht im Prinzip also nur ums Prinzip...

-das ist kein Schaltplan, höchstens eine Skizze
-deine Quellcode ist zu groß? Dann minimiere diesen
-die Abfrage gestaltest du anders als beschrieben? ja wie denn nun

so wirst du nie brauchbare Antworten bekommen ! ;-)


um deiner sperrlichen Frage eine sperrliche Antwort zu liefern: Ja, so 
etwas kann funktionieren

von Falk B. (falk)


Lesenswert?

@ Chris K. (ati13)

>if(portB = 0b00001111){/*mach was*/} // Signale an PortB, Pin0..3 abfragen

FALSCH! Eher so

if(PINB = 0b00001111){/*mach was*/} // Signale an PortB, Pin0..3 
abfragen


>PS: Die Abfrage gestalte ich in Wirklichkeit etwas anders, k.A. ob die
>Beispiel-Syntax so stimmt oder nicht. Es geht nur um's Prinzip!

Eben DARUM soll man IMMER originalen Code posten und keine 
zuzammengetippten Codefetzen!

Siehe

http://www.mikrocontroller.net/articles/Netiquette#Klare_Beschreibung_des_Problems

von Max H. (hartl192)


Lesenswert?

> if(portB = 0b00001111){/*mach was*/}
Das ist unabhängig von PortB immer True, siehe = vs. ==
Zum Abfragen von Eigängen nimmt man PINB

von uwe (Gast)


Lesenswert?

> FALSCH! Eher so
>
> if(PINB = 0b00001111){/*mach was*/} // Signale an PortB, Pin0..3
Eher so
  if(PINB == 0b00001111){/*mach was*/} // Signale an PortB, Pin0..3

von Andreas S. (Firma: Schweigstill IT) (schweigstill) Benutzerseite


Lesenswert?

Chris K. schrieb:
> und beim AVR2 abfrage
1
if(portB = 0b00001111){/*mach was*/} // Signale 
2
> an PortB, Pin0..3 abfragen
> ...würde dies so funktionieren (mit dieser Art von Schaltung) oder
> müsste ich etwas verändern?

Es ist beeindruckend, dass Du es geschafft hast, in dieser einen 
Programmzeile mindestens drei schwere Programmierfehler zu machen. Und 
bei derart schwachen Programmierkenntnissen auch noch zu behaupten, das 
eigentliche Programm sei fehlerfrei, ist schon reichlich vermessen.

Und die Initialisierung Deiner Ports in Sende- und Empfangsrichtung 
verheimlichst Du auch.

Warum soll man sich hier also damit abgeben, auf solchen hingerotzten 
Dreck auch noch inhaltlich einzugehen?

von Falk B. (falk)


Lesenswert?

@ uwe (Gast)

>Eher so
>  if(PINB == 0b00001111){/*mach was*/} // Signale an PortB, Pin0..3

Uuups. ;-)

Naja, wenn schon, dann WIRKLICH richtig, mit Bitmanipulation.

von Chris K. (ati13)


Lesenswert?

@ asterix

Dann ist es eben eine Skizze...diese zeigt aber eben genau mein Problem 
(nicht mehr und nicht weniger): kommen die Einsen und Nullen, die AVR1 
ausgibt überhaupt am AVR2 an, wenn ich einfach die entsprechenden Pins 
(und beide Massen) verbinde?

@ falk

Oh, da habe ich mich vertan, ich meinte eigentlich: if (PINB = ...)...

...der Code mit ausführlicher Kommentierung folgt dann demnächst ;-)

von uwe (Gast)


Lesenswert?

> Oh, da habe ich mich vertan, ich meinte eigentlich: if (PINB = ...)...
nein du meintest if (PINB == ...)...

von uwe (Gast)


Lesenswert?

Also wenn du es geschafft hast in einer Codezeile 2 Fehler zu machen und 
ich dein Programm jetz auf 20 Zeilen schätze, dann komme ich auf 40 
weitere Fehler.

von Route_66 H. (route_66)


Lesenswert?

Falk Brunner schrieb:
> @ uwe (Gast)
>
>>Eher so
>>  if(PINB == 0b00001111){/*mach was*/} // Signale an PortB, Pin0..3
>
> Uuups. ;-)
>
> Naja, wenn schon, dann WIRKLICH richtig, mit Bitmanipulation.

Da er nicht geschrieben hat, was seine Programmiersprache ist, z.B. bei 
Bascom oder Luna, könnte das einfache "=" sogar schon richtig sein.

von Falk B. (falk)


Lesenswert?

@Chris K. (ati13)

>(nicht mehr und nicht weniger): kommen die Einsen und Nullen, die AVR1
>ausgibt überhaupt am AVR2 an, wenn ich einfach die entsprechenden Pins
>(und beide Massen) verbinde?

Natürlich. Das ist elementarste E-Technik.

>Oh, da habe ich mich vertan, ich meinte eigentlich: if (PINB = ...)...

Du kennst den Unterschied zwischen = und == in C?

von Chris K. (ati13)


Lesenswert?

@ uwe

Richtig.

@ schweigstill

Wieso kommentierst du überaubt diesen Thread, wenn du mir eigentlich 
sowieso nicht helfen willst? Das ist doch nur verschwendete Zeit oder? 
Dann lass es doch einfach gleich bleiben...
Und wenn du mir nicht glaubst, dass es einzeln funktioniert hat, kann 
ich dir auch nicht helfen. Den Code-Auzug habe ich frei erfunden, um zu 
verdeutlichen, was mein Problem ist. Er kommt so nicht im Programm vor.

Wie gesagt, das vollständige Programm folgt demnächst...

von spess53 (Gast)


Lesenswert?

Hi

>Dann ist es eben eine Skizze...diese zeigt aber eben genau mein Problem
>(nicht mehr und nicht weniger): kommen die Einsen und Nullen, die AVR1
>ausgibt überhaupt am AVR2 an, wenn ich einfach die entsprechenden Pins
>(und beide Massen) verbinde?

Wenn die Datenrichtungsregister stimmen kommen die klar an. Allerdings 
würde ich mir Gedanken über Handshake-Signale machen. Dann weiß der 
Empfänger wann ein neues Signal anliegt und der Sender, wenn das Signal 
abgeholt/verarbeitet ist.

MfG Spess

von Chris K. (ati13)


Lesenswert?

@ falk

Ja, den kenne ich. C++ kommt Java ja syntaktisch ziemlich nahe. Und nach 
zwei Semestern Java sollte man solch eine elemtare Angelegenheit so 
langsam beherrschen können oder? ;-)

von MiWi (Gast)


Lesenswert?

Chris K. schrieb:
> @ uwe
>
> Richtig.
>
> @ schweigstill
>
> Wieso kommentierst du überaubt diesen Thread, wenn du mir eigentlich
> sowieso nicht helfen willst? Das ist doch nur verschwendete Zeit oder?
> Dann lass es doch einfach gleich bleiben...
> Und wenn du mir nicht glaubst, dass es einzeln funktioniert hat, kann
> ich dir auch nicht helfen. Den Code-Auzug habe ich frei erfunden, um zu
> verdeutlichen, was mein Problem ist. Er kommt so nicht im Programm vor.
>

Wenn DU hier Fragen stellst dann denk daran, daß andere dafür ihre 
Zeit aufwenden DIR zu antworten ohne Dir eine Rechnung zu stellen.

Stelle die Fragen also so, daß sie auch - mit aller (In)kompetenz - den 
aktuellen Zustand beschreiben und dokumentieren.

Schaltpläne, die nicht der Realität entsprechen und Code, der so nicht 
vorhanden ist.... ist gelinde gesagt eine Zumutung. Also rotz hier nicht 
so herum.

Grüße

MiWi

von Frank M. (ukw) (Moderator) Benutzerseite


Lesenswert?

Chris K. schrieb:
> Ist ja gut, wenn's sein muss poste ich den Code...

Ja, vorher hat das keinen Sinn. Es muss ja nicht das komplette Projekt 
sein. Wenn Du den Fehler auf ein Minimal-Programm reduzieren kannst, 
wirds einfacher, den Fehler zu finden.

Ich frage mich nur, wie Du das Handshake zwischen den beiden AVRs 
machst...

> Vorher möchte ich aber meine eigentliche Frage beantwortet haben.
> (-> siehe Schaltung)

In der Schaltung fehlen zumindest die Abblockkondensatoren und evtl. 
auch noch eine korrekte Reset-Beschaltung.

Wie lang sind die Kabel zwischen den beiden AVRs? 100 Meter oder 2 cm?

: Bearbeitet durch Moderator
von 0815 (Gast)


Lesenswert?

Chris K. schrieb:
> Und wenn du mir nicht glaubst, dass es einzeln funktioniert hat, kann
> ich dir auch nicht helfen. Den Code-Auzug habe ich frei erfunden, um zu
> verdeutlichen, was mein Problem ist. Er kommt so nicht im Programm vor.

Mit derartig getürkten und falschen Infos schaffst du dir hier keine 
Freunde.

von Karl H. (kbuchegg)


Lesenswert?

Chris K. schrieb:

> Den Code-Auzug habe ich frei erfunden, um zu
> verdeutlichen, was mein Problem ist. Er kommt so nicht im Programm vor.

Anfrage an Radio Eriwan:
Stimmt es, dass Iwan Iwanowitsch in der Lotterie ein rotes Auto gewonnen 
hat?
Antwort:
Im Prinzip ja.
Aber es war nicht Iwan Iwanowitsch, sondern Pjotr Petrowitsch.
Und es war kein Auto, sondern ein Fahrrad.
Und er hat es nicht gewonnen, sondern es ist ihm gestohlen worden.
Aber sonst stimmt alles.

von Andreas S. (Firma: Schweigstill IT) (schweigstill) Benutzerseite


Lesenswert?

Chris K. schrieb:
> Und wenn du mir nicht glaubst, dass es einzeln funktioniert hat,

Du hast nicht behauptet, dass das Programm einzeln funktioniert habe, 
sondern dass das Programm fehlerfrei sei:

> Fehler in den Programmen sind ausgeschlossen, ...

Das sind völlig unterschiedliche Aussagen, die kaum etwas gemeinsam 
haben. Ich habe auch nie behauptet, Dir nicht zu glauben, dass Dein 
Programm in dem von Dir getesteten Kontext funktioniert hätte.

Bevor Du hier also solche haarsträubenden Behauptungen zur 
Fehlerfreiheit aufstellst, solltest Du Dich erst einmal mehrere Jahre 
mit den Grundlagen der Testbarkeit von Software und Elektronik befasst 
haben.

von Chris K. (ati13)


Lesenswert?

@ MiWi
>Warum soll man sich hier also damit abgeben, auf solchen hingerotzten
>Dreck auch noch inhaltlich einzugehen?
(Zitat von schweigstill)

Ich hab jetzt nach diversen Beiträgen, die sich inhaltlich sehr ähneln 
begriffen, dass ich mein Problem ausführlicher schildern soll.
Aber solche besch...eidenen Beiträge (siehe Zitat) könnt ihr euch 
wirklich sparen! Ich wollte mein Anliegen doch einfach nur auf ein 
Minimum reduzieren. Anscheinend ist das so in Foren nicht üblich, weil 
man die Kenntnisse und Fähigkeiten der anderen nicht kennt.
Gut. Das hab ich nun verstanden und poste die wichtigsten Details meines 
Projektes/Programmes:

Zum Projekt allgemein:
Ich möchte damit eine 4-stufige Treppe effektvoll mit LED-Streifen 
beleuchten. Jeder der 4 Streifen soll einzeln vom µC angesteuert werden 
können, sodass gewisse Muster (z.B. Lauflicht) entstehen können. Im Code 
entspricht "Modus" dem auszugebenen Muster.

Teil1:
Dieser µC soll die Stellungen zweier Potis ermitteln und die Werte 
entsprechend quantisieren. Danach sollen insgesamt 2 3-bit-Werte am 
PortB ausgegeben werden. Die Leitung zum anderen Controller beträgt 
übrigens ca. 15-20m.
1
class Application : public Controller
2
{
3
    // Bausteine und Attribute .........................................
4
    protected: unsigned int moduswahl, g_wert, geschwindigkeit;
5
    protected: AdcMultiChannel potentiometer; // Klasse der Objekt-Biblioth. von SySi (myAVR)
6
    
7
    // Funktionen ......................................................
8
    public: void onStart()
9
    {
10
        // Pin-Konfigurationen 
11
        ddrB.bit0=1; //
12
        ddrB.bit1=1; // Modus
13
        ddrB.bit2=1; //
14
        ddrB.bit3=1;   //
15
        ddrB.bit4=1;   // Geschwindigkeit
16
        ddrB.bit5=1;   // 
17
        
18
        // Objekt konfigurieren
19
        potentiometer.config();    
20
        potentiometer.addChannel(0); // ADC-Kanal 0 
21
        potentiometer.addChannel(1); // ADC-Kanal 1 
22
        potentiometer.configInt();
23
        
24
        // Attribute
25
        moduswahl=0;
26
        g_wert=0;       
27
    } 
28
       
29
    public: void onWork()
30
    {       
31
        moduswahl = potentiometer.getValue10(0); // 10 bit-Wert vom Kanal 0 einlesen  
32
        
33
        // Bits 0 bis 2 sind für die Übergabe des Modus' gedacht
34
        if (moduswahl <= 200){
35
          portB = 0b00000000;  // alles aus (Geschw. egal)    
36
        } 
37
        else if ((moduswahl > 200) & (moduswahl <= 400)){
38
          portB = 0b00000001;  // alles an (Geschw. egal)
39
        }
40
      else if ((moduswahl > 400) & (moduswahl <= 600)){
41
          portB = (0b00000010 + geschw_ermitteln());  // Lauftlicht nach unten
42
        }
43
        else if ((moduswahl > 600) & (moduswahl <= 800)){ 
44
          portB = (0b00000011 + geschw_ermitteln());  // Lauflicht nach oben
45
      } 
46
      else if ((moduswahl > 800) & (moduswahl <= 1024)){ 
47
          portB = (0b00000100 + geschw_ermitteln());  // blinken
48
      }      
49
    } 
50
    
51
    public: int geschw_ermitteln() 
52
    {
53
    g_wert = potentiometer.getValue10(1); // 10 bit-Wert vom Kanal 1 einlesen
54
        
55
        // Bits 3 bis 5 stellen den Wert der Geschwindigkeit dar
56
        if (g_wert <= 128){
57
          geschwindigkeit = 0b00000000;
58
        } else if ((g_wert > 128) & (g_wert <= 256)){
59
          geschwindigkeit = 0b00001000;  
60
        } else if ((g_wert > 256) & (g_wert <= 384)){
61
          geschwindigkeit = 0b00010000;
62
        } else if ((g_wert > 384) & (g_wert <= 512)){ 
63
          geschwindigkeit = 0b00011000;
64
        } else if ((g_wert > 512) & (g_wert <= 640)){
65
          geschwindigkeit = 0b00100000;
66
        } else if ((g_wert > 640) & (g_wert <= 768)){
67
          geschwindigkeit = 0b00101000;
68
        } else if ((g_wert > 768) & (g_wert <= 896)){
69
          geschwindigkeit = 0b00110000;
70
        } else if ((g_wert > 896) & (g_wert <= 1024)){
71
          geschwindigkeit = 0b00111000;
72
        }
73
74
         return geschwindigkeit;
75
    }      
76
        
77
} app;  // Anwendungsinstanz

Teil2:
Dieser µC soll regelmäßig (alle 100ms, siehe Code) die Eingangszustände 
am PortD einlesen. Dies sind die Zustände, die vom anderen Controller 
erzeugt oder angelegt werden. Je nach Modus werden verschiedene 
Prozeduren abgearbeitet. Ändert sich die Geschwindigkeit, wird dies im 
jeweiligen Unterprogramm registriert. Ändert sich der Modus, wird das 
Unterprogramm verlassen und es wird im Hauptprogramm der aktuelle Modus 
abgefragt.
1
class Application : public Controller
2
{
3
    // Bausteine und Attribute .........................................
4
    protected: unsigned char modus;
5
    protected: unsigned int geschwindigkeit;
6
    
7
    // Funktionen ......................................................
8
    public: void onStart()
9
    {
10
        // Pin-Konfigurationen 
11
        ddrD.bit2=0;  //
12
        ddrD.bit3=0;  // Modus 
13
        ddrD.bit4=0;  //
14
        ddrD.bit5=0;    //
15
        ddrD.bit6=0;    // Geschwindigkeit 
16
        ddrD.bit7=0;    //
17
        
18
        ddrB.bit0=1; //
19
        ddrB.bit1=1; // Stufen
20
        ddrB.bit2=1; //
21
        ddrB.bit3=1; //
22
         
23
        modus_lesen(); // beim Start einmal den Modus
24
        geschw_lesen(); // und die Geschwindigk. einlesen
25
        
26
    }
27
    
28
    public: void onWork()
29
    {        
30
        switch (modus)  // Modus abfragen und entsprechende Muster ausgeben
31
        {
32
        case 0 : 
33
          portB = 0b00000000;  // alle Stufen aus
34
          break;
35
       case 1 :
36
          portB = 0b00001111; // alle Stufen an
37
          break;
38
       case 2 :
39
         lauflicht_voll(0); // 0 - nach unten
40
         break;
41
       case 3 :
42
         lauflicht_voll(1); // 1 - nach oben
43
         break;
44
       case 4 :
45
         blinken();  // blinken
46
         break;
47
       default :
48
         portB = 0b00000000;  // sonst alle aus
49
        }
50
        
51
    }
52
    
53
    void lauflicht_voll(char richtung)
54
    {
55
      if (richtung == 0){  // nach unten
56
        while (modus == 2){
57
                ...
58
                }
59
        if (richtung == 1){  // nach oben
60
        while (modus == 3){
61
                ...
62
                }
63
    }
64
    
65
    void blinken()
66
    {
67
      ...
68
    } 
69
    
70
    void modus_lesen()
71
    {
72
      if ((pinD.bit2 == 0) & (pinD.bit3 == 0) & (pinD.bit4 == 0)){ 
73
        modus = 0;
74
      } else if ((pinD.bit2 == 1) & (pinD.bit3 == 0) & (pinD.bit4 == 0)){
75
        modus = 1;
76
      } else if ((pinD.bit2 == 0) & (pinD.bit3 == 1) & (pinD.bit4 == 0)){
77
        modus = 2;
78
      } else if ((pinD.bit2 == 1) & (pinD.bit3 == 1) & (pinD.bit4 == 0)){
79
        modus = 3;
80
      } else if ((pinD.bit2 == 0) & (pinD.bit3 == 0) & (pinD.bit4 == 1)){
81
        modus = 4;
82
      }
83
    }  
84
    
85
    void geschw_lesen()
86
    {
87
      if ((pinD.bit5 == 0) & (pinD.bit6 == 0) & (pinD.bit7 == 0)){
88
        geschw = 1100;
89
      } else if ((pinD.bit5 == 1) & (pinD.bit6 == 0) & (pinD.bit7 == 0)){
90
        geschw = 950;
91
      } else if ((pinD.bit5 == 0) & (pinD.bit6 == 1) & (pinD.bit7 == 0)){
92
        geschw = 800;
93
      } else if ((pinD.bit5 == 1) & (pinD.bit6 == 1) & (pinD.bit7 == 0)){
94
        geschw = 650;
95
      } else if ((pinD.bit5 == 0) & (pinD.bit6 == 0) & (pinD.bit7 == 1)){
96
        geschw = 500;
97
      } else if ((pinD.bit5 == 1) & (pinD.bit6 == 0) & (pinD.bit7 == 1)){
98
        geschw = 350;
99
      } else if ((pinD.bit5 == 0) & (pinD.bit6 == 1) & (pinD.bit7 == 1)){
100
        geschw = 200;
101
      } else if ((pinD.bit5 == 1) & (pinD.bit6 == 1) & (pinD.bit7 == 1)){
102
        geschw = 50;
103
      }    
104
    }
105
    
106
    void onTimer100ms()  // regelmäßige Abfrage der Eingangswerte 
107
    {  
108
      modus_lesen();
109
      geschw_lesen();
110
    }
111
    
112
} app;  // Anwendungsinstanz

Falls es Fragen gibt, raus damit!

von Chris K. (ati13)


Lesenswert?

@ schweigstill

>Beide Programme (Ausgabe der "einsen" bzw. "nullen" auf der einen Seite,
>einlesen der "einsen" mit Hilfe von Tastern und Pull-Ups auf der
>anderen) hab ich natürlich bereits einzeln getestet. -> Fehler in den
>Programmen sind ausgeschlossen

Dass ich beide Programmteile bereits einzeln getestet habe, hatte ich 
schon erwähnt...das hast du vielleicht überlesen. Aber ist jetzt auch 
egal.

von Jonas B. (jibi)


Lesenswert?

> void geschw_lesen()
>    {
>      if ((pinD.bit5 == 0) & (pinD.bit6 == 0) & (pinD.bit7 == 0)){
>        geschw = 1100;
>      } else if ((pinD.bit5 == 1) & (pinD.bit6 == 0) & (pinD.bit7 == 0)){
>        geschw = 950;
>....

Muhaha. Was ein Murks......

von Karl H. (kbuchegg)


Lesenswert?

Chris K. schrieb:

Das ist doch dieses "Sisy" oder wie das heisst

>     void onTimer100ms()  // regelmäßige Abfrage der Eingangswerte
>     {
>       modus_lesen();
>       geschw_lesen();
>     }

Und der Timer läuft einfacgh so? Da muss nichts konfiguriert werden?

Zum Rest: Poah, eh. Selten so "komplizierten" Code gesehen, weil man den 
Zusammenhang zwischen Bits und den sich daraus ergebenden Zahlen nicht 
verstanden hat.

von Chris K. (ati13)


Lesenswert?

@ jibi

Ja, da gibt es sicher noch elegantere Lösungen, mir fiel spontan keine 
ein... ich möchte (darf) eben nicht den gesamten "PinD" abfragen, 
sondern will nur 3 bits prüfen.
Wie könnte man das machen?

von m-obi (Gast)


Lesenswert?

modus = (pinD >> 2) && 0x07;

von Jonas B. (jibi)


Lesenswert?

>Zum Rest: Poah, eh. Selten so "komplizierten" Code gesehen, weil man den
>Zusammenhang zwischen Bits und den sich daraus ergebenden Zahlen nicht
>verstanden hat.

Ne der macht kein Sinn:

Beispiel die Funktion "geschw_lesen"

Er moechte wohl in Abhängigkeit von den bits 5,6,7 die geschwindigkeit 
übermitteln. Statt die drei bits in ein byte zu schieben und das mit 150 
zu multiplizieren wäre wohl zu einfach.

Also diese bitorgie die auch noch fehler enthält:

000
100
010
110
001
101
011
111

Man o man...................

Gruß JOnas

: Bearbeitet durch User
von Karl H. (kbuchegg)


Lesenswert?

Das ist doch C++ Code in einer Umgebung verpackt.
Oder irre ich mich?

Denn in C++ ist das hier
1
      if ((pinD.bit2 == 0) & (pinD.bit3 == 0) & (pinD.bit4 == 0)){
an dieser Stelle nicht richtig.
Ein & ist ein binäres Und. Du willst hier aber ein logisches Und haben. 
Das schreibt sich aber als &&


Abgesehen davon. Kannst du denn nicht auf den Port als Ganzes zugreifen?

Der ganze Code hier
1
    void modus_lesen()
2
    {
3
      if ((pinD.bit2 == 0) & (pinD.bit3 == 0) & (pinD.bit4 == 0)){ 
4
        modus = 0;
5
      } else if ((pinD.bit2 == 1) & (pinD.bit3 == 0) & (pinD.bit4 == 0)){
6
        modus = 1;
7
      } else if ((pinD.bit2 == 0) & (pinD.bit3 == 1) & (pinD.bit4 == 0)){
8
        modus = 2;
9
      } else if ((pinD.bit2 == 1) & (pinD.bit3 == 1) & (pinD.bit4 == 0)){
10
        modus = 3;
11
      } else if ((pinD.bit2 == 0) & (pinD.bit3 == 0) & (pinD.bit4 == 1)){
12
        modus = 4;
13
      }
14
    }
reduziert sich dann zu
1
    void modus_lesen()
2
    {
3
      unsigned char mod = ( PIND >> 2 ) & 0x07;
4
      if( mod < 5 )
5
        modus = mod;
6
    }
(für PIND dann eben das Sprachmittel einsetzen, mit dem du auf den Port 
als ganzes zugreifen kannst)

und mit der Geschwindigkeit kann man ähnliches machen. Und beim Senden 
genau das gleiche, etc. etc.
Manchmal ist es nicht klug alles auf einzelne Bits an einem Port 
runterzubrechen. Das bläht den Code nur ungemein auf und wie man sieht 
steigt damit auch die Fehlerwahrscheinlichkeit. Manchmal ist es viel 
einfacher den Port als ganzes einzulesen und dann einfach gezielt die 
Bits, die man nicht haben will, auf 0 zu setzen oder ein wenig zurecht 
zu schieben, bis sie an den gewünschten Positionen sind.

soviel zum Thema
> Fehler in den Programmen sind ausgeschlossen

: Bearbeitet durch User
von C-Progger (Gast)


Lesenswert?

Chris K. schrieb:
> Dass ich beide Programmteile bereits einzeln getestet habe, hatte ich
> schon erwähnt...das hast du vielleicht überlesen. Aber ist jetzt auch
> egal.

Dann kannst Du froh sein, daß Dein Compiler Code erzeugt, der halbwegs 
funktioniert....:

Chris K. schrieb:
> void geschw_lesen()
>     {
>       if ((pinD.bit5 == 0) & (pinD.bit6 == 0) & (pinD.bit7 == 0)){
>         geschw = 1100;
>       } else if ((pinD.bit5 == 1) & (pinD.bit6 == 0) & (pinD.bit7 ==
> ......

Willst Du hier wirklich bitweise verunden ("=") oder Bedinungen abtesten 
("==")?
 Überleg es Dir, lies das C-Tutorial und schau Dir Deinen Code nochmal 
an....

von C-Progger (Gast)


Lesenswert?

m-obi schrieb:
> modus = (pinD >> 2) && 0x07;

... das ist keinen Deut besser :'(

von Jonas B. (jibi)


Lesenswert?

Im übrigen logische und binäre Operationen unterscheiden sich!

a & b ist nicht das gleiche wie a && b
Gruß Jonas

von Andreas S. (Firma: Schweigstill IT) (schweigstill) Benutzerseite


Lesenswert?

Chris K. schrieb:
> Dass ich beide Programmteile bereits einzeln getestet habe, hatte ich
> schon erwähnt...das hast du vielleicht überlesen. Aber ist jetzt auch
> egal.

Das habe ich selbstverständlich nicht überlesen. Die Aussage, bei Tests 
sei kein Fehler aufgetreten, ist nicht äquivalent zur Fehlerfreiheit des 
Programms. Um letzteres behaupten zu können, müsste der Beweis 
vorliegen, dass es sich um eine vollständige Testabdeckung handelt, was 
in den allermeisten Fällen nicht möglich sein dürfte.

von Helmut L. (helmi1)


Lesenswert?

Chris K. schrieb:
> ((pinD.bit2 == 1) & (pinD.bit3 == 0) & (pinD.bit4 == 0))

Die Unterschied zwischen binaeren & und logischen && kennst du?

Chris K. schrieb:
> Die Leitung zum anderen Controller beträgt
> übrigens ca. 15-20m.

Und du meinst das ist EMV technisch so in Ordnung?

Warum nimmst du nicht die Serielle Schnittstelle oder SPI des 
Controllers.
Und in deine Verbindung gehoeren Leitungstreiber und Empfaenger rein.

von m-obi (Gast)


Lesenswert?

C-Progger schrieb:
> m-obi schrieb:
>> modus = (pinD >> 2) && 0x07;
>
> ... das ist keinen Deut besser :'(

Sorry meinte natürlich &. Ist auf jedenfall ein Deut besser. Wenn noch 
das & statt dem && gewesen wäre, wären es sogar zwei Deut ;).

von Wolfgang (Gast)


Lesenswert?

Chris K. schrieb:
> Die Leitung zum anderen Controller beträgt
> übrigens ca. 15-20m.

Mal abgesehen vom Programmcode würde ich bei einer solchen Streckenlänge 
über was anderes als eine parallele Datenübertragung nachdenken. Wozu 
haben deine Controller einen U(S)ART oder ein SPI?

Als Einstiegsübung auf dem Hackbrett kann man das vielleich mal machen, 
aber sonst gibt es dafür eigentlich keine vernünftigen Gründe.
Und vergiss das Handshaking nicht, sonst sind Probleme mit undefinierten 
Zwischenzuständen vorprogrammiert.

von Chris K. (ati13)


Lesenswert?

@ jibi
>Also diese bitorgie die auch noch fehler enthält:
>000
>100
>010
>110
>001
>101
>011
>111

Wenn Bit 5 das LSB und Bit 7 das MSB darstellen, sollte es doch passen 
oder?
000
001
010
011
100
101
110
111

@ C-Progger
>... das ist keinen Deut besser :'(
Was dann?

Danke für die Eure Hinweise.

von Karl H. (kbuchegg)


Lesenswert?

Chris K. schrieb:

> Wenn Bit 5 das LSB und Bit 7 das MSB darstellen, sollte es doch passen
> oder?
> 000
> 001
> 010
> 011
> 100
> 101
> 110
> 111

Ja. Aber das geht viel einfacher.

Wieder:
den ganzen Port lesen. Das gelesene um 5 Bits nach rechts verschieben. 
Dann liegen die 3 inetressierenden Bits ganz unten im Byte. Mit einer 
Verundung mit 0x07 (binär: 00000111) alle nicht interessierenden Bits 
auf 0 setzen. Übrig bleibt eine Zahl von 0 bis 7. und wenn ich mir deine 
zu erzielenden Ergebniszahlen ansehe, dann folgen die dem Muster: 
Stufenzahl * 150 + 50

alles zusammen ergibt
1
   void geschw_lesen()
2
   {
3
     unsigned char stufe = ( PIND >> 5 ) & 0x07;
4
     geschw = stufe * 150  + 50;
5
   }

und jetzt vergleich mal mit dem Monster, das du geschrieben  hast und in 
dem du (natürlich) auch wieder alle logischen Und Operationen verbockt 
hast.

: Bearbeitet durch User
von Falk B. (falk)


Lesenswert?

@ Karl Heinz (kbuchegg) (Moderator)

>und jetzt vergleich mal mit dem Monster, das du geschrieben  hast.

BUHHHHHH, das ist ja Losercode im hornalten C. Richtig fett aufgedunsen 
muss es, sein ala C++ und Java . . . . 8-0

von Karl H. (kbuchegg)


Lesenswert?

Karl Heinz schrieb:

> und jetzt vergleich mal mit dem Monster, das du geschrieben  hast.

Fast. Noch nicht ganz.
Bei dir ist ja bei 7 die kleinste Stufe und bei 0 die größte.
Also muss man halt entweder
1
     geschw = ( 7 - stufe ) * 150  + 50;

oder aber man dreht einfach nach dem Einlesen gleich mal alle Bits um, 
so dass sich dann ebenfalls die Bedeutung umdreht.
1
     unsigned char stufe = ( ~PIND >> 5 ) & 0x07;

von Jonas B. (jibi)


Lesenswert?

void geschw_lesen()
{
  return ((pinD.bit5<<2) | (pinD.bit6<<1) | (pinD.bit7<<0))*150;
}


Gruß Jonas

von Chris K. (ati13)


Lesenswert?

Ich habe mit C++ angefangen, weil ich zu Anfang nur Java kannte. Für 
einfache "Anfängerbeispiele" haben diese Kenntnisse ausgereicht, zumal 
man sich dank SiSy nicht um h-Dateien oder sonstiges kümmern muss. ;-)
So langsam stoße ich da eben an grenzen...wie gut, das wir gerade das 
"gute alte C" behandeln ;-)

: Bearbeitet durch User
von Karl H. (kbuchegg)


Lesenswert?

Chris K. schrieb:

> So langsam stoße ich da eben an grenzen...wie gut, das wir gerade das
> "gute alte C" behandeln ;-)

Das hat mit C wenig zu tun.

Wenn du µC programmierst, dann ist eines deiner wichtigsten Werkzeuge 
die Beherrschung der Bitoperationen.
Die braucht man auf Desktop-Systemen eher selten, weil man da 
tatsächlich eher wenig mit einzelnen Bits rummacht. Aber auf einem µC 
ist das anders: Da sind die Bitoperationen dein Lebenselexier, weil sich 
80% der ganze Programmierung nur mit der Manipulation von einzelnen Bits 
bzw. Bitfolgen beschäftigt. Und da ist dann auch das Aufdröseln in 
einzelne Bits nicht mehr zielführend, weil es viel zu umständlichen Code 
erzeugt.

Das ist so, wie eine Exponentialfunktion oder ein Logarithmus für einen 
BWL Studenten nichts wirklich wichtiges ist, als Naturwissenschaftler 
muss man aber mit diesen Operationen umgehen können.

Bitmanipulation

: Bearbeitet durch User
von Jonas B. (jibi)


Lesenswert?

Achso rückwärts dann

test1 = 1050-(((bit5<<2) | (bit6<<1) | (bit7<<0))*150);

Gruss Jonas

von Falk B. (falk)


Lesenswert?

@ Karl Heinz (kbuchegg) (Moderator)

>Das ist so, wie eine Exponentialfunktion oder ein Logarithmus für einen
>BWL Studenten nichts wirklich wichtiges ist,

Irrtum, es ist die Grundlage der Religion "Kapitalismus". Zinseszins und 
ewiges Wachstum . . .

> als Naturwissenschaftler
>muss man aber mit diesen Operationen umgehen können.

Ok, die Naturwissenschaftler können damit umgehen und wissen, dass 
expontielles Wachstum nicht ewig währt . . .

von Jonas B. (jibi)


Lesenswert?

>000 = 0
>100 = 4
>010 = 2
>110 = 6
>001 = 1
>101 = 5
>011 = 3
>111 = 7

Merkst du was?

gruss  jonas

von Chris K. (ati13)


Lesenswert?

@ jibi

Lies es doch einfach rückwärts ;-)
Ich frage erst das LSB und als letztes das MSB ab.

von Karl H. (kbuchegg)


Lesenswert?

Falk Brunner schrieb:
> @ Karl Heinz (kbuchegg) (Moderator)
>
>>Das ist so, wie eine Exponentialfunktion oder ein Logarithmus für einen
>>BWL Studenten nichts wirklich wichtiges ist,
>
> Irrtum, es ist die Grundlage der Religion "Kapitalismus". Zinseszins und
> ewiges Wachstum . . .

Tja. Jetzt sag bloss das BWL-er das verstehen.
Banker, ja. Vielleicht. Solange es um die Zinsen geht, die sie kriegen.

von Karl H. (kbuchegg)


Lesenswert?

Jonas Biensack schrieb:
> Achso rückwärts dann
>
> test1 = 1050-(((bit5<<2) | (bit6<<1) | (bit7<<0))*150);

Ich versteh immer noch nicht, was du damit bezweckst, 3 Bits an dieselbe 
Position zu schieben, um dann das Ergebnis mit 150 zu multiplizieren.

von Jonas B. (jibi)


Lesenswert?

Warum an eine Stelle?

Ich schiebe bit5 an Stelle 2, bit5 an stelle1 und bit7 an stelle0.
Was meinst du?

gruß Jonas

von Jonas B. (jibi)


Lesenswert?

>@ jibi

>Lies es doch einfach rückwärts ;-)

Ok 7,3,5,1....

DU WILLST ABER

7,6,5,4,3,2,1

Echt mal.

Gruß Jonas

: Bearbeitet durch User
von C-Progger (Gast)


Lesenswert?

Jonas Biensack schrieb:
> Warum an eine Stelle?
>
> Ich schiebe bit5 an Stelle 2, bit5 an stelle1 und bit7 an stelle0.
> Was meinst du?
>
> gruß Jonas

Du schiebst:

Bit 5 2x nach links => Bit7
Bit 6 1x nach links => Bit7
Bit 7 0x nach links => Bit7


Also immer die gleiche Stelle... wo er Recht hat, hat er Recht

von Jonas B. (jibi)


Lesenswert?

Hm, jetzt weiss ich was du meinst, ich hatte es vorher so einmal 
getestet:
1
  bit5 = true;
2
  bit6 = false;
3
  bit7 = false;
4
5
  test1 = 1050-(((bit5<<2) | (bit6<<1) | (bit7<<0))*150);

Da ist das nicht aufgefallen. Sorry.

Gruß Jonas

von MiWi (Gast)


Lesenswert?

Chris K. schrieb:
> @ MiWi
>>Warum soll man sich hier also damit abgeben, auf solchen hingerotzten
>>Dreck auch noch inhaltlich einzugehen?
> (Zitat von schweigstill)
>
> Ich hab jetzt nach diversen Beiträgen, die sich inhaltlich sehr ähneln
> begriffen, dass ich mein Problem ausführlicher schildern soll.
> Aber solche besch...eidenen Beiträge (siehe Zitat) könnt ihr euch
> wirklich sparen! Ich wollte mein Anliegen doch einfach nur auf ein
> Minimum reduzieren. Anscheinend ist das so in Foren nicht üblich, weil
> man die Kenntnisse und Fähigkeiten der anderen nicht kennt.
> Gut. Das hab ich nun verstanden und poste die wichtigsten Details meines
> Projektes/Programmes:
>
> Zum Projekt allgemein:

Na also. Geht ja eh. Aber ohne diese Beiträge.....


Grüße & viel Erfolg

MiWi

von Chris K. (ati13)


Lesenswert?

@ jibi

Ich meine statt:
000
100
010
110
...

-> 000
   001
   010
   011
   ...
siehe:
1
if ((pinD.bit5 == 0) & (pinD.bit6 == 0) & (pinD.bit7 == 0))...

Ich lese sozusagen von rechts (LSB) nach links (MSB).

Aber dieses "Monster" werde ich ja jetzt beseitigen...

von Wolfgang (Gast)


Lesenswert?

Jonas Biensack schrieb:
> ich hatte es vorher so einmal getestet:
> ...
> Da ist das nicht aufgefallen.

Beweis durch Beispiel - oder wie nennt sich das?

Wie kommst du denn mit solchen Software-"Testmethoden" in Java klar. Das 
muss doch genauso schief gehen.

Andreas Schweigstill schrieb:
> solltest Du Dich erst einmal mehrere Jahre mit den Grundlagen der
> Testbarkeit von Software und Elektronik befasst haben.

Ack

von Jonas B. (jibi)


Lesenswert?

>Beweis durch Beispiel - oder wie nennt sich das?

>Wie kommst du denn mit solchen Software-"Testmethoden" in Java klar. Das
>muss doch genauso schief gehen.

Ich glaub du vermischst hier zwei Personen, keine Ahnung wie du mit so 
einer Wahrnehmung klar kommst ;)

Gruß Jonas

von Chris K. (ati13)


Lesenswert?

Also. Ich habe jetzt das "Monster" auf ein Minimum verkleinert. Guckst 
du hier:
1
void modus_lesen()
2
    {
3
      /*if ((pinD.bit2 == 0) & (pinD.bit3 == 0) & (pinD.bit4 == 0)){ 
4
        modus = 0;
5
      } else if ((pinD.bit2 == 1) & (pinD.bit3 == 0) & (pinD.bit4 == 0)){
6
        modus = 1;
7
      } else if ...*/
8
      
9
      modus = pinD & 0x07; // neue Variante
10
    }
bzw.
1
void geschw_lesen()
2
    {
3
      /*if ((pinD.bit5 == 0) & (pinD.bit6 == 0) & (pinD.bit7 == 0)){
4
        geschw = 1100;
5
      } else if ((pinD.bit5 == 1) & (pinD.bit6 == 0) & (pinD.bit7 == 0)){
6
        geschw = 950;
7
      } else if ...*/
8
      
9
      geschw = ((~pinD >> 3) & 0x07) * 150 + 50; // neue Variante 
10
    }
Sollte denk ich auch das bei rauskommen, was ich haben will.

Außerdem habe ich das Einleseprogramm verbessert, z.B.:
1
if ((moduswahl > 400) && (moduswahl <= 600)){
2
          portB = (0b00000010 + geschw_ermitteln());  // Lauftlicht nach unten
3
        }
(hatte vorher fälschlicher Weise das einfache, binäre UND verwendet)

Sonst habt ihr im Einleseprogramm keine weiteren Fehler entdecken 
können?

von m-obi (Gast)


Lesenswert?

Wenn du Bit 2, 3 und 4 willst musst du dann nicht mit 0x1C prüfen?

von Chris K. (ati13)


Lesenswert?

Ah na klar, danke!
1
void modus_lesen()
2
    {
3
      modus = pinD & 0x1C; // Bits 2-4 "einlesen"
4
    } 
5
 
6
    void geschw_lesen()
7
    {     
8
      geschw = (~pinD & 0xE0) * 150 + 50; // Bits 5-7 "einlesen"  
9
    }

So könnte es passen.

von Karl H. (kbuchegg)


Lesenswert?

Chris K. schrieb:
> Ah na klar, danke!
>
>
1
void modus_lesen()
2
>     {
3
>       modus = pinD & 0x1C; // Bits 2-4 "einlesen"
4
>     }
5
> 
6
>     void geschw_lesen()
7
>     {
8
>       geschw = (~pinD & 0xE0) * 150 + 50; // Bits 5-7 "einlesen"
9
>     }
>
> So könnte es passen.

Nein.
Denn wenn du an den Bits 2, 3 und 4 interessiert bist, dann musst du die 
auch gaaaanz nach unten schieben, damit sich da die von dir gewünschten 
Zahlen von 0 bis 7 ergeben.


Ist doch ganz simpel.
Du bist beispielsweise an diesen Bits hier interessiert und willst das 
ganze so haben, dass du diese Bits in ihrer Gesamtheit als Zahlen 
benutzen kannst.

Diese Bits a - d willst du ( 4 Stück Bits, daher Zahlen von 0 bis 15 )
1
 
2
     7   6   5   4   3   2   1   0
3
   +---+---+---+---+---+---+---+---+
4
   | x | x | d | c | b | a | x | x |
5
   +---+---+---+---+---+---+---+---+

Alle mit x markierten Bits sind für dich uninteressant.

Zuerst mal schiebst du den ganzen Wust um 2 Bits nach rechts. Warum 2 
Bits? Na weil das Bit a an der Bitposition 2 ist. Damit es ganz nach 
rechts rutscht, schiebst du es um 2 Bits
1
     value = value >> 2
1
 
2
     7   6   5   4   3   2   1   0
3
   +---+---+---+---+---+---+---+---+
4
   | 0 | 0 | x | x | d | c | b | a |
5
   +---+---+---+---+---+---+---+---+

Jetzt sind die 4 Bits ganz rechts. Aber links sind noch ein paar mit x 
markierte Bits, deren Wert du erstens nicht kennst und die dich zweitens 
auch nicht interessieren.
Also machst du eine binäre Und-Verknüpfung und wendest eine Maske an, 
die dir nur die 4 interessierenden Bits übrig lässt und alle andern Bits 
(selbst wenn sie schon auf 0 waren) gezielt auf 0 zwingt.
1
   value = value & 0x0F;
2
3
oder
4
5
   value = value & 0b00001111;
6
7
oder
8
9
   value = value & ( (1 << PB0) | (1 << PB1) | (1 << PB2) | (1<<PB3) );
10
11
oder
12
13
   value = value & ~( (1<<PB7) | (1<<PB6) | (1<<PB5) | (1<<PB4) );

Alle Varianten sind nur unterschiedliche Schreibweisen für dasselbe: 
Eine Bitmaske, in der an den interessierenden Bits ein 1-Bit steht und 
alle andern Bits 0 sind. Die 0 Bits erzwingen, dass im Ergebnis getreu 
der Und-Verknüpfung für Bits
1
UND
2
3
   a    b     Ergebnis
4
  ---------------------
5
   0    0        0
6
   1    0        0
7
   0    1        0
8
   1    1        1
9
10
(b ist quasi das jeweilige Bit aus der 'Maske', während a dem Bit in value entspricht)
in jedem Fall eine 0 auftaucht (Kontrolliere: In der Und-Tabelle sind 
alle Ergebnis Zeilen tatsächlich 0, in denen auch in der b-Spalte eine 0 
steht. Wohingegen in den Zeilen, in denen b auf 1 steht, das Ergebnis 
identisch mit der jeweiligen a Spalte ist.)

Die Operation ist dann
1
 
2
           7   6   5   4   3   2   1   0
3
         +---+---+---+---+---+---+---+---+
4
         | 0 | 0 | x | x | d | c | b | a |
5
         +---+---+---+---+---+---+---+---+
6
7
UND
8
         +---+---+---+---+---+---+---+---+
9
         | 0 | 0 | 0 | 0 | 1 | 1 | 1 | 1 |
10
         +---+---+---+---+---+---+---+---+
11
12
---------------------------------------------
13
14
         +---+---+---+---+---+---+---+---+
15
         | 0 | 0 | 0 | 0 | d | c | b | a |
16
         +---+---+---+---+---+---+---+---+
17
18
      auf jede Spalte einzeln die Und-Verknüpfung anwenden!
19
      Genau das ist es, was die binäre Und-Verknüpfung in C++ (bzw. C)
20
      macht! binäre Und Verknüpfung schreibt sich als &
21
      Im Gegensatz zur logischen Und Verknüpfung, die sich als && schreibt.

Das Eregbnis ist also ein Byte, in dem deine interessierenden Bits ganz 
rechts stehen und unversehrt übernommen wurden, während alle anderen 
Bits definitiv auf 0 sind.

Und getreu
1
     Bits    Hex Dezimal        Bits   Hex Dezimal
2
     0000     0     0           1000    8    8
3
     0001     1     1           1001    9    9
4
     0010     2     2           1010    A   10
5
     0011     3     3           1011    B   11
6
     0100     4     4           1100    C   12
7
     0101     5     5           1101    D   13
8
     0110     6     6           1110    E   14
9
     0111     7     7           1111    F   15

steht jede der Bitkombinationen für eine Zahl. In dem Fall, mit 4 Bits, 
dann eben für Zahlen von 0 bis 15.
Genau das, was wir wollten. Denn mit den Zahlen wollen wir ja 
weiterrechnen bzw. etwas damit machen.


Du musst natürlich nicht um 2 Bits schieben. Nur kommen dann eben nicht 
Zahlen von 0 bis 15 raus, sondern andere. Das kann  manchmal sinnvoll 
sein, wenn man aber an den Zahlen als solche explizit interessiert ist, 
dann ist es meist einfacher, die Schiebe-Operation zu machen. Wir tun 
uns eben mit der Zahlenfolge 0, 1, 2, 3, 4, ... 15 leichter, als mit der 
Zahlenfolge 0, 4, 8, ... 60. Vor allen Dingen dann, wenn dann damit noch 
gerechnet werden soll.

: Bearbeitet durch User
von Chris K. (ati13)


Lesenswert?

Vielen dank kbuchegg für die sehr ausführliche Nachhilfe!
So ausführlich wäre sie eigentlich nicht notwendig gewesen...
Mein Problem ist, dass ich zu flüchtig über die Problemstellungen 
nachdenke, um möglichst schnell ein Ergebnis zu bekommen oder zu sehen.

Also hier nochmal die überarbeitete Variante:
1
void modus_lesen()
2
    {
3
      modus = (pinD >> 2) & 0x07;
4
    }  
5
    
6
    void geschw_lesen()
7
    {
8
      geschw = (~(pinD >> 5) & 0x07) * 150 + 50;  
9
    }

von Chris K. (ati13)


Lesenswert?

Noch eine kleine Frage.
Für mein Projekt benötige ich ja 2 µC. bis jetzt habe ich immer das 
"myAVR Board MK2" für Übungszwecke verwendendet. Darauf befindet sich 
bereits ein ATmega8. Einen weiteren Atmega8 habe ich aber nicht zur 
Hand, sondern nur einen ATmega32 (war im Einsteigerset mit enthalten). 
Ich habe jetzt zum Testen des neuen Controllers zunächst die 
Grundschaltung (Minimalbeschaltung) aufgebaut, danach einen Taster und 
LED's angeschlossen und ein simples Programm draufgeladen welches die 
LED's bei Betätigen eines Tasters aufleuchten lässt. Und es 
passiert...nichts. Reicht die Minimalbeschaltung auf dem Bild 
tatsächlich aus? Habe z.B. keinen entsprechenden Kondensator zur Hand. 
Aber ich möchte ja auch nur kurz die Funktion testen, mehr nicht. Gibt 
es noch etwas zu beachten, wenn einen neuen µC zum ersten mal 
programmiert oder in Betrieb nimmt?

von Chris K. (ati13)


Angehängte Dateien:

Lesenswert?

(Bild)

von Karl H. (kbuchegg)


Lesenswert?

Chris K. schrieb:

> passiert...nichts. Reicht die Minimalbeschaltung auf dem Bild
> tatsächlich aus?

An Avcc/AGND sollte noch ein 100nF Kondensator ran.

> Habe z.B. keinen entsprechenden Kondensator zur Hand.

Das ist schlecht.

Aber: Es kann auch ohne Kondensator funktionieren. Sicherer ist mit.

> Aber ich möchte ja auch nur kurz die Funktion testen, mehr nicht. Gibt
> es noch etwas zu beachten, wenn einen neuen µC zum ersten mal
> programmiert oder in Betrieb nimmt?

Nein.

Ausser das du schon wieder zu kompliziert loslegst.
Du musst erst noch lernen, dass das Arbeiten in kleinen SChritten nur 
auf den ersten Blick langsamer aussieht. Es wird noch einige Zeit 
dauern, bis du sweit bist, dass deine Schritte größer werden können.

Ein erstes Testprogramm ist: EINE Led an einem Portpin. Die schaltet man 
ein. Im nächsten Testprogramm schaltet man sie aus (auch wenn das 
paradox klingt. Es geht darum festzustellen, ob die leuchtende LED im 
erste Testprogramm auch wirklich deswegen geleuchtet hat, weil man im 
Programm eingeschaltet hat). Dann vielleicht mal blinken. Dann 
vielleicht 8 Led an den Portpins und die gemeinsam blinken lassen (damit 
stellt man zb fest: ob der sprunghafte Anstieg im Stromverbrauch 
irgendwelche negativen Effekte in der Spannungsversorung hat). Und erst 
dann kommt erstmalig ein Taster ins Spiel.

> So ausführlich wäre sie eigentlich nicht notwendig gewesen...

Macht nix. Wenn ich mir den Krampf ansehe, mit dem du losgestartet bist, 
hab ich schon den Eindruck, du kannst noch gar nicht abschätzen, wieviel 
Mehrarbeit du dir da überall gemacht hast und immer noch machst.

> Mein Problem ist, dass ich zu flüchtig über die Problemstellungen
> nachdenke, um möglichst schnell ein Ergebnis zu bekommen oder zu sehen.

Tja. Computer sind da gnadenlos. Da musst du sorgfältiger werden.
Das bedeutet auch, in kleineren Schritten zu arbeiten. Mit der einfachst 
möglichen Problemstellung anfangen (so wie bei den LED und dem Taster) 
und dich dann in kleinen SChritten vorarbeiten, wobei jeder SChritt 
getestet wird. Denn sonst wird es immer so weiter gehen, dass du mit 
einem komplexen Produkt dasteht, nichts funktioniert und du hast keine 
Ahnung, wo du mit Fehlersuche anfangen sollst oder du hast noch nicht 
mal den Hauch einer Idee, was da nicht stimmen könnte.
Wie gesagt: Auf lange Sicht bist du mit schrittweisem Vorgehen immer 
schneller, als wie wenn du gleich zu viel willst.

von Chris K. (ati13)


Lesenswert?

Gut. Dass ich kleinschrittiger und sorgfältiger arbeiten muss, werde ich 
jetzt beherzigen.
Ich habe mit Absicht nicht nur eine, sondern 6 LED's angeschlossen, um 
zu prüfen, ob der (gesamte) Port für die geplante Übertragung der Bits 
fehlerfrei funktioniert. Den Taster hätte ich dabei allerdings weglassen 
können. Im übrigen leuchten die LED's nun, war natürlich wieder mal ein 
Flüchtigkeitsfehler...

Ich habe jetzt außerdem herausgefunden, weshalb der ATmega32 mit dem 
Programm zum Einlesen der Werte über die ADC-Kanäle nicht funktioniert 
hat. Beim Anlegen eines neuen "kleinen Programmes" (SiSy) öffnet sich 
ein Fenster für diverse Einstellungen. Dort muss man bereits den 
benutzten Controllertyp auswählen. Mit diesen Einstellungen wird das 
Programm dann wahrscheinlich kompiliert. Nach dem Kompilieren hat man 
aber ebenfalls die Möglichkeit, den Controllertyp einzustellen (was ich 
bisher getan hatte). Ich hab also ein Programm für einen Mega8 
gescchrieben auf einen Mega32 geladen (warum so etwas überhaupt möglich 
ist, ist mir unklar). Das nächste Problem ist, dass das Paket mit den 
vorgefertigten Klassen, welches ich benutze, nicht mit dem Mega32 
kompatibel ist (laut Compiler).
Da ich ein wenig unter Zeitdruck stehe, werde ich mir wohl einen zweiten 
Mega8 besorgen - den ich ja sowieso dafür vorgesehen hatte - anstatt das 
Programm (wahrscheinlich wieder zu schnell, zu hektisch und vor allem 
falsch) umzuschreiben...

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.