*EDIT*
Problem löst, körde med epilog(); det blev en ok lösning.
*/EDIT*
Hmm egentligen borde kanske detta vara en ny tråd... jaja här kommer frågan iaf!
Jag har 3 st Task:
Task1: kollar om det kommer tangenttryckning, beroende på vilken tangent
som blev nedtryckt så skickas ett meddelande till Task2.
Task2: Beroende på vilket meddelande som kommer så skrivs det tecknet
ut på displayen, samt skickar acknowledge till Task1.
Task3: Rinnande ljus på PortB.
Problemet som jag har är att såfort jag trycker på en knapp så skrivs det tecknet ut OCH även nästa tecken... trycker jag sedan på en knapp igen så blir allt galet. varför? jag vill ju kunna skriva ut ett tecken igen.
antar att felet ligger i task2´s if/else röra.. tänkte ha en else efter alla andra if/else, men vad ska det stå där? inte avrXhalt(); iallafall!
hela programmet följer nedan.
Kod: Markera allt
/*
KOPPLA IN SÅHÄR:
PORTA->NR2
PORTB->NR5
PORTC->NR1
PORTD->NR3
*/
#include <c:/avrx/avrx/avrx-io.h>
#include <c:/avrx/avrx/avrx-signal.h>
#include "c:/avrx/avrx/Avrx.h"
#include "hardware.h"
#define timerdelay 70000
#define timerdelay1 550
void set_rs(void);
void write_dd_ram(void);
void e_rsclock(void);
void eclock(void);
void delay(void);
void cleardisplay(void);
void disp(char*, int);
char nb1[1]="1";
char nb2[1]="2";
char nb3[1]="3";
char nb4[1]="4";
char nb5[1]="5";
char nb6[1]="6";
char nb7[1]="7";
char nb8[1]="8";
char nb9[1]="9";
char nb0[1]="0";
char nbA[1]="A";
char nbB[1]="B";
char nbC[1]="C";
char nbD[1]="D";
char nbStar[1]="*";
char nbBrackets[1]="#";
TimerControlBlock Timer1,Timer2,Timer3; // Create a control blocks for a timer
MessageControlBlock no1,no2,no3,no4,no5,no6,no7,no8,no9,no0,noA,noB,noC,noD,noStar,noBrackets; // Create simple messages (no internal data)
MessageQueue Queue1; // Create a message queue
/*
Timer 0 Overflow Interrupt Handler
Prototypical Interrupt handler:
. Switch to kernel context
. handle interrupt
. switch back to interrupted context.
*/
AVRX_SIGINT(SIG_OVERFLOW0)
{
IntProlog(); // Switch to kernel stack/context
outp(TCNT0_INIT, TCNT0); // Reset timer overflow count
AvrXTimerHandler(); // Call Time queue manager
Epilog(); // Return to tasks
}
//Skapa 3 task. Rinnande ljus, rinnande ljus, och 1 till.
AVRX_GCC_TASK(task1, 40, 3); // Create three tasks with 70 bytes stacksize and priority 3
AVRX_GCC_TASK(task2, 50, 3);
AVRX_GCC_TASK(task3, 30, 1);
//*****TASK1*****
NAKEDFUNC(task1) // Task 1
{
while(1)
{
int temp=0,temp1=0;
temp=inp(PINC);
temp1=temp&16;
if(temp1==16)
{
PORTC=PORTC&223; //Output enable går LÅG.
AvrXDelay(&Timer1,1); //Vänta 1ms.
temp=inp(PINC); //Lägg PINC till temp, dvs tangenpositionen i temp.
PORTC=PORTC|32; //Output enable går HÖG.
switch(temp){
case 3 : AvrXSendMessage(&Queue1, &no1); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no1); //Vänta på kvitto
case 2 : AvrXSendMessage(&Queue1, &no2); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no2); //Vänta på kvitto
case 1 : AvrXSendMessage(&Queue1, &no3); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no3); //Vänta på kvitto
case 0 : AvrXSendMessage(&Queue1, &noA); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&noA); //Vänta på kvitto
case 7 : AvrXSendMessage(&Queue1, &no4); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no4); //Vänta på kvitto
case 6 : AvrXSendMessage(&Queue1, &no5); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no5); //Vänta på kvitto
case 5 : AvrXSendMessage(&Queue1, &no6); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no6); //Vänta på kvitto
case 4 : AvrXSendMessage(&Queue1, &noB); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&noB); //Vänta på kvitto
case 11: AvrXSendMessage(&Queue1, &no7); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no7); //Vänta på kvitto
case 10: AvrXSendMessage(&Queue1, &no8); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no8); //Vänta på kvitto
case 9 : AvrXSendMessage(&Queue1, &no9); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no9); //Vänta på kvitto
case 8 : AvrXSendMessage(&Queue1, &noC); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&noC); //Vänta på kvitto
case 15: AvrXSendMessage(&Queue1, &noStar); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&noStar); //Vänta på kvitto
case 14: AvrXSendMessage(&Queue1, &no0); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&no0); //Vänta på kvitto
case 13: AvrXSendMessage(&Queue1, &noBrackets); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&noBrackets); //Vänta på kvitto
case 12: AvrXSendMessage(&Queue1, &noD); // Skicka Meddelande till kö1
AvrXWaitMessageAck(&noD); //Vänta på kvitto
}
}
}
}
//Task2, kollar efter och fixar med meddelanden.
NAKEDFUNC(task2)
{
MessageControlBlock *p; // Create a pointer to a MessageControlBlock
int pelle=0;
while (1)
{
p=AvrXWaitMessage(&Queue1); // Wait for new message @ Queue1
if(p==&no1)
{
disp(nb1, 1);
AvrXAckMessage(p);
}
else
if (p==&no2)
{
disp(nb2, 1);
AvrXAckMessage(p);
}
else
if (p==&no3)
{
disp(nb3, 1);
AvrXAckMessage(p);
}
else
if (p==&no4)
{
disp(nb4, 1);
AvrXAckMessage(p);
}
else
if (p==&no5)
{
disp(nb5, 1);
AvrXAckMessage(p);
}
else
if (p==&no6)
{
disp(nb6, 1);
AvrXAckMessage(p);
}
else
if (p==&no7)
{
disp(nb7, 1);
AvrXAckMessage(p);
}
else
if (p==&no8)
{
disp(nb8, 1);
AvrXAckMessage(p);
}
else
if (p==&no9)
{
disp(nb9, 1);
AvrXAckMessage(p);
}
else
if (p==&no0)
{
disp(nb0, 1);
AvrXAckMessage(p);
}
else
if (p==&noStar)
{
disp(nbStar, 1);
AvrXAckMessage(p);
}
else
if (p==&noBrackets)
{
disp(nbBrackets, 1);
AvrXAckMessage(p);
}
else
if (p==&noA)
{
disp(nbA, 1);
AvrXAckMessage(p);
}
else
if (p==&noB)
{
disp(nbB, 1);
AvrXAckMessage(p);
}
else
if (p==&noC)
{
disp(nbC, 1);
AvrXAckMessage(p);
}
else
if (p==&noD)
{
disp(nbD, 1);
AvrXAckMessage(p);
}
}
}
//******TASK3******
NAKEDFUNC(task3)
{
while(1){
int dcount=1;
outp(dcount, PORTB);
do
{
dcount=dcount<<1;
AvrXDelay(&Timer3,250); //Vänta 1ms.
//PORTB=dcount;
outp(dcount, PORTB);
AvrXDelay(&Timer2,250); //Vänta 1ms.
}while(dcount<=127);
dcount=1;
}
}
void main(void) // Main runs under the AvrX Stack
{
AvrXSetKernelStack(0); // Set kernel stack to current SPL/SPH
//outp((1<<SE), MCUCR); // Enable "Sleep" instruction
outp(TCNT0_INIT, TCNT0);
outp(TMC8_CK256, TCCR0); // Set up Timer0 for CLK/256 rate
outp((1<<TOIE0), TIMSK); // Enable Timer0 overflow interrupt
DDRC=0x20;
PORTC=PORTC|20;
DDRA=255;
DDRD=255;
outp(0xFF, DDRB); // Make PORT B output and...
// outp(0xFF, PORTB); // LEDs on
PORTA=56;
eclock();
PORTA=15;
eclock();
PORTA=6;
eclock();
cleardisplay();
AvrXRunTask(TCB(task3));
AvrXRunTask(TCB(task1)); // Start task1
AvrXRunTask(TCB(task2)); // Start task2
Epilog(); // Switch from AvrX Stack to first task
return(0);
}
//*****Delay*****
void delay()
{
long i; // Declare a variable
for(i=0;i<=timerdelay;i=i+1) // Do nothing for "timerdelay" times
{}
}
//***************
//*****E_Clock*****
//Klockar ut Instruktioner
void eclock()
{
PORTD=4;
delay();
PORTD=0;
}
//***************
//*****RS_Clock*****
//Klockar ut tecken
void e_rsclock()
{
PORTD=5;
delay();
PORTD=0;
}
//******************
//*****Write_dd_ram*****
//Stoppar efter 8 tecken
void write_dd_ram()
{
PORTA=192;
eclock();
}
//**********************
//*****write RS R/W och E*****
void set_rs()
{
delay();
PORTD=4;
delay();
PORTD=0;
delay();
}
//****************************
//*****Rensa Displayen*****
void cleardisplay()
{
PORTA=1;
eclock();
delay();
PORTA='L';
e_rsclock();
delay();
PORTA='a';
e_rsclock();
delay();
PORTA='s';
e_rsclock();
delay();
PORTA='t';
e_rsclock();
delay();
PORTA=':';
e_rsclock();
delay();
PORTA=' ';
e_rsclock();
delay();
}
//*************************
//**********Display funktion******
void disp(char *string, int x)
{
int c;
int i;
c=0;
x=x-1;
do {
PORTA=string[c];
e_rsclock();
if (c==7) //Byter "rad" på displayen om det behövs.
{
write_dd_ram();
PORTA=string[c];
}
c=c+1;
}
while(c<=x);
}