Помогите с кодом на C
|
|
| Вс, 05.07.2015, 20:38 | Сообщение # 1
|
adamchuk2012
Постов: 14
ОК |
Всем привет. Делаю первое устройство на атмеге 8 сижу верстаю код. вот в чём затык. есть две ножки опрашивемых при выполнении цикла. одна должна запускать другая останавливать (прерывать даже если не закончен цикл) вот код /* parostruika */
#define F_CPU 1000000 #include <avr/io.h> #include <util/delay.h> void preset (){ DDRB = 0xFF; PORTB = 0x00; DDRC = 0x00; PORTC = 0xFF; }
int main(void) { preset() ; {PORTB = 0b00000001; //влючаю нагрев while(PC0==0) // пока на датчике верхнего уровня нет воды if (PINC&(1<<PC1)) // если на датчике нижнего нет воды то ( pinc0- датчик верхнего уровня, pinc1-датчик нижнего уровня) { PORTB = 0b00000010 ;// выключаю нагрев, пищу 10 сек _delay_ms(10000) ; PORTB = 0b00000100;// прекратил пищать включил сброс пара _delay_ms(10000); PORTB = 0b00001100;// сбрасываю пар и заправляюсь одновременно _delay_ms(10000000);} else PORTB = 0b00000001; // включаю нагрев }
}
|
|
| Вс, 05.07.2015, 21:09 | Сообщение # 2
|
Витинари
Постов: 1503
Друзья |
adamchuk2012, в программировании в целом опыт есть? У контроллеров имеются некоторые тонкости. 1. Зачем настройки портов выведены в отдельную функцию preset()? 2. Главная функция есть, но где основной цикл while(1)? Именно он заставляет программу выполняться снова и снова, а не стопориться после первого раза. int main(void) { preset() ; {PORTB = 0b00000001; //влючаю нагрев откуда здесь взялась фигурная скобка, если ей ничего не предшествует? ПО-видимому, это и есть рудиментный остаток от бесследно пропавшего цикла.
while(PC0==0) // пока на датчике верхнего уровня нет воды ... после оператора цикла нет фигурных скобок.
Вообще, не стоит забывать про фигурные скобки. Даже если по логике их можно смело опустить, лучше не пренебрегать ими. Компиляторы - штука тонкая, и ничто не мешает их разработчикам порадовать программистов очередным маразмом с собственными стандартами Си, придуманными по велению задней левой пятки. И тогда может оказаться, что эти самые пропущенные скобки сыграют злую шутку при сборке или оптимизации кода. На пиках, в частности, неоднократно сталкивался с таким - явный говнокод с элементами индусского программирования может работать лучше, чем красивый и правильный (а все потому, что нерегулируемая оптимизация все равно перекроит его во славу Шеогората).
Попробуй так: Код #define F_CPU 1000000 #include <avr/io.h> #include <util/delay.h>
int main(void) { DDRB = 0xFF; PORTB = 0x00; DDRC = 0x00; PORTC = 0xFF; while(1) { PORTB = 0b00000001; //влючаю нагрев if(!PC0) // лучше избегать цикла в цикле; пока на датчике верхнего уровня нет воды { if (PINC&(1<<PC1)) // если на датчике нижнего нет воды то ( pinc0- датчик верхнего уровня, pinc1-датчик нижнего уровня) { PORTB = 0b00000010 ;// выключаю нагрев, пищу 10 сек _delay_ms(10000) ; PORTB = 0b00000100;// прекратил пищать включил сброс пара _delay_ms(10000); PORTB = 0b00001100;// сбрасываю пар и заправляюсь одновременно _delay_ms(10000000); } else{PORTB = 0b00000001;} // включаю нагрев } } }
|
|
| Вс, 05.07.2015, 21:43 | Сообщение # 3
|
adamchuk2012
Постов: 14
ОК |
тоже не работает как надо. цикл прерывается когда нижний датчик в воде. а нужно верхним останавливать. Программист я начинающий. поэтому и косячу. но научиться охота большая
|
|
| Вс, 05.07.2015, 21:49 | Сообщение # 4
|
msmmmm2
Постов: 166
ОК |
Цитата Витинари ( ) нерегулируемая оптимизация все равно перекроит его во славу Шеогората А как же volatile? И оптимизация с указанной переменной по барабану. Проверял, сравнивал код ассемблера с "volatile" и без. На PIC-ах.
|
|
| Вс, 05.07.2015, 21:57 | Сообщение # 5
|
adamchuk2012
Постов: 14
ОК |
msmmmm, что вы имели в виду?
|
|
| Вс, 05.07.2015, 22:17 | Сообщение # 6
|
msmmmm2
Постов: 166
ОК |
Это к Витинари, но, если интересно... Компилятор очень сложно, многоступенчато и витиевато делает свою работу - превращает текст на С в машинный код, при чем так, как ему кажется эффективно. Например, если раз 5 подряд написать присвоение одного и того же числа переменной, в машинном коде (даю 99%) будет одно присвоение, что мы можем увидеть, проанализировав листинг дизассемблирования. Если раз 20 подряд линейно опросить порт, компилятор организует цикл, а нам нужен именно очень быстрый опрос. В циклах меняются местами проверка условия и тело (с умом, программа работает нормально), вследствие чего имеем работающую программу, но, например, разное время выполнения первого и последующих проходов цикла, что может быть важно в очень скоростных программах. Везде в таких случаях нужно перед объявлением переменной ставить ключевое слово volatile, которое указывает компилятору, что все, что касается данной переменной нужно компилировать "как есть", не оптимизируя.Добавлено (05.07.2015, 23:17) --------------------------------------------- А вообще, если заморачиваться оптимизацией, лучше писать на ассемблере, там программист царь, а не премьер-министр (тоже начальство, но могут и послать ).
|
|
| Вс, 05.07.2015, 22:21 | Сообщение # 7
|
adamchuk2012
Постов: 14
ОК |
msmmmm, а с кодом мне помочь разобраться могёте? я вам тож как нить помогу...
|
|
| Вс, 05.07.2015, 22:27 | Сообщение # 8
|
msmmmm2
Постов: 166
ОК |
Если поклонники атмел не отзовутся - помогу. Но, я больше по пикам выступаю . С - почти тот же, но архитектура разная. Иногда играюсь...
|
|
| Вс, 05.07.2015, 22:34 | Сообщение # 9
|
adamchuk2012
Постов: 14
ОК |
не отзываются.пока. а времени маловато. штуковина нужная должна получиться.
|
|
| Вс, 05.07.2015, 22:50 | Сообщение # 10
|
Витинари
Постов: 1503
Друзья |
msmmmm, а вот с условиями, особенно если ветвлений много, оптимизатор такое может накрутить, что мало не покажется. И я уже писал как-то, что CCS вытворяет с оператором "/" - около 400 байт на одно только деление! Для 628a это аж 20% памяти. Та же функция, написанная вручную, занимает всего 40 Б.
adamchuk2012, на пике оно бы проще вышло. И дешевле в разы - какой-нить 629-й преспокойно справился бы с такой задачей.
|
|