Перейти к содержанию

Помогите с инкрементом в операторе ветвления


Юстас

Рекомендуемые сообщения

Переменная для обратного отсчета нужна? Где она будет инициализироваться, где изменяться и где проверяться?

Ругался на отсутствие форматирования исходного кода (включая отсутствие осмысленных комментариев и наличие неубранного после конфигуратора мусора) не менее 15 раз.

Часть моих наработок.

Ссылка на комментарий
Поделиться на другие сайты

Реклама: ООО ТД Промэлектроника, ИНН: 6659197470, Тел: 8 (800) 1000-321

9 часов назад, Григорий Т. сказал:

А зачем ещё один флаг? Достаточно выставить длительность импульса в t_imp_count.

можно и так как вы предлагаете, но флаг это один бит и не зависит от размера переменной t_imp_count, а она похоже может стать двухбайтной. Не стоит оптимизировать на стадии написания кода (напоминает spectrum, кто быстрее закрасит экран).

Надо двигаться дальше в написании программы, а мы продолжаем тянуть в разные стороны, может тогда каждый будет реализовывать свой вариант (и что не странно у всех будет работать, не зависимо от количества файлов в проекте и количества флагов). Пусть ТС получит работающий проект, потом хоть заоптимизируется, хоть по скорости, хоть по объёму. Хотя при таких ресурсах микроконтроллера это уже может стать лишним (на данном уровне знаний), так для самосовершенствования на будущее.

Ссылка на комментарий
Поделиться на другие сайты

20% скидка на весь каталог электронных компонентов в ТМ Электроникс!

Акция "Лето ближе - цены ниже", успей сделать выгодные покупки!

Плюс весь апрель действует скидка 10% по промокоду APREL24 + 15% кэшбэк и бесплатная доставка!

Перейти на страницу акции

Реклама: ООО ТМ ЭЛЕКТРОНИКС, ИНН: 7806548420, info@tmelectronics.ru, +7(812)4094849

Заполнение переменной обратного отсчета это одно действие (для однобайтной переменной 1 такт, для двухбайтной - 4 такта), взведение флага - тоже одно действие. Но использование флага требует дополнительные действия - в основном, проверки флага в процессе отсчета и синхронизация с вводом и выводом.

Ругался на отсутствие форматирования исходного кода (включая отсутствие осмысленных комментариев и наличие неубранного после конфигуратора мусора) не менее 15 раз.

Часть моих наработок.

Ссылка на комментарий
Поделиться на другие сайты

Выбираем схему BMS для корректной работы литий-железофосфатных (LiFePO4) аккумуляторов

 Обязательным условием долгой и стабильной работы Li-FePO4-аккумуляторов, в том числе и производства EVE Energy, является применение специализированных BMS-микросхем. Литий-железофосфатные АКБ отличаются такими характеристиками, как высокая многократность циклов заряда-разряда, безопасность, возможность быстрой зарядки, устойчивость к буферному режиму работы и приемлемая стоимость. Но для этих АКБ, также как и для других, очень важен контроль процесса заряда и разряда, а специализированных микросхем для этого вида аккумуляторов не так много. Инженеры КОМПЭЛ подготовили список имеющихся микросхем и возможных решений от разных производителей. Подробнее>>

Реклама: АО КОМПЭЛ, ИНН: 7713005406, ОГРН: 1027700032161

 

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

Я так думаю...

Никогда не спорьте с дураком - люди могут не заметить между вами разницы

Ссылка на комментарий
Поделиться на другие сайты

46 минут назад, COKPOWEHEU сказал:

Заполнение переменной обратного отсчета это одно действие (для однобайтной переменной 1 такт, для двухбайтной - 4 такта), взведение флага - тоже одно действие. Но использование флага требует дополнительные действия - в основном, проверки флага в процессе отсчета и синхронизация с вводом и выводом

я не собираюсь дискутировать, где и сколько мы сэкономим

как я уже писал - эту задачу каждый решит по своему и по своему будет прав. Я не сколько не сомневаюсь, что вы в состоянии написать данный код (красивый, быстрый, компактный...)

32 минуты назад, Григорий Т. сказал:

Не нужно усложнять и унифицировать

и усложнять я не пытаюсь,

я хочу увидеть реализацию Юстасом чего-нибудь, понять где он не понял и двигаться дальше...

Изменено пользователем dm37
Ссылка на комментарий
Поделиться на другие сайты

Привет всем) Я только с работы пришёл. Не успеваем сдать заказ во время. 
 

Дело в том, как бы я не старался начать с простого и двигаться к сложному, мои алгоритмы неизбежно натыкаются на обработку кнопок. Я думаю, может ввести один регистр ощего назначения специально для флагов? В нём поместится 8 флагов это даже больше чем нужно. А в перерывании постоянно их контролить, обрабатывать данные и reti.... В основной программе уже всё остальное.
 

Ссылка на комментарий
Поделиться на другие сайты

Всем остальным для своих версий импульса кнопки не требуются.

С флагами тоже самое - сначала определитесь зачем они нужны.

Сейчас вам предложено два родственных варианта генерации импульса - со стартом по записи значения в переменную обратного отсчета и со стартом по флагу.

Ругался на отсутствие форматирования исходного кода (включая отсутствие осмысленных комментариев и наличие неубранного после конфигуратора мусора) не менее 15 раз.

Часть моих наработок.

Ссылка на комментарий
Поделиться на другие сайты

@COKPOWEHEU  Сечас займусь кодом. Попробую написать функцию генерации импульса  - со стартом по записи значения в переменную обратного отсчета. Мне это больше по душе.
 

Ссылка на комментарий
Поделиться на другие сайты

Это лучшее, из всех моих вариантов)

Скрытый текст

; Частота кварца 16 МГц
.include "m8def.inc" 
.def temp = r16
.def vremya_impulsa = r17
.def temp_key = r18
.def flag = r19
.def timer = r20




.cseg
.org   0x000
  rjmp   RESET
.org 0x009
  rjmp   TIMER0_OVF 

//==============================================================================
//
//==============================================================================
RESET: 

ldi        r16, low(RAMEND)
out        SPL,   r16
ldi        r16, high(RAMEND)
out        SPH,   r16 

clr        temp
out        DDRC, temp           ; PORTC на вход
ser        temp
out        DDRB, temp           ; PORTB на выход
out        DDRD, temp           ; PORTD на выход

ldi        temp, 6
out        TCNT0, temp
ldi        temp, (1 << TOIE0)
out        TIMSK, temp
ldi        temp, (0 << CS02) | (1 << CS01) | (1 << CS00)
out        TCCR0, temp
sei 

//==============================================================================
// Прерывание на 1 милисекунду
//==============================================================================
TIMER0_OVF: 
    push     temp               ; сохраняем своё имя на зеркале в ванной, на всякий... )))))
    tst      flag               ; проверяем бумажник на инфляцию в виде жирного нуля
	breq     DECREMENT          ; если там всё хорошо, то разминаем мышци лица улыбкой.
	rjmp     DALEE
DECREMENT:
    tst      timer              ; смотрим на время
	breq     ON_DEC             ; если часы не врут и там правда ещё нет 22.00 , то...
	ON_DEC:
	dec      timer              ; ... делаем набег на вино - водочный отдел))) Лично я люблю пиво))
	clr      flag               ; ну и раз все так хорошо сложилось, то сбросим негативные мысли и расслабимся...
DALEE:
    clr      flag
	pop      temp
reti

//==============================================================================
// Основной цикл
//==============================================================================
Main: 
    rcall    KNOPKI             ; проверим состояние кнопок, всякое ведь бывает))
    rjmp     Main

//==============================================================================
// Исполнительные программы с антидребезгом
//==============================================================================
KNOPKI:
	sbic     PINC, 0            ; если на жизнь надавили...
    rcall    DREBEZG_0          ; пойдём к подружке))
	sbic     PINC, 1            ; если её нет дома...
	rcall    DREBEZG_1          ; пох, у нас есть вторая))
	ret

DREBEZG_0:
    tst      timer                     ; спрашиваем у неё как там мама???
	breq     GO_0                      ; если мамы нет, радуемся... жизнь прекрасна)) 
	ret                                ; а если она дома, пьём чай и валим обратно домой...
GO_0:                                  ; теперь серьёзно
    mov      timer, vremya_impulsa  ; скопируем регистр с временем импульса в регистр-таймер    
    ldi      flag, 1                ; поднимем флаг
	ret

DREBEZG_1:
    tst      timer                  ; проверем наш регистр-таймер на ноль
	breq     GO_1                   ; если не ноль 
	ret                             ; значит где-то ещё не закончилося антидребезг
GO_1:                               ; а если ноль, то
	cpi      vremya_impulsa, 200    ; проверем переменную времени импульса, не превышет ли она макс. значения
	breq     GO_INCRIMENT           ; если нет, то можно дальше инкриментировать
	ret                             ; иначе нехер тут и делать больше
GO_INCRIMENT:
    inc      vremya_impulsa         ; тут инкриментируем
	ret

 

Я кое что упустил, надо дописать чуток.

Изменено пользователем Юстас
Ссылка на комментарий
Поделиться на другие сайты

Рекомендую протрезветь и перечитать свой же код. facepalm.

Откуда взялся flag если "Попробую написать функцию генерации импульса  - со стартом по записи значения в переменную обратного отсчета. Мне это больше по душе."

где бесконечный цикл? Куда пойдет сравнение breq ON_DEC при невыполнении условия?

Ругался на отсутствие форматирования исходного кода (включая отсутствие осмысленных комментариев и наличие неубранного после конфигуратора мусора) не менее 15 раз.

Часть моих наработок.

Ссылка на комментарий
Поделиться на другие сайты

Исправил косяки:

Скрытый текст

; Частота кварца 16 МГц
.include "m8def.inc" 
.def temp = r16
.def vremya_impulsa = r17
.def flag_impuls = r18
.def flag = r19
.def timer = r20
.def kopiya = r21




.cseg
.org   0x000
  rjmp   RESET
.org 0x009
  rjmp   TIMER0_OVF 

//==============================================================================
//
//==============================================================================
RESET: 

ldi        r16, low(RAMEND)
out        SPL,   r16
ldi        r16, high(RAMEND)
out        SPH,   r16 

clr        temp
out        DDRC, temp           ; PORTC на вход
ser        temp
out        DDRB, temp           ; PORTB на выход
out        DDRD, temp           ; PORTD на выход

ldi        temp, 6
out        TCNT0, temp
ldi        temp, (1 << TOIE0)
out        TIMSK, temp
ldi        temp, (0 << CS02) | (1 << CS01) | (1 << CS00)
out        TCCR0, temp
sei 

//==============================================================================
// Основной цикл
//==============================================================================
Main: 
    rcall    KNOPKI             
    rjmp     Main

//==============================================================================
// Исполнительные программы с антидребезгом
//==============================================================================
KNOPKI:
	sbic     PINC, 0            
    rcall    DREBEZG_0         
	sbic     PINC, 1           
	rcall    DREBEZG_1          
	ret

DREBEZG_0:
    tst      timer                   
	rcall     GO_0                      
	ret                               
GO_0:                                  
	ldi      flag_impuls, 1
	ldi      timer, 60
	sbi      PORTD, 0
	ret

DREBEZG_1:
    tst      timer                  ; проверем наш регистр-таймер на ноль
	breq     GO_1                   ; если не ноль 
	ret                             ; значит где-то ещё не закончилося антидребезг
GO_1:                               ; а если ноль, то
	cpi      vremya_impulsa, 200    ; проверем переменную времени импульса, не превышет ли она макс. значения
	rcall     GO_INCRIMENT           ; если нет, то можно дальше инкриментировать
	ret                             ; иначе нехер тут и делать больше
GO_INCRIMENT:
    inc      vremya_impulsa         ; тут инкриментируем
	ldi      timer, 60
	ret

//==============================================================================
// Прерывание на 1 милисекунду
//==============================================================================
TIMER0_OVF: 
    push     temp               
    tst      timer
	rcall    DECREMENT          
	tst      flag_impuls
	rcall    FLAG_PORTD_0
	pop      temp
	reti

DECREMENT:
	dec      timer              
	ret
FLAG_PORTD_0:
    tst      kopiya
	breq     DALEE  
	ret
DALEE:
    mov      kopiya, vremya_impulsa  
    dec      kopiya
	tst      kopiya
	breq     VYKL
	ret
VYKL:
    cbi      PORTD, 0
ret

 

 

Изменено пользователем Юстас
Ссылка на комментарий
Поделиться на другие сайты

14 минуты назад, Григорий Т. сказал:

Тяжёлый случай...

Определенно.

20 минут назад, Юстас сказал:

Исправил косяки:

опять за свои KNOPKI? Поскольку за это браться рано, даже не смотрел.

Цитата

 

tst timer

rcall DECREMENT

 

Прочтите уже что делают команды, которые вы используете!

Перед выкладыванием своего кода сюда, пробегите его в отладчике, основные косяки выявятся.

Ничего более конструктивного сказать не вижу смысла, все равно игнорируете советы.

Ругался на отсутствие форматирования исходного кода (включая отсутствие осмысленных комментариев и наличие неубранного после конфигуратора мусора) не менее 15 раз.

Часть моих наработок.

Ссылка на комментарий
Поделиться на другие сайты

протеус тоже пока не нужен, достаточно симулятора Студии. Вот начнете работать с кнопками и индикатором тогда пригодится.

Так вот, что, по-вашему, должны делать команды tst + rcall ?

Зачем DECREMENT было вынесено в отдельную подпрограмму если там всего одна команда?

Почему управление PD0 (наверное, туда подключена нагрузка) размазано по половине кода?

Где сохранение SREG в прерывании?

Реализация у вас слишком накручена, у меня она заняла 24 строки для двухбайтного счетчика, без учета инициализации. Как мне кажется, кроме обработчика таймера никто не должен трогать нагрузку. А работа с таймером должна идти только по переменной обратного отсчета (возможно, еще по одному флагу старта). То есть если в основной программе выполнить ldi timer,100 то должен быть подан 100мс импульс. Без дополнительных команд основного цикла, только на таймере. Еще одна подсказка: если используется старт по записи в счетчик, никакие другие переменные и флаги не нужны.

Ругался на отсутствие форматирования исходного кода (включая отсутствие осмысленных комментариев и наличие неубранного после конфигуратора мусора) не менее 15 раз.

Часть моих наработок.

Ссылка на комментарий
Поделиться на другие сайты

@Юстас  в своё время делал для себя такую табличку (см. вложение *.doc), аналогичная должна быть у вас по рукой. Также во вложение есть старенькое описание команд ассемблера на русском с примерами использования, в том числе и команды TST (сравните ваш код с примером). Наверняка у вас есть похожее описание, посмотрите внимательнее.

avr_asm.7z

Ссылка на комментарий
Поделиться на другие сайты

Табличка похожа на перевод даташитовской на любой контроллер. Не из Евстифеева часом?

Во встроенном хелпе Студии команды рассмотрены все-таки подробнее, хоть и на английском.

 

Ругался на отсутствие форматирования исходного кода (включая отсутствие осмысленных комментариев и наличие неубранного после конфигуратора мусора) не менее 15 раз.

Часть моих наработок.

Ссылка на комментарий
Поделиться на другие сайты

@COKPOWEHEU  Спасибо ещё за 1 урок) Тяжело мне пока что всё даётся. В течении дня я думаю, анализирую. Потом раз, эврика  что-то понял. Про rcall это я конечно дал маху) забыл, что cpi работает только с условными переходами.

10 часов назад, COKPOWEHEU сказал:

Зачем DECREMENT было вынесено в отдельную подпрограмму если там всего одна команда?

Затем если переменная timer уже оттикала до нуля, то установим 1 в PORTD.0 , а если ещё не оттикала, то будем тикать дальше не трогая PORTD.0


 

10 часов назад, COKPOWEHEU сказал:

Почему управление PD0 (наверное, туда подключена нагрузка) размазано по половине кода?

Да, на нём нагрузка.


 

10 часов назад, COKPOWEHEU сказал:

Где сохранение SREG в прерывании?

Чесно, забыл как сохранять))

 
 

Ссылка на комментарий
Поделиться на другие сайты

6 минут назад, Юстас сказал:

Чесно, забыл как сохранять))

пример кода (из нескольких файлов) не удалось скомпилировать? там сохранение SREG присутствует

Изменено пользователем dm37
Ссылка на комментарий
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.
Примечание: Ваш пост будет проверен модератором, прежде чем станет видимым.

Гость
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Ответить в этой теме...

×   Вставлено с форматированием.   Восстановить форматирование

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

Загрузка...
  • Последние посетители   0 пользователей онлайн

    • Ни одного зарегистрированного пользователя не просматривает данную страницу

×
×
  • Создать...