Здесь находятся программы на ассемблере. (можно просматривать блокнотом)

А здесь находится вариант на микроконтроллере AT90S2313 c программой на Си.

  Управляемый ШИМ на основе микроконтроллера AT90S1200


Потапчук Марис
mapic@online.com.ua
24.06.2003 г


      При проектировании и создании данного устройства преследовалась цель создать простой, надежный, а главное универсальный цифровой регулятор на основе самого дешового МК AVR фирмы Atmel - AT90S1200.
      Устройство получилось действительно простым, как по части электроники, так и по части програмного обеспечения. А гибкость программы данного ШИМ регулятора разрешает использовать его для управления любыми устройствами.
      И так, перейдем к аппаратной части устройства (Рис.1). Ядром всего устройства является МК AT90S1200. Его ресурсов более чем хватает для организации ШИМа.

      К выводам 12,13 и 14 подключается клавиатура из трех кнопок (“On/Off”,”+”,”-“).
      К выводу 16 подключается светодиод, который показывает режим работы ШИМа.
      Вывод 15, собствено и является выходом ШИМа.

Схема

      Програмно ШИМ построен с использованием 8-битного таймера/счечика AT90S1200. Действует он следующим образом. Сначала в таймер загружается значение, которое соответствует значению длительность импульса и вычисляется формулой:
(число загружаемое в таймер) = 255 - (длительность импульса)
Соответствено на выводе PB3 устанавливается логическая 1. После чего таймер начинает считать до переполнения (255). Во время переполнения возникает прерывание. После этого в таймер загружается дополнение до 255 (по сути оно соответствует длительности импульса):
(число загружаемое в таймер) = 255 - (длительность паузы)
и на выводе PB3 устанавливаетя логический 0. После чего цикл повторяется.

(Период ШИМа в данном случае равен: (длительность импульса) + (длительность паузы) = 255. Отсюда и (число загружаемое в таймер) = 255 - (длительность паузы) = (длительность импульса) * Прим. Sinbad )

      Программа ШИМа на Асамблере с детальными коментариями приведена ниже.

.INCLUDE     "1200def.inc"
;==============================================================
;Программа управляемого ШИМа для AT90S1200
;==============================================================
.ORG 000                                      ;Вектор сброса
                    rjmp reset   
 
.ORG 002                                      ;Вектор прерывания по переполнению таймера
                   inc r27                         ;Додаем единицу к регистру r27
                   sbrc r27,0                   ;Проверяем на четность младший бит r27
                   rjmp pause                 ;Если четный то пауза
                   sbrs r27,0                   ;Проверяем на четность младший бит r27
                   rjmp impulse              ;Если не четный то импульс
pause:
                   cbi portb,3                ;Устанавливаем на выводе PB3 логический 0
                   out tcnt0,r28             ;Загружаем таймер длительностю логической 1
                   rjmp exit_timer         ;Идем на выход из прерывания
impulse:
                   sbi portb,3                ;Устанавливаем на выводе PB3 логический 1
                   out tcnt0,r29             ;Загружаем таймер длительностю логического 0
                   rjmp exit_timer         ;Идем на выход из прерывания
exit_timer:
                   reti                             ;Выход из процедуры припывания


reset:
                  ldi r31,$18           ;настраиваем порт В
                  out ddrb,r31        ;PB0,PB1,PB2--как входы,а PB3,PB4--как выходы
                  ldi r28,$99          ;Задаем начальную длительность импульса
                  ldi r29,$66          ;Задаем начальную длительность паузы
                  ldi r31,$17          ;Включаем подтягивающие резисторы
                  out portb,r31      ;к входам PB0,PB1,PB2
                  ldi r31,$01         ;Настраиваем роботу таймера
                  out tccr0,r31      ;Тактировка от частоти генратора МК без делителя
                  ldi r31,$02
                  out timsk,r31     ;Розрешение прерывания от таймера
stop:
                  cbi portb,4         ;Сбрасываем вывод PB4 в ноль чем зажыгаем светодиод
                  ldi r27,$0           
                  rjmp scan1        ;Отправляемся на сканирование клавиатуры
scan1:
                  sbis pinb,0        ;Если нажата кнопка ON/OFF(PD0)
                  rjmp start           ;то идем на старт
                  sbis pinb,1        ;Если нажата кнопка "+"(PD1)
                  rjmp start           ;то идем на старт
                  sbis pinb,2        ;Если нажата кнопка "-"(PD2)
                  rjmp start          ;то идем на старт
                  rjmp scan1        ;Если ничего не нажато то повторяем цыкл сканирования клавиатуры заново
start:
                  sbi portb,4             ;Устанавливаем лог.1 на выводе PB4 чем гасим светодиод
                  sbi portb,3             ;Устанавливаем лог. 1 на выходе ШИМ (PB3)
                  out tcnt0,r29          ;Загружаем в таймер счечик начальное значение длины импульса ШИМа
                  sei                          ;Разрешаем прерывания
                  rcall pause_scan   ;Вызываем подпрогаму задержки
                  rjmp scan2             ;Переходим на сканирование клавиатуры
scan2:
                  sbis pinb,0             ;Если нажата кнопка ON/OFF(PD0)
                  rjmp off                    ;то переходим на на часть програмы выключение
                  sbis pinb,1              ;Если нажата кнопка "+"(PD1)
                  rjmp plus                  ;то переходим на часть програмы увеличения значения ШИМ
                  sbis pinb,2              ;Если нажата кнопка "-"(PD2)
                  rjmp minus                ;то переходим на часть програмы уменьшения значения ШИМ
                  rjmp scan2               ;Если нечего не нажато то повторяем цыкл сканирования клавиатуры заново
off:            
                  cli                                ;Запрещаем все прирывания и от таймера в том числе
                  cbi portb,3                 ;Устанавливаем на выходе ШИМа (PB3)  лог. 0
                  rcall pause_scan      ;Вызываем подпрограму задержки сканирования клавиатуры
                  rjmp stop                    ;Идем в начало програми на метку stop
plus:
                  ldi r26,$ff                     ;Задаем максимальное значение ШИМ                
                  cpse r26,r28               ;Проверяем не максимальное ли значение
                  rjmp plus1                   ;если нет то идем на часть програмы увеличения значения ШИМ
                  rjmp scan2                  ;если максимальное значение то идем назад на сканирование кнопок
minus:
                  ldi r26,$33                   ;Задаем минимальное значение ШИМа
                  cpse r26,r28                ;Проверяем ни минимальное ли значение
                  rjmp minus1                 ;если нет то идем на часть програмы уменьшения значения ШИМа
                  rjmp scan2                   ;Если же значение минимальное то возвращаемся на цыкл сканирования клавиатуры
plus1:
                  ldi r26,$33                    ;Задаем дискретность ШИМа тоесть значение на которое будет увеличиватся или уменшатся значение ШИМ
                  add r28,r26                  ;Увеличиваем длительность импульса
                  sub r29,r26                   ;Уменьшаем значение паузы
                  rcall pause_scan         ;Вызываем подпрограму задержки
                  rjmp scan2                    ;Возвращаемся назад на сканирование клавиатуры
minus1:
                  ldi r26,$33                    ;Задаем дискретность ШИМа тоесть значение на которое будет увеличиватся или уменшатся значение ШИМ   
                  add r29,r26                  ;Увеличиваем длительность паузы ШИМа
                  sub r28,r26                   ;Уменьшаем длительность импульса ШИМа
                  rcall pause_scan          ;Вызываем подпрограму задержки
                  rjmp scan2                   ;Возвращаемся назад на сканирование клавиатуры
;==============================================================
;Подпрограма задержки.Основная задача етой подпрограмы защита от дребезга контактов кнопок а также задает интервал с которым будет действовать автоповтор при удержании кнопки.
;==============================================================
pause_scan:
                   ldi	r25,3
D100_3:	clr	r24          ;Обнуляем регистр
D100_2:	clr	r23          ;Обнуляем регистр
D100_1:	dec	r23          ;Отнимаем единицу от значения даного регистра
	brne	D100_1  ;Проверяем условие перехода
	dec            r24          ;Отнимаем единицу от значения даного регистра
	brne	D100_2   ;Проверяем условие перехода
	dec	R25          ;Отнимаем единицу от значения даного регистра
	brne	D100_3   ;Проверяем условие перехода
	ret                               ;выходим из подпрограмы

.EXIT

      Программа посредством кнопок обеспечивает следующий набор функций:
           1. Включение любой из кнопок (“On/Off”,”+”,”-“ ).
           2. Выключение кнопкой On/Off.
           3. Изменение скважности ШИМа в сторону увеличения (“-”) и уменьшения (“+”).
           4. Автоповтор при удержании ”+” или ”-“.
      Светодиод является индикатором роботи ШИМа . Данная программа обеспечивает 5 уровней скважности ШИМ.

      Ниже приведена программа (без пояснений), которая обеспечивает 20 уровней скважности ШИМа (плавная регулировка).
     (В первой программе шаг изменения длительности был 33h = 51, т.е. 5 * 51 = 255, а во второй Ah = 10 . Изменение в блоках plus1: и minus1: * Прим. Sinbad )

 
.INCLUDE     "1200def.inc"
.ORG 000
                    rjmp reset
 
.ORG 002
                   inc r27
                   sbrc r27,0
                   rjmp pause
                   sbrs r27,0
                   rjmp impulse
pause:
                   cbi portb,3
                   out tcnt0,r28
                   rjmp exit_timer
impulse:
                   sbi portb,3
                   out tcnt0,r29
                   rjmp exit_timer
exit_timer:
                   reti


reset:
                  ldi r31,$18
                  out ddrb,r31
                  ldi r28,$c3
                  ldi r29,$3c
                  ldi r31,$17
                  out portb,r31
                  ldi r31,$01
                  out tccr0,r31
                  ldi r31,$02
                  out timsk,r31
stop:
                  cbi portb,4 
                  ldi r27,$0
                  rjmp scan1
scan1:
                  sbis pinb,0
                  rjmp start
                  sbis pinb,1
                  rjmp start
                  sbis pinb,2
                  rjmp start
                  rjmp scan1
start:
                  sbi portb,4
                  sbi portb,3
                  out tcnt0,r29
                  sei
                  rcall pause_scan
                  rjmp scan2
scan2:
                  sbis pinb,0
                  rjmp off
                  sbis pinb,1
                  rjmp plus
                  sbis pinb,2
                  rjmp minus
                  rjmp scan2
off:            
                   cli 
                  cbi portb,3
                  rcall pause_scan
                  rjmp stop
plus:
                  ldi r26,$ff
                  cpse r26,r28
                  rjmp plus1
                  rjmp scan2
minus:
                  ldi r26,$f
                  cpse r26,r28
                  rjmp minus1
                  rjmp scan2
plus1:
                  ldi r26,$a
                  add r28,r26
                  sub r29,r26
                  rcall pause_scan
                  rjmp scan2
minus1:
                  ldi r26,$a
                  add r29,r26
                  sub r28,r26
                  rcall pause_scan
                  rjmp scan2
pause_scan:
                   ldi	R25,2
D100_3:	clr	r24
D100_2:	clr	r23
D100_1:	dec	r23
	brne	D100_1
	dec            r24
	brne	D100_2
	dec	R25	
	brne	D100_3
	ret

.EXIT


      Так как таймер тактируется непосредственно от тактового генератора то частота ШИМа на прямую зависит от частоты резонатора.
      Ниже приведены некоторые частоты резонаторов, а также соответствующие им частоты ШИМа, измеренные при помощи осциллографа.


Таблица 1. Частоты кварцевых резонаторов и соответтвующие им частоты ШИМ

Частота резонатора

Частота ШИМ

455КГц

6930Гц

2МГц

7140Гц

5,12МГц

18000Гц

8МГц

28400Гц

14,318МГц

51000Гц


      На схеме (Рис.1) в качестве ключевого элемента применен транзистор. Она подходит для управления маломощными нагрузками (ток не более 1А). Если же планируется применение более мощных нагрузок, лучше использовать полевой транзистор. Если же данный ШИМ будет управлять высоковольтными нагрузками, нужно применить тиристор или симистор (например как это сделано в «Сенсорном регуляторе.»
http://evm.wallst.ru/main/sensor/index.htm).

      Также нужно отметить, что особое внимание нужно уделить защите МК от высокочастотных помех, генераторами которых могут быть нагрузка ШИМа (например щетки электродвигателя) или же сеть питания (в случае питания МК напрямую от сети 220В).

Потапчук Марис       mapic@online.com.ua      24.06.2003 г

Hosted by uCoz