Hallo Leute,
bisher kann ich ein einziges Mob versckicken und auch empfangen. Nun
will ich zwei Mobs versckicken und empfangen nur es klappt irgendwie
nicht. Die CAN Initialisierung in main sieht so aus:
1
//CAN-Initialisierung
2
CANBT1=0x08;
3
CANBT2=0x0C;
4
CANBT3=0x37;
5
CANGIE|=(1<<ENIT)|(1<<ENTX);
6
CANIE2|=(1<<IEMOB0)|(1<<IEMOB1);
7
CANPAGE=0x08;//Auto Increment off
8
CANIDT1=0x55;
9
CANIDT2=0x00;
10
CANIDT3=0x00;
11
CANIDT4=0x00;
12
CANSTMOB=0x00;
13
CANCDMOB=0x48;
14
CANGCON|=(1<<ENASTB);
15
sei();
In der while(1) Schleife des Senders mache ich prinzipiell folgendes.
1
if((Eingabe!=Eingabe_old)&&(!My_CAN_Flag))//if new input and message sent
2
{
3
My_CAN_Flag=0x01;//trying to send
4
for(inti=0;i<8;i++)//Mob0
5
{
6
CANPAGE=8+i;
7
CANMSG=latitude[i];
8
}
9
for(inti=0;i<3;i++)//Mob1
10
{
11
CANPAGE=40+i;
12
CANMSG=latitude[i+8];
13
}
14
15
CANSTMOB=0x00;//Status reset
16
CANCDMOB=0x48;//enable transmission, set 11bit identifier, send 8 bytes
17
}
Die Init beim Empfänger sieht so aus:
1
//CAN-Init
2
CANBT1=0x08;
3
CANBT2=0x0C;
4
CANBT3=0x37;
5
CANGIE|=(1<<ENIT)|(1<<ENRX);
6
CANIE2|=(1<<IEMOB0)|(1<<IEMOB1);
7
CANPAGE=0x08;//Mob0, auto increment off, Byte0
8
CANIDT1=0x55;
9
CANIDT2=0x00;
10
CANIDT3=0x00;
11
CANIDT4=0x00;
12
CANIDM1=0xFF;
13
CANIDM2=0xE0;
14
CANIDM3=0x00;
15
CANIDM4=0x05;
16
CANSTMOB=0x00;
17
CANCDMOB=0x88;
18
CANGCON|=(1<<ENASTB);
19
sei();
Und die Empfangsroutine in der while(1) so:
1
if(My_Interrupt_Flag)
2
{
3
4
for(inti=0;i<8;i++)
5
{
6
CANPAGE=8+i;
7
latitude[i]=CANMSG;
8
}
9
for(inti=0;i<3;i++)
10
{
11
CANPAGE=40+i;
12
latitude[i+8]=CANMSG;
13
}
14
CANSTMOB=0x00;
15
CANCDMOB=0x88;//enable receiver, receive 8 bytes
16
My_Interrupt_Flag=0;
17
18
}
Wenn ich beim Sender
1
for(inti=0;i<3;i++)//Mob1
2
{
3
CANPAGE=40+i;
4
CANMSG=latitude[i+8];
5
}
weglasse und beim Empfänger
1
for(inti=0;i<3;i++)
2
{
3
CANPAGE=40+i;
4
latitude[i+8]=CANMSG;
5
}
weglasse und jeweils in CANIE2 nur den Mob0 Interrupt freischalte, also
quasi nur Mob0 benutze kann ich prima senden und empfangen. Warum gehts
mit Mob0 und Mob1 nicht?
Vielen Dank schon mal im Voraus!
Gruß
Franz
Danke tex für deine Antwort. Wenn ich die einzelnen Mobs aktiviere kann
ich nun auch beide Empfangen. Nun habe ich erweitert auf insgesamt 4
Mobs und kann aber nur die ersten zwei emfpangen (Interrupt für mob2 und
mob3 wird nich aufgerufen). Ich habe jetzt die Verarbeitung allerdings
in die ISR ausgelagert was aber nichts ausmachen dürfte da es mit nur 2
mobs ja funktioniert. Wäre super wenn mal jemand grob über den etwas
länglichen code schauen könnte warum ich nur die ersten zwei mobs
empfangen kann.
Vielen Dank
Franz
Sender init:
Nun nochmal ne allgemeinere Frage. Wie seht ihr welches Mob die ISR
aufgerufen hat? Anscheinend kann werden nur Interrupts für Mob0 und Mob1
aufgerufen was wahrscheinlich daran liegt, dass Mob0 und Mob1 von der
Priorität her höher sind und deswegen Mob2 und 3 nicht zum zuge kommen
können. Wenn ich wüsste ob mob0 oder 1 den Interrupt aufgerufen hat
könnte ich die beiden ja solange sperren bis mob 2 und 3 abgearbeitet
wurden. Mit der Abfrage auf CANHPMOB hauts nicht hin und es zeigt bei
jedem ISR Aufruf 0x00 an.
Vielen Dank
Franz
Da mußt Du dazu jedes mal CANSIT1 und/ oder CANSIT2 bemühen.
Weil das Auswerten dieser Register seine Zeit braucht, habe ich mich von
diesem Chip verabschiedet, weil jeder Zugriff stets über Register
abgewickelt wird.
Habe ich jetzt versucht mit CANSIT2 nur ist das Problem dass wenn ich in
die ISR springe zeigt mit CANSIT2 an dass meistens alle 4 Interrupts auf
einmal gekommen sind oder bestens mal dass Interrupt von Mob0 und 1
gemeinsam gekommen sind. Also was kann ich machen damit nur jeweils ein
Interrupt aufgerufen wird?
Tja, willkommen in der Interruptprogrammierung des 90CANxxx.
CAN Enable Interrupt MOb Registers - CANIE2 and CANIE1
hier schaltest Du nur die MOBs frei, die reagieren sollen.
Eigentlich ganz einfach.
Aber wenn man das Datasheet sich das erste Mal zu Gemüte führt raucht
der Kopf.
Es hilft nichts -> dran bleiben.
Viel Erfolg
Auf den letzten Seiten des Datenblattes findest Du die Zeiten, die die
einzelnen Prozesse in Anspruch nehmen. Es ist ausgesprochen
unschicklich, sein Programm mit hunderten von IRSs zu traktieren, ohne
sich zuvor Gedanken darüber gemacht zu haben, was eine ISR eigentlich im
Prozessor und den Registern bewirkt. Da Du vermutlich genau so
rücksichtslos mit den übrigen ISRs umgesprungen bist, wie mit den hier
dargestellten ISRs würde ich behaupten, dass Dein Problem nicht an dem
Befehl oder der Zeile liegt, sondern schlicht in der Struktur Deines
Programms zu suchen ist.
Vermutlich läuft Deine komplette Datums- und Uhrzeitberechnung ebenso in
einer ISR wie die UART- Verarbeitung usw.
Die ISR entbindet nicht von der Verpflichtung, über eine geordnete
Programmstruktur nachdenken zu müssen, die setzt diese voraus.
Schau Dir nur mal diese beiden Monstren an die Du hier als ISR gepostet
hast und überlege Dir mal, wie lange Dein Prozessor damit beschäftigt
ist, diese abzuarbeiten.
ISRs sollte man nach Möglichkeit vermeiden und wirklich nur für
zeitkritische Anwendungen verwenden.
Hast Du irgend wo in Deinem Programm, Z.B. für das Display noch
Warteschleifen? ... Und warum muss der Prozessor da sinnlos rumsitzen
und Däumchen drehen, statt mal eben die UART und CAN-Register
abzufragen, die Uhrzeit und den Kalender berechnen oder was sonst noch
so sinnloses zu tun ist? Klar, dann kann man ihn ja nicht via IRS aus
seiner Arbeit reißen, wenn er wirklich was zu tun hat.
Vielen Dank Leute mittlerweile hab dich die Sache zum laufen gebracht.
Ich hab auch die Verarbeitung wieder ins Hauptprogramm geholt und frage
ein CAN Interrupt Flag ab. Erkennen welches Mob gerade an der Reihe ist
mache ich über CANHPMOB. Nach der Abarbeitung eines Mobs schalte ich das
CANIE dieses Mobs aus und die anderen je nach Priorität an. Ein
Ringpuffer also sozusagen. Damit dürte ich nun auch in der Lage sein
alle 14 Mobs zu versenden/empfangen falls benötigt.
Gruß Franz
Hey Franz,
meinste Du könntest mir mal Dein Programm posten??
Da mein Programm nicht in die ISR sprinen möchte..............ich
verzweifle noch!!!
Sendest Du die Daten über TXCAN???