РАДИОСХЕМЫ



СТАРЫЙ ФОРУМ

ФОРУМ НА ЭЛВО

РАДИОФОРУМЫ


СХЕМЫ И СТАТЬИ
  • БЛОГИ
  • НОВОЕ
  • СХЕМЫ
  • РАЗНОЕ
  • ТЕОРИЯ
  • ТЕЛЕВИДЕО
  • СВЕТОДИОД
  • МЕДТЕХНИКА
  • БЫТТЕХНИКА
  • ИЗМЕРИТЕЛИ
  • СПРАВОЧНИК
  • ТЕХНОЛОГИИ
  • РЕМОНТ СХЕМ
  • МОБИЛЬНИКИ
  • КОМПЬЮТЕРЫ
  • НАЧИНАЮЩИМ
  • ЗАРЯДКИ И АКБ
  • СИГНАЛИЗАЦИИ
  • АУДИОТЕХНИКА
  • АВТОВЕЛОМОТО
  • БЛОКИ ПИТАНИЯ
  • РАДИОПРИЁМНИКИ
  • МЕТАЛЛОИСКАТЕЛИ
  • МИКРОКОНТРОЛЛЕР
  • РАДИОПЕРЕДАТЧИКИ

  • Курс по ускорению работы Мозга на 100%


    • Страница 1 из 2
    • 1
    • 2
    • »
    Архив - только для чтения
    Форум радиолюбителей » СХЕМЫ » МИКРОСХЕМЫ » Помогите с кодом на C
    Помогите с кодом на 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)
    ---------------------------------------------
    А вообще, если заморачиваться оптимизацией, лучше писать на ассемблере, там программист царь, а не премьер-министр (тоже начальство, но могут и послать biggrin ).

    Вс, 05.07.2015, 22:21 | Сообщение # 7        
    adamchuk2012
    аватар
      Постов: 14   ОК 
    msmmmm, а с кодом мне помочь разобраться могёте?
    я вам тож как нить помогу...
    Вс, 05.07.2015, 22:27 | Сообщение # 8        
    msmmmm2
    аватар
      Постов: 166   ОК 
    Если поклонники атмел не отзовутся - помогу. Но, я больше по пикам выступаю biggrin .
    С - почти тот же, но архитектура разная. Иногда играюсь...
    Вс, 05.07.2015, 22:34 | Сообщение # 9        
    adamchuk2012
    аватар
      Постов: 14   ОК 
    не отзываются.пока.
    а времени маловато. штуковина нужная должна получиться.
    Вс, 05.07.2015, 22:50 | Сообщение # 10        
    Витинари
    аватар
      Постов: 1503   Друзья 
    msmmmm, а вот с условиями, особенно если ветвлений много, оптимизатор такое может накрутить, что мало не покажется.
    И я уже писал как-то, что CCS вытворяет с оператором "/" - около 400 байт на одно только деление! Для 628a это аж 20% памяти. Та же функция, написанная вручную, занимает всего 40 Б.

    adamchuk2012, на пике оно бы проще вышло. И дешевле в разы - какой-нить 629-й преспокойно справился бы с такой задачей.
    Форум радиолюбителей » СХЕМЫ » МИКРОСХЕМЫ » Помогите с кодом на C
    • Страница 1 из 2
    • 1
    • 2
    • »
    Поиск:

    Внимание! Форум переехал на Tehnodium.ru



    © 2010-2022 "Форум Радиосхемы". All Rights Reserved  Почта  PDA