Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: Прошу помощи в написании первой программы
Форум разработчиков электроники ELECTRONIX.ru > Сайт и форум > В помощь начинающему > MCS51, AVR, PIC, STM8, 8bit
AlxX
Здравствуйте. Я начинаю изучать програмирование под МК и у меня не получается корректно написать первую программу.
МК, используемый мною, ATmega8535. Из обвязки 2 светодиода на порту A на нулевом и первом соответственно. Схема стаблилизации питания на 78L05. Два светодиода подключены катодом к МК, анодом к одному и тому же резистору на 1 килоом. Вся эта конструкция запитана от кроны.

Пишу программу:

#include <mega8535.h>
#include <delay.h>

void main(void){
PORTA=0x00;
DDRA=0xFF;
while(1){
PORTA.0=1;
PORTA.1=0;
delay_ms(500);
PORTA.0=1;
PORTA.1=0;
//PORTA.1=1;
delay_ms(700);
}//while
}//main

В результате мигают оба светодиода, как будто я написал PORTA = 1(PORTA=0);
Подскажите как быть?
kovigor
Цитата(AlxX @ Aug 18 2012, 06:38) *
В результате мигают оба светодиода, как будто я написал PORTA = 1(PORTA=0);
Подскажите как быть?

В приведенном вами фрагменте ошибка: светодиоды никак не могут мигать. Ну и аноды нужно к разным резисторам подключить ...
zombi
Цитата(AlxX @ Aug 18 2012, 06:38) *
Два светодиода подключены катодом к МК, анодом к одному и тому же резистору на 1 килоом.

Куда подключён второй вывод резистора? или аноды соединены через резистор???

Нарисуйте схему, напишите как должны мигать светодиоды.

Цитата(AlxX @ Aug 18 2012, 06:38) *
Код
void main(void){
PORTA=0x00;
DDRA=0xFF;
    while(1){
        PORTA.0=1;
    PORTA.1=0;
        delay_ms(500);
        PORTA.0=1;
    PORTA.1=0;
        //PORTA.1=1;
        delay_ms(700);
    }//while
}//main

В результате мигают оба светодиода


Судя по программе состояние ног порта А вообще не меняется, как может что то мигать?

AlxX
Цитата(zombi @ Aug 18 2012, 19:47) *
Куда подключён второй вывод резистора? или аноды соединены через резистор???

Нарисуйте схему, напишите как должны мигать светодиоды.



Судя по программе состояние ног порта А вообще не меняется, как может что то мигать?


Схема подключения (78L05 убрана).
программа действительно не рабочая, я ошибся, когда добавлял код в 1 пост:
Код
#include <mega8535.h>
#include <delay.h>

void main(void){
PORTA=0x00;
DDRA=0xFF;
    while(1){
        PORTA.0=1;
        PORTA.1=0;
        delay_ms(500);
        PORTA.0=0;
        PORTA.1=1;
        delay_ms(700);
    }//while
}//main
mempfis_
Цитата(AlxX @ Aug 19 2012, 19:04) *
Код
#include <mega8535.h>
#include <delay.h>

void main(void){
PORTA=0x00;
DDRA=0xFF;
    while(1){
        PORTA.0=1;
        PORTA.1=0;
        delay_ms(500);
        PORTA.0=0;
        PORTA.1=1;
        delay_ms(700);
    }//while
}//main


А Вы на ножках тестером посмотрите - дергаются ли PORTA.0 & PORTA.1
И фус-биты проверьте - особенно постоянное включение wdt (если он есть в 8535). На какой частоте работает процессор, правильно ли она указана в проекте. Так в коде ошибок не наблюдается. Может не работать если постоянно ресетится изза сторожевого таймера или косяков в подключении светодиодов.
Ruslan1
Цитата(AlxX @ Aug 18 2012, 06:38) *
Два светодиода подключены катодом к МК, анодом к одному и тому же резистору на 1 килоом.

Я всегда говорил, что только те, кто застал ламповую технику, никогда не путают анод и катод. Потому как если хоть раз в жизни довелось ткнуть пальцем в анодное напряжение - то на всю жизнь запомниться, что анод это ПЛЮС (ну да, сейчас этот плюс уже можно маленькими буквами писать, он маленький, но все же плюс sm.gif
Семин
Сторона диода которая похожа на букву К - есть КАТОД.
Диод открывается, проводит ток, а светодиод при этом ещё
и светится, когда на него подаётся минус.
zombi
to AlxX
AlxX
Цитата(zombi @ Aug 20 2012, 12:20) *
to AlxX


Абсолютно верно - у меня наоборот светодиоды подключены (+ - выход мк, - - через резистор на GND ).

Сторожевой таймер в настройках проекта отключен. В настройках указана частота 1 мегагерц, доп. кварцев не подключено. Сигнал на обеих ногах появляется одновременно (на всех остальных сигнала нет).
Xenia
Думаю, что надо разориться и купить ... еще один резистор на 1 ком sm.gif. Как только светодиоды разведут по отдельным резисторам, всё само наладится. А сейчас, скорее всего, по отдельности они горят, а вместе гаснут (резко ослабляют свое свечение) из-за увеличения падения напряжения на единственном сопротивлении.
Alexashka
Скорей всего у Вас сопля между ногами wink.gif
ЗЫ. т.е не у Вас, а у процессора.
_Ivana
Чем сидеть в онлайне на форуме и ждать подсказок, лучше давно бы уже сами попробовали поморгать ногами в противофазе, оторвать светодиоды и посмотреть напряжение на выводах, просто выставить противофазные напряжения без моргания... Дел на 5 минут, баг ловится сразу.
AlxX
В общем проблема решена. Я как человек привыкший верить конструкторам и заставший еще живые радиодетали СССР по старой памяти спаял "широкую" ногу к выводу МК, а "узкую" через сопротивление на землю. Но китайская промышленность, как оказалось, думает иначе! У них на красных светодиодах так и есть, а на желтых и зеленых с точностью до наоборот! В общем перепаял светодиоды и добавил сопротивление и все работает на ура. Всем огромное спасибо.
Ruslan1
Цитата(AlxX @ Aug 22 2012, 08:27) *
Я как человек привыкший верить конструкторам и заставший еще живые радиодетали СССР

Как человек, повидавший настолько многое, могли бы по крайней мере разобраться и правильно описать причину неработоспособности. Так как Вы последовательно утверждали:
1) светодиоды мигают одновременно
2) светодиоды припаяны анодом к земле

Одно из этих утверждений явно ложное.

На будущее: попробуйте корректно и правильно описать проблему. Часто хорошо поставленный вопрос не нуждается в ответе. Задающий, прочитав такой вопрос, сам находит ответ sm.gif
esaulenka
Цитата
"широкую" ногу к выводу МК, а "узкую" через сопротивление на землю.
...
на красных светодиодах так и есть, а на желтых и зеленых с точностью до наоборот!


Нарисуйте, пожалуйста, схему, как такая конструкция в принципе работает. С указанием направления токов и значениями напряжений в каждой точке. Ну хоть примерно, умозрительно.

UPDATE. Пардон, сообразил. Если самому додумать, что один светодиод зелёный ("неправильный"), второй красный, то логика какая-то прослеживается. Я с чего-то решил, что они одинаковые.
AlxX
Цитата(Ruslan1 @ Aug 22 2012, 09:39) *
Как человек, повидавший настолько многое, могли бы по крайней мере разобраться и правильно описать причину неработоспособности. Так как Вы последовательно утверждали:
1) светодиоды мигают одновременно
2) светодиоды припаяны анодом к земле

Одно из этих утверждений явно ложное.

На будущее: попробуйте корректно и правильно описать проблему. Часто хорошо поставленный вопрос не нуждается в ответе. Задающий, прочитав такой вопрос, сам находит ответ sm.gif


Я не многое видел. У меня отец инженер КИПиА, поэтому данного железа времен союза у нас дома было много. Я никогда не учился работать с электроникой (я программист по образованию и работаю по нему же), поэтому познания мои весьма скудные, и мк меня заинтересовали со стороны программирования. А теперь в свои 25 я еще пытаюсь изучить правила построения схем-обвязок к мк.
Plain
Хороший программист в первую очередь хорошо себе комментирует, и если бы Вы, как Вам говорят, отписали бы здесь, с самого начала, простым и понятным русским языком, всё то, что в действительности сделали, а именно "я подпаял, не глядя ни в какие бумаги, и не проверяя никакими приборами, первые попавшиеся мне красный и зелёный светодиоды неизвестной марки тольстенькими ножками к выводам МК, а тоненькими к резистору 1 кОм на общий провод", то — ещё раз, как Вам и сказали то, что Вы сейчас процитировали — Вы бы сами увидели ответ на свой вопрос.
ilglbv
Доброго времени суток!
Даже стыдно как то спрашивать) Но все же..
Пытаюсь поиграться с регистом PIN, вроде все варианты перепробывал, но не получается(((

#include <avr/io.h>
#include <util/delay.h>
int main (void)
{ DDRC = 01111111;
PORTC = 10000000;
while (1){
if (PINC0 == 0)
{PORTB |= (1<<5); // включаем
_delay_ms(550); // ждём
PORTB &= ~(1<<5); // выключаем
_delay_ms(550); // ждём
}

}
}

В двоичном пишу потому что стал думать может в хексе запутался((
Please, Help!
Avr Studio 6, Proteus 7.7
_Артём_
Цитата(ilglbv @ Aug 26 2012, 23:21) *
Пытаюсь поиграться с регистом PIN, вроде все варианты перепробывал, но не получается(((

Не помешало бы указать тип МК: так как у разных типов разные возможности для "игр" с PINx.
У mega8/16/../128 PINx - только для чтения состояния порта, а у mega48/88../328 - PINx может быть использован для инвертирования выхода.

Цитата(ilglbv @ Aug 26 2012, 23:21) *
DDRC = 01111111;
PORTC = 10000000;
while (1){
if (PINC0 == 0)
{PORTB |= (1<<5);

В двоичном пишу потому что стал думать может в хексе запутался((

DDRC = 01111111; - настройка порта С на выход?
Тогда PORTB |= (1<<5) зачем? Подключить подтягивающие резисторы в порте B?
DDRB = 0xFF; было бы логичней.
И вообще кстати непонятна цель вашей программы- вывести на PB5 "1" если на PC0 - высокий уровень? Или что-то другое?

Цитата(ilglbv @ Aug 26 2012, 23:21) *
if (PINC0 == 0)

PINC0 это вот что:
#define PINC0 0
то есть ваш код
if (0 == 0)
.
Лучше так:
Код
if ((PINC&(1<<0))==0) { // если PC0 == 0
//....
}



Цитата(ilglbv @ Aug 26 2012, 23:21) *
В двоичном пишу потому что стал думать может в хексе запутался((

Кому как, в bin проще запутаться - букв много, в hex-е меньше.

zombi
Цитата(ilglbv @ Aug 26 2012, 23:21) *
PORTC = 10000000;

Пишем в PORTC десять лямов?! и что компилятор не ругается?

Цитата
2.2. Константы


Имеется несколько видов констант, которые перечислены
ниже.

2.2.1. Целые константы


Целая константа, состоящая из последовательности цифр,
считается восьмеричной, если она начинается с 0 (цифра
нуль), и десятичной в противном случае. Цифры 8 и 9 имеют
восьмеричные значения 10 и 11 соответственно. Последова-
тельность цифр, которой предшествуют символы 0х (нуль, х-
маленькое) или 0х (нуль X-большое), рассматривается как
шестнадцатиричное целое. Шестнадцатиричные цифры включают
буквы от a (маленькое) или A (большое) до f (маленькое) или
F (большое) со значениями от 10 до 15. Десятичная константа,
величина которой превышает наибольшее машинное целое со зна-
ком, считается длинной; восьмеричная или шестнадцатиричная
константа, которая превышает наибольшее машинное целое без
знака, также считается длинной.
_Артём_
Цитата(zombi @ Aug 27 2012, 00:09) *
Пишем в PORTC десять лямов?!

наверное имелось в виде PORTC=0b1000000; или как там этот бин пишется...
Цитата(zombi @ Aug 27 2012, 00:09) *
и что компилятор не ругается?

А должен?
Варнинг выпишет и не более...
_Артём_
Цитата(zombi @ Aug 27 2012, 00:09) *
Пишем в PORTC десять лямов?!

наверное имелось в виде PORTC=0b1000000; или как там этот бин пишется...
Цитата(zombi @ Aug 27 2012, 00:09) *
и что компилятор не ругается?

А должен?
Варнинг выпишет и не более...
zombi
Цитата(_Артём_ @ Aug 27 2012, 00:21) *
наверное имелось в виде PORTC=0b1000000; или как там этот бин пишется...

Дык, вроде в СИ вообще нет двоичной формы записи числа.
_Артём_
Цитата(zombi @ Aug 27 2012, 00:28) *
Дык, вроде в СИ вообще нет двоичной формы записи числа.

В Си нету, а в AVRGCC есть: не знаю точно как и зачем сделали, наверное что-то вроде такого:
Код
#define b00000001 1
#define b00000010 2

Бессмысленная штука.
ilglbv
Поторопился... "проектик" на Mega8, суть его в том, что при нажатии на кнопку (pc0) должен запуститься цикл (pb5).
Попробую сейчас сделать запись PINX вашего вида
_Артём_
. стёрто
форум глючит - сообщения по 2 раза пишутся...
ilglbv
Вот, поправил и все заработало)
#include <avr/io.h>
#include <util/delay.h>
int main (void)
{ DDRC |=(0<<0); <- смущает меня эта запись, но компилятор не возмущается... все работает
PORTC |=(1<<0);
while (1){
if ((PINC&(1<<0))==0)
{PORTB |= (1<<5); // включаем
_delay_ms(550); // ждём
PORTB &= ~(1<<5); // выключаем
_delay_ms(550); // ждём
}

}
}
По поводу описания портов, номеров битов идут слева направо или наоборот (DDRX=0123..7 или DDRX=765..10)?
Насчет хекса, вы постоянно пересчитываете или же наизусть знаете?
_Артём_
Цитата(ilglbv @ Aug 27 2012, 00:35) *
DDRC |=(0<<0); <- смущает меня эта запись, но компилятор не возмущается... все работает

А что ему возмущатся?
DDRC |=(0<<0); тоже самое, что
DDRC|=0;
то есть порт DDRC не изменится в результате.
Компилятор не должен возмушаться на такое - может так надо.
Он только должен сгенерить код который прочитает DDRC, сделать ИЛИ с заданным числом и результат записать в DDRC.
Если нужно переключить PC0 на вход нужно написать так:
Код
DDRC&=~(1<<0);


Цитата(ilglbv @ Aug 27 2012, 00:35) *
По поводу описания портов, номеров битов идут слева направо или наоборот (DDRX=0123..7 или DDRX=765..10)?

Вопрос какой-то некорректный...
Допустим
DDRC=1; установка в 1 бита 0
DDRC=2; установка в 1 бита 1
...
DDRC=1<<7; установка в 1 бита 7

Цитата(ilglbv @ Aug 27 2012, 00:35) *
Насчет хекса, вы постоянно пересчитываете или же наизусть знаете?

Ну, тетраду в hex представить что она есть в бин не сложно, байт в hex тоже можно - в этих пределах можно сказать наизусть.
А вот таблицу умножения в hex не знаю, наверное оно не надо.
А в bin-записи много букв и труднее представить что там 0 что один - глаза разбегаются...

PS
Код
PORTB |= (1<<5); // включаем
_delay_ms(550); // ждём
PORTB &= ~(1<<5); // выключаем
_delay_ms(550); // ждём

PB5 может нужно на выход включить?
DDRB|=(1<<5);
или включения pullup резистора достаточно?
ilglbv
Цитата(_Артём_ @ Aug 27 2012, 02:09) *
А что ему возмущатся?
DDRC |=(0<<0); тоже самое, что
DDRC|=0;
то есть порт DDRC не изменится в результате.
Компилятор не должен возмушаться на такое - может так надо.
Он только должен сгенерить код который прочитает DDRC, сделать ИЛИ с заданным числом и результат записать в DDRC.
Если нужно переключить PC0 на вход нужно написать так:
Код
DDRC&=~(1<<0);



Вопрос какой-то некорректный...
Допустим
DDRC=1; установка в 1 бита 0
DDRC=2; установка в 1 бита 1
...
DDRC=1<<7; установка в 1 бита 7


Ну, тетраду в hex представить что она есть в бин не сложно, байт в hex тоже можно - в этих пределах можно сказать наизусть.
А вот таблицу умножения в hex не знаю, наверное оно не надо.
А в bin-записи много букв и труднее представить что там 0 что один - глаза разбегаются...

PS
Код
PORTB |= (1<<5); // включаем
_delay_ms(550); // ждём
PORTB &= ~(1<<5); // выключаем
_delay_ms(550); // ждём

PB5 может нужно на выход включить?
DDRB|=(1<<5);
или включения pullup резистора достаточно?


Видимо достаточно... ведь все работает) (avr studio 6)
PS спасибо Артему за PINC&(1<<0))==0
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.