#c #pic #microchip
#c #рис #микрочип
Вопрос:
Я новичок в Microchip PIC uC. У меня есть некоторый опыт работы с AVR, но несколько недель назад я решил узнать о PICs.
Проблема заключается в следующем. Я пытаюсь выполнить свою первую программу с 2 мигающими светодиодами, это очень просто. RA1 и RA2 мигают.
Когда я набираю код 1 и код 2, программа работает отлично. Код 1: работает нормально.
//Code 1. OK.
main(){
while(1){
__delay_ms(1000); //wait 1 second
PORTA |= 0b00000110; //RA1 amp; RA2 on
__delay_ms(1000); //wait 1 second
PORTA amp;= 0b00000000; //RA1 amp; RA2 off
}
}
Код 2: работает нормально.
//Code 2. OK
main(){
while(1){
__delay_ms(1000); //wait 1 second
PORTA |= (1 << 1) | (1 << 2); //RA1 amp; RA2 on
__delay_ms(1000); //wait 1 second
PORTA amp;= ~(1 << 1) amp; ~(1 << 2); //RA1 amp; RA2 off
}
}
Код 3: этот код не работает. Только 1 светодиодная вспышка. Я использую это с AVR, и код работает отлично. В чем проблема? ИЛИ операция не должна влиять на работу RA1.
//Code 3. Don't work. Only RA2 flash.
main(){
while(1){
__delay_ms(1000); //wait 1 second
PORTA |= (1 << 1); //RA1 on
PORTA |= (1 << 2); //RA2 on
__delay_ms(1000); //wait 1 second
PORTA amp;= ~(1 << 1); //RA1 off
PORTA amp;= ~(1 << 2); //RA2 off
}
}
Большое вам спасибо за вашу помощь.
С наилучшими пожеланиями
Ответ №1:
Регистры ввода-вывода PIC используют чтение-изменение-запись. В некоторых случаях это может привести к повторному считыванию напряжения с выводов вместо логического значения, которое вы ожидаете в своей программе. Это особенно верно, если выходной вывод имеет некоторую емкость, которая заставляет его изменять значение медленнее, чем то, что последовательность инструкций предписывает ему делать с выводом.
В вашем случае третий случай пытается очень быстро изменить контакты на порту последовательно. Это может привести к тому, что второе значение будет фиксировать фактическое напряжение на выходе вместо того, что вы предполагали в своем коде.
В таких случаях необходимо использовать переменную для затенения регистра PORTA:
main(){
unsigned char output = 0;
while(1){
__delay_ms(1000); //wait 1 second
output |= (1 << 1); //RA1 on
PORTA = output;
output |= (1 << 2); //RA2 on
PORTA = output;
__delay_ms(1000); //wait 1 second
output amp;= ~(1 << 1); //RA1 off
PORTA = output;
output amp;= ~(1 << 2); //RA2 off
PORTA = output;
}
}
Комментарии:
1. Многие PIC также имеют выходные регистры блокировки, которые лучше подходят для управления выходами, поскольку они содержат только те значения, которые вы записываете в них. ИНАЧЕ. LATA против PORTA
2. Спасибо за ответ, оба решения сработали для меня. В AVR регистр PORTX не имеет проблем такого типа.
3. @JuanLuis На любом микроконтроллере, кроме PIC, это не проблема. Я понятия не имею, почему люди используют PIC в новых проектах.
Ответ №2:
Всегда записывайте в порты LATx (выходные защелки) и считывайте из PORTx.
Запись в PORTx неизменно вызывает головную боль.
Комментарии:
1. Большое вам спасибо! Я сделаю это!