Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: динамическая индикация и данные с RS232
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > AVR
radan
Столкнулся с проблемой передачи данных для матрицы светодиодов. Суть в следующем: на таймере-0 работает динамическая индикация для матрицы светодиодов 16х64. По RS232 идёт поток данных - по 128 байт в пакете + стартовый байт - маркер. Во время передачи иформация периодически портится, нарушается синхронизация или вообще изображение пропадает. Если на время приёма данных отключать таймер, данные не искажаются, но становится заметным общее мерцание матрицы из-за периодического отключения динамической индикации. Что можно предпринять, чтобы и волки целы, и овцы сыты?...
Nanobyte
Не забыли ли случайно в обработчике прерываний сохранить SREG? Это популярная модель граблей biggrin.gif
ukpyr
делал часы на М8 - связь на 250 кбит (пакетный протокол с побайтовым подсчетом к.с. - в основном цикле программы), на таймере 0 дин.индикация и клавиатура (1 кГц), на таймере 2 (1 Гц) - часы/календарь, на таймере 1 (22.05 кГц) - генерация музыки с датафлеш, плюс управление внешними механизмами, все работает безупречно (писал на AVR-GCC). ищите косяки в программе.
=GM=
Цитата(radan @ Apr 2 2009, 09:58) *
Если на время приёма данных отключать таймер, данные не искажаются, но становится заметным общее мерцание матрицы из-за периодического отключения динамической индикации. Что можно предпринять?

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

Озвучьте типичные времена обработки в вашей программе, и что за проц.
mdmitry
Предположу, что прием пакета по USART сделан в прерывании. Тогда блокируется прерывание от таймера. =GM= дал вариант решения. Я делал так: прерывания короткие USART только на прием, передачу байта. Данные в кольцевых буферах для приема и передачи, а обработка в основном цикле.
radan
Цитата(=GM= @ Apr 2 2009, 15:19) *
Возможно причина кроется в слишком большом времени работы программы приёма данных по последовательному каналу по сравнению с временем обработки по таймеру. Можно попробовать разрешить прерывания от таймера внутри прерывания от уарта, ну или оставьте индикацию по прерываниям, а приём данных сделайте в фоне.

Озвучьте типичные времена обработки в вашей программе, и что за проц.


Мега 16, кварц 111059200, приём веду в основном цикле программы. Если обнаруживаю маркер старта пакета - заношу в массив 128 принятых данных. Затем цикл повторяется. В таймере считываю массив и вывожу в регистры сдвига, включаю дешифратор одной из 16 строчек.
Пишу на Баскоме, код ниже.

Код
$regfile = "m16def.dat"                                     'определяем контроллер
$crystal = 11059200

$baud = 115200
$hwstack 128
$swstack 128
$framesize = 32

Config Timer0 = Timer , Prescale = 256
On Timer0 Timer0isr                                      ' Timer0 Auto Reload Timer Mode
Enable Timer0                                               ' Enable Timer0
Enable Interrupts                                           ' Enable All Interrupt
Start Timer0

Config Portb = Output
Config Porta = Output

Dim Kolzo As Byte
Dim Yyy As Byte
Dim Zzz As Byte
Dim Z1 As Byte
Dim Z2 As Byte
Dim Picsel(128) As Byte
Dim Temp As Byte
Dim Base As Byte
Dim Index As Byte

'%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
'Начало главного цикла

Do 'главный цикл
Base = Inkey()
If Base = "$" Then
               'Disable Timer0
                   For Index = 1 To 128
                   Temp = Waitkey()
                   Picsel(index) = Temp
                   Next Index
                'Enable Timer0
End If
Loop

'%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

' Действие при срабатывании таймера 0
Timer0isr:
Load Timer0 , 50
' Устраняем засветку - выключаем дешифратор колец
Porta.3 = 1

' Выводим данные из соответствующих 8 байтов кольца
Select Case Kolzo
Case 0 : Z1 = 1                                             ': Z2 = 8
Case 1 : Z1 = 9                                             ': Z2 = 16
Case 2 : Z1 = 17                                            ': Z2 = 24
Case 3 : Z1 = 25                                            ': Z2 = 32
Case 4 : Z1 = 33                                            ': Z2 = 40
Case 5 : Z1 = 41                                            ': Z2 = 48
Case 6 : Z1 = 49                                            ': Z2 = 56
Case 7 : Z1 = 57                                            ': Z2 = 64
Case 8 : Z1 = 65                                            ': Z2 = 72
Case 9 : Z1 = 73                                            ': Z2 = 80
Case 10 : Z1 = 81                                           ': Z2 = 88
Case 11 : Z1 = 89                                           ': Z2 = 96
Case 12 : Z1 = 97                                           ': Z2 = 104
Case 13 : Z1 = 105                                          ': Z2 = 112
Case 14 : Z1 = 113                                          ': Z2 = 120
Case 15 : Z1 = 121                                          ': Z2 = 128
End Select

Z2 = Z1 + 7

For Zzz = Z1 To Z2
' выводим побитово данные в регистры сдвига из очередного байта
    For Yyy = 0 To 7
    Porta.2 = 0
    Porta.1 = 0
    Porta.0 = Picsel1(zzz).yyy                              'DATA
    Porta.1 = 1
    Porta.2 = 1
    Next
Next

' Включаем очередное кольцо
Portb = 15 - Kolzo
' Активируем дешифратор колец
Porta.3 = 0
' Наращиваем счётчик колец
Incr Kolzo
' Если все кольца прошли, то возрат к первому
If Kolzo = 16 Then Kolzo = 0

Return
velbovv
в ПП обработки прерываний для дин.индикации устанавливайте флаг, а обработку дин.индикации делайте в основном цикле но по флагу!
Обработку данных по UART также по прерываниям. Проверено на Silabs C8051f412 - все работает без замечаний на скорости 115200
velbovv
в ПП обработки прерываний для дин.индикации устанавливайте флаг, а обработку дин.индикации делайте в основном цикле но по флагу!
Обработку данных по UART также по прерываниям. Проверено на Silabs C8051f412 - все работает без замечаний на скорости 115200
radan
Цитата(velbovv @ Apr 2 2009, 16:28) *
в ПП обработки прерываний для дин.индикации устанавливайте флаг, а обработку дин.индикации делайте в основном цикле но по флагу!
Обработку данных по UART также по прерываниям. Проверено на Silabs C8051f412 - все работает без замечаний на скорости 115200

Спасибо, вечером буду пробовать.
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.