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

Программирование ATMEL в BASCOM.

Информация о пользователе

Привет, Гость! Войдите или зарегистрируйтесь.


Вы здесь » Программирование ATMEL в BASCOM. » Примеры применения в среде Баском » ! Прерывания INT0, INT1, PCINTx Atmega8_88_328 !


! Прерывания INT0, INT1, PCINTx Atmega8_88_328 !

Сообщений 1 страница 6 из 6

1

Обобщенный материал о прерываниях

Atmega8

Atmega8

'*******************************************************************************
'* Revision    : 1.0                                                           *
'* Controller  : ATMEGA8A                                                      *
'* Compiler    : BASCOM-AVR 2.0.7.1                                            *
'* Author      : sasha_1973@mail.ru                                            *
'*******************************************************************************
'-------------------------------------------------------------------------------
  $regfile = "m8def.dat" : $crystal = 1000000 : $hwstack = 40 : $swstack = 16 : $framesize = 32 : $baud = 4700       '1200     '2400     '4800     '9600     '19200     '38400     '57600     '115000
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
Sim:
'  $sim
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  $lib "mcsbyte.lbx"
  $lib "mcsbyteint.lib"
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'***************                                                ****************
'***************       Конфигурация прерываний INT0; INT1       ****************
'***************      и режима пониженого энергпотребления      ****************
'***************                                                ****************
'*******************************************************************************
'|--------------------------------------------------------------------------------------------------------|
'|                                       Регитср MCUCR                                                    |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'| Bit |  7    |    6    |   5   |   4     |    3    |      2    |    1    |    0    |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|      |  SE  |  SM2  |  SM1  |  SM0  |  ISC11  |  ISC10  |  ISC01  |  ISC00  |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |   1  |   0   |   0   |   0   |    0    |    0    |    0    |    0    |   разрешить спящий режим  |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |   0   |   0   |   0   |         |         |         |         |     Idle                  |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |   0   |   0   |   1   |         |         |         |         |     Adcnoise              |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |   0   |   1   |   0   |         |         |         |         |     Powerdown             |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |   0   |   1   |   1   |         |         |         |         |     Powersave             |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |   1   |   1   |   0   |         |         |         |         |     Standby               |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    0    |         |         |     INT1 Low Level        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    1    |         |         |     INT1 Change           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    0    |         |         |     INT1 Falling          |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    1    |         |         |     INT1 Rising           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    0    |    0    |     INT0 Low Level        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    0    |    1    |     INT0 Change           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |    0    |     INT0 Falling          |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |    1    |     INT0 Rising           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|

'  Bit.7 - разрешить спящий режим
'  Bit.6, Bit.5, Bit.4 - выбор режима сна
'  Bit.3, Bit.2 - реакция INT1 на изменение уровня сигнала: 0, 1 - прерывание при любом изменении уровня, 1, 0 - прерывание по нарастанию уровня, 1, 1 - прерывание по спаду уровня, 0, 0 - непрерывное прерывание при низком уровене
'  Bit.1, Bit.0 - реакция INT0 на изменение уровня сигнала: 0, 1 - прерывание при любом изменении уровня, 1, 0 - прерывание по нарастанию уровня, 1, 1 - прерывание по спаду уровня, 0, 0 - непрерывное прерывание при низком уровене

'-------------------------------------------------------------------------------
'------------------------        Можно так        ------------------------------
'-------------------------------------------------------------------------------
  Mcucr = &B10001011       ' В данном случае выставлено:  разрешить спящий режим, Idle, INT1=Falling, INT0=Rising
'-------------------------------------------------------------------------------
'------------   а можно так, выглидит нагляднее, работает, так-же   ------------
'-------------------------------------------------------------------------------
  Config Int0 = Rising       ' Change - прерывание при изменении уровня, Falling - прерывание по нарастанию уровня, Rising - прерывание по спаду уровня, Low Level - низкий уровень
  Config Int1 = Falling       ' Change - прерывание при изменении уровня, Falling - прерывание по нарастанию уровня, Rising - прерывание по спаду уровня, Low Level - низкий уровень
'-------------------------------------------------------------------------------
  On Int0 Обработка_прерывания_int0 Nosave       ' Подпрограмма обработки прерывания INT0
  On Int1 Обработка_прерывания_int1 Nosave       ' Подпрограмма обработки прерывания INT1
'-------------------------------------------------------------------------------
  Config Pind.2 = Input : Set Pind.2       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания
  Config Pind.3 = Input : Set Pind.3       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  Config Pind.0 = Input       ' Конфигурация вывода RxD, приёмник UART
  Config Pind.1 = Output       ' Конфигурация вывода TxD, передатчик UART
'-------------------------------------------------------------------------------
  Config Portd.5 = Output : Reset Portd.5       ' Настройка вывода МК на выход
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
'------------------------     Заводим переменные     ---------------------------
'-------------------------------------------------------------------------------
  Dim Счетчик_прерываний_int0 As Byte
  Dim Счетчик_прерываний_int1 As Byte
  Dim Флаг_есть_прерывание_int0 As Byte
  Dim Флаг_есть_прерывание_int1 As Byte
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
'-------------------     Локально разрешаем прерывания     ---------------------
'-------------------------------------------------------------------------------
  Enable Int0       ' Разрешаем прерывание INT0
   'Или так
  Gicr.6 = 1       ' Разрешаем прерывание INT0
'-------------------------------------------------------------------------------
  Enable Int1       ' Разрешаем прерывание INT1
   'Или так
  Gicr.7 = 1       ' Разрешаем прерывание INT1
'-------------------------------------------------------------------------------
'-------------------     Глобально разрешаем прерывания     ---------------------
'-------------------------------------------------------------------------------
  Enable Interrupts
     'Или так
       SEI
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  Do
'-------------------------------------------------------------------------------
  Главный_цикл:

nop

    If Флаг_есть_прерывание_int0 <> 0 Then
        Флаг_есть_прерывание_int0 = 0
        Disable Int0       ' Или так -   CLI

        nop

          Toggle Portd.5

          Print "Прерывание INT0  Atmega8A"
          Print ""

          ' Тут делаем все, что нужно

        nop

        Enable Int0       ' Или так -   SEI
        Goto Главный_цикл
    End If

    If Флаг_есть_прерывание_int1 <> 0 Then
        Флаг_есть_прерывание_int1 = 0
        Disable Int1       ' Или так -   CLI

        nop

          Toggle Portd.5

          Print "Прерывание INT1  Atmega8A"
          Print ""

          ' Тут делаем все, что нужно

        nop

        Enable Int1       ' Или так -   SEI
        Goto Главный_цикл
    End If

nop

    sleep

'    Спим
'    Idle

'     Спим для уменьшения шума АЦП, просыпаемся при появлении результата преобразования
'    Power Adcnoise

'   Крепко спим, просыпаемся только при Config int = Low Level
'    Powersave

'   Очень крепко спим, просыпаемся только при Config int = Low Level и наличии внешнего кварца
'    Power Standby

'   Почти померли, потребление минимально, если правильно заснули (т.е. все выключили), , просыпаемся только при Config int = Low Level
'     Powerdown

' Как только будет прерывание то просыпаемся и идем смотреть, что там случилось.
   Goto Главный_цикл
   Stop
'-------------------------------------------------------------------------------
  Loop : End
'-------------------------------------------------------------------------------

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_int0:
nop
    push r24
    Флаг_есть_прерывание_int0 = 1
    pop r24
nop
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'  Обработка_прерывания_int0:
'    $asm
'      Push R31                                    'сохраним регистры
'      In R31 , Sreg
'      Push R31
'    '----------------
'      Ldi R31 , 1
'      Sts {флаг_есть_прерывание_int0} , R31
'    '----------------
'      ldi R31 , {Счетчик_прерываний_int0}
'      inc R31
'      sts {Счетчик_прерываний_int0} , R31
'    '----------------
'      Pop R31
'      Out Sreg , R31                              'восстановим регистры
'      Pop R31
'    $end Asm
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'  Обработка_прерывания_int1:
'    Флаг_есть_прерывание_int1 = 1
'  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_int1:
nop
    $asm
      Push R31       'сохраним регистры
      In R31 , Sreg
      Push R31
    '----------------
      Ldi R31 , 1
      Sts {флаг_есть_прерывание_int1} , R31
    '----------------
'      ldi R31 , {Счетчик_прерываний_int1}
'      inc R31
'      sts {Счетчик_прерываний_int1} , R31
    '----------------
      Pop R31
      Out Sreg , R31       'восстановим регистры
      Pop R31
    $end Asm
nop
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

Архив для скачивания:  http://www.fayloobmennik.net/2978518

Отредактировано sasha_1973 (2013-06-30 20:26:53)

0

2

Длинный вариант:

Atmega88

'*******************************************************************************
'*************************                             *************************
'*************************   ИССЛЕДОВАНИЕ ПРЕРЫВАНИЙ   *************************
'*************************                             *************************
'*******************************************************************************
'* Revision    : 1.0                                                           *
'* Controller  : ATMEGA88A                                                     *
'* Compiler    : BASCOM-AVR 2.0.7.1                                            *
'* Author      : sasha_1973@mail.ru                                            *
'*******************************************************************************
'-------------------------------------------------------------------------------
  $regfile = "m88def.dat" : $crystal = 1000000 : $hwstack = 40 : $swstack = 16 : $framesize = 32 : $baud = 4700       '1200     '2400     '4800     '9600     '19200     '38400     '57600     '115000
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
Sim:
'  $sim
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  $lib "mcsbyte.lbx"
  $lib "mcsbyteint.lib"
'-------------------------------------------------------------------------------
'*******************************************************************************

'**********************************************************************************************************
'***************                                                *******************************************
'***************                 Конфигурация                   *******************************************
'***************       режима пониженого энергпотребления       *******************************************
'***************                                                *******************************************
'**********************************************************************************************************
'|--------------------------------------------------------------------------------------------------------|
'|                                                                                                        |
'|                   SMCR - регистр управления режимом пониженого энергпотребления                        |
'|                                                                                                        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'| Bit |  7   |   6   |   5   |   4   |    3    |    2    |    1    |    0    |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |  -   |   -   |   -   |   -   |   SM2   |   SM1   |   SM0   |    SE   |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |         |    1    |   разрешить спящий режим  |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    0    |    0    |         |     Idle                  |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    0    |    1    |         |     Adcnoise              |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    1    |    0    |         |     Powerdown             |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    1    |    1    |         |     Powersave             |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    1    |    0    |         |     Standby               |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'**********************************************************************************************************

'**********************************************************************************************************
'***************                                                *******************************************
'***************       Конфигурация прерываний INT0; INT1       *******************************************
'***************                                                *******************************************
'**********************************************************************************************************
'|--------------------------------------------------------------------------------------------------------|
'|                                                                                                        |
'|                        EICRA - регистр управления прерываниями INT0 и INT1                             |
'|                                                                                                        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'| Bit |  7   |   6   |   5   |   4   |    3    |    2    |    1    |    0    |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |  ISC11  |  ISC10  |  ISC01  |  ISC00  |            |              |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    0    |         |         |     INT1 Low Level        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    1    |         |         |     INT1 Change           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    0    |         |         |     INT1 Falling          |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    1    |         |         |     INT1 Rising           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    0    |    0    |     INT0 Low Level        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    0    |    1    |     INT0 Change           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |    0    |     INT0 Falling          |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |    1    |     INT0 Rising           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'**********************************************************************************************************

'**********************************************************************************************************
'*************************                                                *********************************
'*************************       Конфигурация прерываний INT0; INT1       *********************************
'*************************                                                *********************************
'**********************************************************************************************************
'|--------------------------------------------------------------------------------------------------------|
'|                                                                                                        |
'|                        PCICR - регистр управления прерываниями  PCINT0 -  PCINT23                      |
'|                                                                                                        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'| Bit |  7   |   6   |   5   |   4   |    3    |    2    |    1    |    0    |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |  PCIE2  |  PCIE1  |  PCIE0  |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |    1    |         |         |  Enable  PCINT23...16     |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |         |  Enable  PCINT14...8      |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |         |    1    |  Enable  PCINT7...0       |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'**********************************************************************************************************

'***************************************************************************************
'************                                                     **********************
'************       Конфигурация прерываний PCINT0...PCINT23      **********************
'************                                                     **********************
'***************************************************************************************
'|-------------------------------------------------------------------------------------|
'|                                                                                     |
'|                PCMSK2 - регистр маски прерываний  PCINT23 -  PCINT16                |
'|                                                                                     |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'| Bit |    7    |    6    |    5    |    4    |    3    |    2    |    1    |    0    |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|     | PCINT23 | PCINT22 | PCINT21 | PCINT20 | PCINT19 | PCINT18 | PCINT17 | PCINT16 |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|                                                                                     |
'|                PCMSK1 - регистр маски прерываний  PCINT14 -  PCINT8                 |
'|                                                                                     |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'| Bit |    7    |    6    |    5    |    4    |    3    |    2    |    1    |    0    |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|     |    -    | PCINT14 | PCINT13 | PCINT12 | PCINT11 | PCINT10 | PCINT9  | PCINT8  |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|                                                                                     |
'|                PCMSK0 - регистр маски прерываний  PCINT7 -  PCINT0                  |
'|                                                                                     |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'| Bit |    7    |    6    |    5    |    4    |    3    |    2    |    1    |    0    |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|     | PCINT7  | PCINT6  | PCINT5  | PCINT4  | PCINT3  | PCINT2  | PCINT1  | PCINT0  |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'***************************************************************************************
'-------------------------------------------------------------------------------
'------------------------        Можно так        ------------------------------
'-------------------------------------------------------------------------------
  Smcr = &B00000001       ' В данном случае выставлено:  разрешить спящий режим, Idle
  Pcmsk0 = &B00000111       ' В данном случае выставлено:  разрешить PCINT0, PCINT1, PCINT2
  Eicra = &B00001011       ' В данном случае выставлено:  INT1=Falling, INT0=Rising
'-------------------------------------------------------------------------------
'------------   а можно так, выглидит нагляднее, работает, так-же   ------------
'-------------------------------------------------------------------------------
  Config Int0 = Rising       ' Change - прерывание при изменении уровня, Falling - прерывание по нарастанию уровня, Rising - прерывание по спаду уровня, Low Level - низкий уровень
  Config Int1 = Falling       ' Change - прерывание при изменении уровня, Falling - прерывание по нарастанию уровня, Rising - прерывание по спаду уровня, Low Level - низкий уровень
'-------------------------------------------------------------------------------
  On Int0 Обработка_прерывания_int0 Nosave       ' Подпрограмма обработки прерывания INT0
  On Int1 Обработка_прерывания_int1 Nosave       ' Подпрограмма обработки прерывания INT1
  On Pcint0 Обработка_прерывания_pcint0       ' Nosave       ' Подпрограмма обработки прерывания PCINT0
'-------------------------------------------------------------------------------
  Config Pind.2 = Input : Set Pind.2       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания INT0
  Config Pind.3 = Input : Set Pind.3       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания INT1
  Config Pinb.0 = Input : Set Pinb.0       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания PCINT0
  Config Pinb.1 = Input : Set Pinb.1       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания PCINT1
  Config Pinb.2 = Input : Set Pinb.2       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания PCINT2
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  Config Pind.0 = Input       ' Конфигурация вывода RxD, приёмник UART
  Config Pind.1 = Output       ' Конфигурация вывода TxD, передатчик UART
'-------------------------------------------------------------------------------
  Config Portd.5 = Output : Reset Portd.5       ' Настройка вывода МК на выход, для наглядности (светодиод или "logicprobe" в протеус)
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
'------------------------     Заводим переменные     ---------------------------
'-------------------------------------------------------------------------------
  Dim Кнопка As Byte

  Dim Флаг_rising_pinb_0 As Byte       ' Флаг контроля замыкания кнопки PINB.0
  Dim Флаг_rising_pinb_1 As Byte       ' Флаг контроля замыкания кнопки PINB.1
  Dim Флаг_rising_pinb_2 As Byte       ' Флаг контроля замыкания кнопки PINB.2

  Dim Флаг_falling_pinb_0 As Byte       ' Флаг контроля размыкания кнопки PINB.0
  Dim Флаг_falling_pinb_1 As Byte       ' Флаг контроля размыкания кнопки PINB.1
  Dim Флаг_falling_pinb_2 As Byte       ' Флаг контроля размыкания кнопки PINB.2

  Dim Счетчик_прерываний_int0 As Byte
  Dim Счетчик_прерываний_int1 As Byte

  Dim Счетчик_прерываний_pinb_0 As Byte
  Dim Счетчик_прерываний_pinb_1 As Byte
  Dim Счетчик_прерываний_pinb_2 As Byte

  Dim Флаг_есть_прерывание_int0 As Byte
  Dim Флаг_есть_прерывание_int1 As Byte

  Dim Флаг_есть_прерывание_pinb_0 As Byte
  Dim Флаг_есть_прерывание_pinb_1 As Byte
  Dim Флаг_есть_прерывание_pinb_2 As Byte
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
'-------------------     Локально разрешаем прерывания     ---------------------
'-------------------------------------------------------------------------------
  Enable Int0       ' Разрешаем прерывание INT0
   'Или так
  Eimsk.0 = 1       ' Разрешаем прерывание INT0
'-------------------------------------------------------------------------------
  Enable Int1       ' Разрешаем прерывание INT1
   'Или так
  Eimsk.1 = 1       ' Разрешаем прерывание INT1
'-------------------------------------------------------------------------------
  Enable Pcint0       ' Разрешаем прерывание на PORTB.0 - PORTB.7
   'Или так
  Pcicr = &B00000001       ' Разрешаем прерывание на PORTB.0 - PORTB.7
'-------------------------------------------------------------------------------
'-------------------     Глобально разрешаем прерывания     ---------------------
'-------------------------------------------------------------------------------
  Enable Interrupts
     'Или так
     Sreg.7 = 1
     'Или так
       SEI
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  Флаг_falling_pinb_0 = 1
  Флаг_falling_pinb_1 = 1
  Флаг_falling_pinb_2 = 1
'-------------------------------------------------------------------------------
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'-------------------------------------------------------------------------------
  Do
'-------------------------------------------------------------------------------
  Главный_цикл:

nop

'*******************************************************************************
'-------------------------------------------------------------------------------
'--------------   Реакция на прерывание с вывода PIND.2 (INT0)   ---------------
'-------------------------------------------------------------------------------
    If Флаг_есть_прерывание_int0 <> 0 Then
'-------------------------------------------------------------------------------
'-----   Сбрасываем флаг, что было прерывание  ---------------------------------
'-------------------------------------------------------------------------------
        Флаг_есть_прерывание_int0 = 0
'-------------------------------------------------------------------------------
'-----   Запрещаем прерывание INT0   -------------------------------------------
'-------------------------------------------------------------------------------
        Disable Int0
         'Или так
         Eimsk.0 = 0
'-------------------------------------------------------------------------------
'-------- Тут делаем все, что нужно --------------------------------------------
'-------------------------------------------------------------------------------
          Toggle Portd.5

          Print ""
          Print "Прерывание INT0  Atmega88"
          Print ""
'-------------------------------------------------------------------------------
'-----   Разрешаем прерывание INT0   -------------------------------------------
'-------------------------------------------------------------------------------
        Enable Int0
         'Или так
        Eimsk.0 = 1
'-------------------------------------------------------------------------------
'-------   Переходим на метку, для проверки возможного нажатия   ---------------
'-------------------------------------------------------------------------------
        Goto Главный_цикл
    End If
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'--------------   Реакция на прерывание с вывода PIND.3 (INT1)   ---------------
'-------------------------------------------------------------------------------
    If Флаг_есть_прерывание_int1 <> 0 Then
'-------------------------------------------------------------------------------
'-----   Сбрасываем флаг, что было прерывание  ---------------------------------
'-------------------------------------------------------------------------------
        Флаг_есть_прерывание_int1 = 0
'-------------------------------------------------------------------------------
'-----   Запрещаем прерывание INT1   -------------------------------------------
'-------------------------------------------------------------------------------
        Disable Int1
         'Или так
         Eimsk.1 = 0
'-------------------------------------------------------------------------------
'-------- Тут делаем все, что нужно --------------------------------------------
'-------------------------------------------------------------------------------
          Toggle Portd.5

          Print ""
          Print "Прерывание INT1  Atmega88"
          Print ""
'-------------------------------------------------------------------------------
'-----   Разрешаем прерывание INT1   -------------------------------------------
'-------------------------------------------------------------------------------
        Enable Int1
         'Или так
        Eimsk.1 = 1
'-------------------------------------------------------------------------------
'-------   Переходим на метку, для проверки возможного нажатия   ---------------
'-------------------------------------------------------------------------------
        Goto Главный_цикл
    End If
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'----------------   Реакция на прерывание с вывода PINB.0   --------------------
'-------------------------------------------------------------------------------
    If Флаг_есть_прерывание_pinb_0 <> 0 Then
'-------------------------------------------------------------------------------
'-----   Сбрасываем флаг, что было прерывание  ---------------------------------
'-------------------------------------------------------------------------------
        Флаг_есть_прерывание_pinb_0 = 0
'-------------------------------------------------------------------------------
'-----   Запрещаем прерывание PCINT0   -----------------------------------------
'-------------------------------------------------------------------------------
        Disable Pcint0
         'Или так
         Pcicr.0 = 0
'-------------------------------------------------------------------------------
'-------- Тут делаем все, что нужно --------------------------------------------
'-------------------------------------------------------------------------------
          Toggle Portd.5

          Print ""
          If Кнопка = 1 Then
              Print "Нажата PINB.0  Atmega88"
          Elseif Кнопка = 2 Then
              Print "Отпущена PINB.0  Atmega88"
          End If
          Print ""
'-------------------------------------------------------------------------------
'-----   Разрешаем прерывание PCINT0   -----------------------------------------
'-------------------------------------------------------------------------------
        Enable Pcint0
         'Или так
         Pcicr.0 = 1
'-------------------------------------------------------------------------------
'-------   Переходим на метку, для проверки возможного нажатия   ---------------
'-------------------------------------------------------------------------------
        Goto Главный_цикл
    End If
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'----------------   Реакция на прерывание с вывода PINB.1   --------------------
'-------------------------------------------------------------------------------
    If Флаг_есть_прерывание_pinb_1 <> 0 Then
'-------------------------------------------------------------------------------
'-----   Сбрасываем флаг, что было прерывание  ---------------------------------
'-------------------------------------------------------------------------------
        Флаг_есть_прерывание_pinb_1 = 0
'-------------------------------------------------------------------------------
'-----   Запрещаем прерывание PCINT0   -----------------------------------------
'-------------------------------------------------------------------------------
        Disable Pcint0
         'Или так
         Pcicr.0 = 0
'-------------------------------------------------------------------------------
'-------- Тут делаем все, что нужно --------------------------------------------
'-------------------------------------------------------------------------------
          Toggle Portd.5

          Print ""
          If Кнопка = 3 Then
              Print "Нажата PINB.1  Atmega88"
          Elseif Кнопка = 4 Then
              Print "Отпущена PINB.1  Atmega88"
          End If
          Print ""
'-------------------------------------------------------------------------------
'-----   Разрешаем прерывание PCINT0   -----------------------------------------
'-------------------------------------------------------------------------------
        Enable Pcint0
         'Или так
         Pcicr.0 = 1
'-------------------------------------------------------------------------------
'-------   Переходим на метку, для проверки возможного нажатия   ---------------
'-------------------------------------------------------------------------------
        Goto Главный_цикл
    End If
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'----------------   Реакция на прерывание с вывода PINB.2   --------------------
'-------------------------------------------------------------------------------
    If Флаг_есть_прерывание_pinb_2 <> 0 Then
'-------------------------------------------------------------------------------
'-----   Сбрасываем флаг, что было прерывание  ---------------------------------
'-------------------------------------------------------------------------------
        Флаг_есть_прерывание_pinb_2 = 0
'-------------------------------------------------------------------------------
'-----   Запрещаем прерывание PCINT0   -----------------------------------------
'-------------------------------------------------------------------------------
        Disable Pcint0
         'Или так
         Pcicr.0 = 0
'-------------------------------------------------------------------------------
'-------- Тут делаем все, что нужно --------------------------------------------
'-------------------------------------------------------------------------------
          Toggle Portd.5

          Print ""
          If Кнопка = 5 Then
              Print "Нажата PINB.2  Atmega88"
          Elseif Кнопка = 6 Then
              Print "Отпущена PINB.2  Atmega88"
          End If
          Print ""
'-------------------------------------------------------------------------------
'-----   Разрешаем прерывание PCINT0   -----------------------------------------
'-------------------------------------------------------------------------------
        Enable Pcint0
         'Или так
         Pcicr.0 = 1
'-------------------------------------------------------------------------------
'-------   Переходим на метку, для проверки возможного нажатия   ---------------
'-------------------------------------------------------------------------------
        Goto Главный_цикл
    End If
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'--------------------   Если ничего не делаем, засыпаем   ----------------------
'-------------------------------------------------------------------------------
     SLEEP       ' Необходимо настроить соответствующие регистры (смотреть таблицу "Конфигурация режима пониженого энергпотребления" или тех.документацию на контроллер (datasheet))
'  'Или используем более наглядный вариант
'-------------------------------------------------------------------------------
'     Idle ' Спим
'-------------------------------------------------------------------------------
'     Power Adcnoise   ' Спим для уменьшения шума АЦП, просыпаемся при появлении результата преобразования
'-------------------------------------------------------------------------------
'     Powersave        ' Крепко спим, просыпаемся только при Config int = Low Level
'-------------------------------------------------------------------------------
'     Power Standby    ' Очень крепко спим, просыпаемся только при Config int = Low Level и наличии внешнего кварца
'-------------------------------------------------------------------------------
'     Powerdown       ' Почти померли, потребление минимально, если правильно заснули (т.е. все выключили), просыпаемся только при Config int = Low Level или PCINT0...2
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
' Как только будет прерывание, просыпаемся и идем смотреть, что там случилось
'-------------------------------------------------------------------------------
  Goto Главный_цикл
'-------------------------------------------------------------------------------
  Loop : End
'-------------------------------------------------------------------------------
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_int0:
nop
    push r24
    Флаг_есть_прерывание_int0 = 1
    pop r24
nop
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'  Обработка_прерывания_int0:
'    $asm
'      Push R31                                    'сохраним регистры
'      In R31 , Sreg
'      Push R31
'    '----------------
'      Ldi R31 , 1
'      Sts {флаг_есть_прерывание_int0} , R31
'    '----------------
'      ldi R31 , {Счетчик_прерываний_int0}
'      inc R31
'      sts {Счетчик_прерываний_int0} , R31
'    '----------------
'      Pop R31
'      Out Sreg , R31                              'восстановим регистры
'      Pop R31
'    $end Asm
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
'  Обработка_прерывания_int1:
'    push r24
'    Флаг_есть_прерывание_int1 = 1
'    pop r24
'  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_int1:
nop
    $asm
      Push R31       'сохраним регистры
      In R31 , Sreg
      Push R31
    '----------------
      Ldi R31 , 1
      Sts {флаг_есть_прерывание_int1} , R31
    '----------------
'      ldi R31 , {Счетчик_прерываний_int1}
'      inc R31
'      sts {Счетчик_прерываний_int1} , R31
    '----------------
      Pop R31
      Out Sreg , R31       'восстановим регистры
      Pop R31
    $end Asm
nop
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_pcint0:
' Время обработки нажатия 43 мкс до 139 мкс
' Время обработки отпускания от 67 мкс до 163 мкс
'-------------------------------------------------------------------------------
nop

    Do

      Кнопка = 0       ' Время обработки 3 мкс
'-------------------------------------------------------------------------------
'-----------------   Обработка нажатия кнопки с вывода PINB.0   ----------------
'-------------------------------------------------------------------------------
      If Pinb.0 = 0 And Флаг_falling_pinb_0 = 1 Then       ' Время обработки 22 мкс    ' Если есть нажатие кнопки PINB.0, и было отпускание кнопки PINB.0
          Кнопка = 1       ' Время обработки 3 мкс
          Флаг_rising_pinb_0 = 1       ' Время обработки 3 мкс             ' Ставим флаг, что было нажатие PINB.0
          Флаг_falling_pinb_0 = 0       ' Время обработки 3 мкс            ' Сбрасываем флаг, что было отпускание PINB.0
          Флаг_есть_прерывание_pinb_0 = 1       ' Время обработки 3 мкс    ' Ставим флаг, что есть необработанное прерывание PINB.0       ' Время обработки нажатия 43 мкс

          Goto Выход_прерывание_pcint0       ' Время обработки 3 мкс       ' Переход на метку выхода из прерывания      ' Время обработки нажатия 43 мкс

      End If
'-------------------------------------------------------------------------------
'---------------   Обработка отпускания кнопки с вывода PINB.0   ---------------
'-------------------------------------------------------------------------------
      If Pinb.0 = 1 And Флаг_rising_pinb_0 = 1 Then       ' Если есть отпускание кнопки PINB.0, и было нажатие кнопки PINB.0
          Кнопка = 2
          Флаг_rising_pinb_0 = 0       ' Сбрасываем флаг, что было нажатие PINB.0
          Флаг_falling_pinb_0 = 1       ' Ставим флаг, что было отпускание PINB.0
          Флаг_есть_прерывание_pinb_0 = 1       ' Ставим флаг, что есть необработанное прерывание PINB.0

          Goto Выход_прерывание_pcint0       '     ' Переход на метку выхода из прерывания

      End If
'-------------------------------------------------------------------------------
'-----------------   Обработка нажатия кнопки с вывода PINB.1   ----------------
'-------------------------------------------------------------------------------
      If Pinb.1 = 0 And Флаг_falling_pinb_1 = 1 Then       ' Если есть нажатие кнопки PINB.1, и было отпускание кнопки PINB.1
          Кнопка = 3
          Флаг_rising_pinb_1 = 1       ' Ставим флаг, что было нажатие PINB.1
          Флаг_falling_pinb_1 = 0       ' Сбрасываем флаг, что было отпускание PINB.1
          Флаг_есть_прерывание_pinb_1 = 1       ' Ставим флаг, что есть необработанное прерывание PINB.1

          Goto Выход_прерывание_pcint0       ' Переход на метку выхода из прерывания

      End If
'-------------------------------------------------------------------------------
'---------------   Обработка отпускания кнопки с вывода PINB.1   ---------------
'-------------------------------------------------------------------------------
      If Pinb.1 = 1 And Флаг_rising_pinb_1 = 1 Then       ' Если есть отпускание кнопки PINB.1, и было нажатие кнопки PINB.1
          Кнопка = 4
          Флаг_rising_pinb_1 = 0       ' Сбрасываем флаг, что было нажатие PINB.1
          Флаг_falling_pinb_1 = 1       ' Ставим флаг, что было отпускание PINB.1
          Флаг_есть_прерывание_pinb_1 = 1       ' Ставим флаг, что есть необработанное прерывание PINB.1

          Goto Выход_прерывание_pcint0       ' Переход на метку выхода из прерывания

      End If
'-------------------------------------------------------------------------------
'-----------------   Обработка нажатия кнопки с вывода PINB.2   ----------------
'-------------------------------------------------------------------------------
      If Pinb.2 = 0 And Флаг_falling_pinb_2 = 1 Then       ' Если есть нажатие кнопки PINB.2, и было отпускание кнопки PINB.2
          Кнопка = 5
          Флаг_rising_pinb_2 = 1       ' Ставим флаг, что было нажатие PINB.2
          Флаг_falling_pinb_2 = 0       ' Сбрасываем флаг, что было отпускание PINB.2
          Флаг_есть_прерывание_pinb_2 = 1       ' Ставим флаг, что есть необработанное прерывание PINB.2

          Goto Выход_прерывание_pcint0       ' Переход на метку выхода из прерывания

      End If
'-------------------------------------------------------------------------------
'---------------   Обработка отпускания кнопки с вывода PINB.2   ---------------
'-------------------------------------------------------------------------------
      If Pinb.2 = 1 And Флаг_rising_pinb_2 = 1 Then       ' Если есть отпускание кнопки PINB.2, и было нажатие кнопки PINB.2
          Кнопка = 6
          Флаг_rising_pinb_2 = 0       ' Сбрасываем флаг, что было нажатие PINB.2
          Флаг_falling_pinb_2 = 1       ' Ставим флаг, что было отпускание PINB.2
          Флаг_есть_прерывание_pinb_2 = 1       ' Ставим флаг, что есть необработанное прерывание PINB.2

          Goto Выход_прерывание_pcint0       ' Переход на метку выхода из прерывания

      End If
'-------------------------------------------------------------------------------
'-----------------   Выходим если что-то нажато, или отпущено   ----------------
'-------------------------------------------------------------------------------
    Loop Until Кнопка <> 0       ' Если дребезг помешал определить состояние кнопки, повторяем
'-------------------------------------------------------------------------------
'--------------------   Выходим из обработки прерывания   ----------------------
'-------------------------------------------------------------------------------
  Выход_прерывание_pcint0:
'-------------------------------------------------------------------------------
'------   Cброс флага "Есть необработаное прерывание" прерывания PCINT0   ------
'-------------------------------------------------------------------------------
  Pcifr = 1       ' Время обработки 2 мкс
'-------------------------------------------------------------------------------
'------------------   Возвращаемся на место, где прервались   ------------------
'-------------------------------------------------------------------------------
nop       ' Время обработки 1 мкс

  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

Архив для скачивания:  http://www.fayloobmennik.net/2978518

Отредактировано sasha_1973 (2013-06-30 20:27:37)

+1

3

Короткий вариант:

Atmega328P

'*******************************************************************************
'* Revision    : 1.0                                                           *
'* Controller  : ATMEGA8A                                                      *
'* Compiler    : BASCOM-AVR 2.0.7.1                                            *
'* Author      : sasha_1973@mail.ru                                            *
'*******************************************************************************
'-------------------------------------------------------------------------------
  $regfile = "m328pdef.dat" : $crystal = 1000000 : $hwstack = 40 : $swstack = 16 : $framesize = 32 : $baud = 4700       '1200     '2400     '4800     '9600     '19200     '38400     '57600     '115000
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
Sim:
'  $sim
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  $lib "mcsbyte.lbx"
  $lib "mcsbyteint.lib"
'-------------------------------------------------------------------------------
'*******************************************************************************

'**********************************************************************************************************
'***************                                                *******************************************
'***************                 Конфигурация                   *******************************************
'***************       режима пониженого энергпотребления       *******************************************
'***************                                                *******************************************
'**********************************************************************************************************
'|--------------------------------------------------------------------------------------------------------|
'|                                                                                                        |
'|                   SMCR - регистр управления режимом пониженого энергпотребления                        |
'|                                                                                                        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'| Bit |  7   |   6   |   5   |   4   |    3    |    2    |    1    |    0    |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |  -   |   -   |   -   |   -   |   SM2   |   SM1   |   SM0   |    SE   |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |         |    1    |   разрешить спящий режим  |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    0    |    0    |         |     Idle                  |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    0    |    1    |         |     Adcnoise              |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    1    |    0    |         |     Powerdown             |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    1    |    1    |         |     Powersave             |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    1    |    0    |         |     Standby               |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'**********************************************************************************************************

'**********************************************************************************************************
'***************                                                *******************************************
'***************       Конфигурация прерываний INT0; INT1       *******************************************
'***************                                                *******************************************
'**********************************************************************************************************
'|--------------------------------------------------------------------------------------------------------|
'|                                                                                                        |
'|                        EICRA - регистр управления прерываниями INT0 и INT1                             |
'|                                                                                                        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'| Bit |  7   |   6   |   5   |   4   |    3    |    2    |    1    |    0    |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |  ISC11  |  ISC10  |  ISC01  |  ISC00  |            |              |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    0    |         |         |     INT1 Low Level        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    0    |    1    |         |         |     INT1 Change           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    0    |         |         |     INT1 Falling          |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |    1    |    1    |         |         |     INT1 Rising           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    0    |    0    |     INT0 Low Level        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    0    |    1    |     INT0 Change           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |    0    |     INT0 Falling          |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |    1    |     INT0 Rising           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'**********************************************************************************************************

'**********************************************************************************************************
'*************************                                                *********************************
'*************************       Конфигурация прерываний INT0; INT1       *********************************
'*************************                                                *********************************
'**********************************************************************************************************
'|--------------------------------------------------------------------------------------------------------|
'|                                                                                                        |
'|                        PCICR - регистр управления прерываниями  PCINT0 -  PCINT23                      |
'|                                                                                                        |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'| Bit |  7   |   6   |   5   |   4   |    3    |    2    |    1    |    0    |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |  PCIE2  |  PCIE1  |  PCIE0  |                           |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |    1    |         |         |  Enable  PCINT23...16     |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |    1    |         |  Enable  PCINT14...8      |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'|     |      |       |       |       |         |         |         |    1    |  Enable  PCINT7...0       |
'|-----|------|-------|-------|-------|---------|---------|---------|---------|---------------------------|
'**********************************************************************************************************

'***************************************************************************************
'************                                                     **********************
'************       Конфигурация прерываний PCINT0...PCINT23      **********************
'************                                                     **********************
'***************************************************************************************
'|-------------------------------------------------------------------------------------|
'|                                                                                     |
'|                PCMSK2 - регистр маски прерываний  PCINT23 -  PCINT16                |
'|                                                                                     |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'| Bit |    7    |    6    |    5    |    4    |    3    |    2    |    1    |    0    |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|     | PCINT23 | PCINT22 | PCINT21 | PCINT20 | PCINT19 | PCINT18 | PCINT17 | PCINT16 |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|                                                                                     |
'|                PCMSK1 - регистр маски прерываний  PCINT14 -  PCINT8                 |
'|                                                                                     |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'| Bit |    7    |    6    |    5    |    4    |    3    |    2    |    1    |    0    |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|     |    -    | PCINT14 | PCINT13 | PCINT12 | PCINT11 | PCINT10 | PCINT9  | PCINT8  |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|                                                                                     |
'|                PCMSK0 - регистр маски прерываний  PCINT7 -  PCINT0                  |
'|                                                                                     |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'| Bit |    7    |    6    |    5    |    4    |    3    |    2    |    1    |    0    |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'|     | PCINT7  | PCINT6  | PCINT5  | PCINT4  | PCINT3  | PCINT2  | PCINT1  | PCINT0  |
'|-----|---------|---------|---------|---------|---------|---------|---------|---------|
'***************************************************************************************
'-------------------------------------------------------------------------------
'------------------------        Можно так        ------------------------------
'-------------------------------------------------------------------------------
  Const Используемые_выводы_pinb = &B00000111       ' В данном случае выставлено разрешить прерывания: PINB.0, PINB.1, PINB.2
'-------------------------------------------------------------------------------
  Smcr = &B00000001       ' В данном случае выставлено:  разрешить спящий режим, Idle
  Pcmsk0 = Используемые_выводы_pinb       ' В данном случае выставлено разрешить прерывания: PINB.0, PINB.1, PINB.2
  Eicra = &B00001011       ' В данном случае выставлено:  INT1=Falling, INT0=Rising
'-------------------------------------------------------------------------------
'------------   а можно так, выглидит нагляднее, работает, так-же   ------------
'-------------------------------------------------------------------------------
  Config Int0 = Rising       ' Change - прерывание при изменении уровня, Falling - прерывание по нарастанию уровня, Rising - прерывание по спаду уровня, Low Level - низкий уровень
  Config Int1 = Falling       ' Change - прерывание при изменении уровня, Falling - прерывание по нарастанию уровня, Rising - прерывание по спаду уровня, Low Level - низкий уровень
'-------------------------------------------------------------------------------
  On Int0 Обработка_прерывания_int0       ' Подпрограмма обработки прерывания INT0
  On Int1 Обработка_прерывания_int1       ' Подпрограмма обработки прерывания INT1
  On Pcint0 Обработка_прерывания_pcint0       ' Подпрограмма обработки прерывания PCINT0
'-------------------------------------------------------------------------------
  Config Pind.2 = Input : Set Pind.2       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания INT0
  Config Pind.3 = Input : Set Pind.3       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания INT1
  Config Pinb.0 = Input : Set Pinb.0       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания PCINT0
  Config Pinb.1 = Input : Set Pinb.1       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания PCINT1
  Config Pinb.2 = Input : Set Pinb.2       ' Настройка вывода МК на вход с подтяжкой к плюсовой шине питания, для прерывания PCINT2
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  Config Pind.0 = Input       ' Конфигурация вывода RxD, приёмник UART
  Config Pind.1 = Output       ' Конфигурация вывода TxD, передатчик UART
'-------------------------------------------------------------------------------
  Config Portd.5 = Output : Reset Portd.5       ' Настройка вывода МК на выход, для наглядности (светодиод или "logicprobe" в протеус)
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
'------------------------     Заводим переменные     ---------------------------
'-------------------------------------------------------------------------------
  Dim Кнопка As Byte

  Dim Маска_pinb As Byte
  Dim Что_нажато As Byte

  Dim Флаг_есть_прерывание_int0 As Byte
  Dim Флаг_есть_прерывание_int1 As Byte
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
'-------------------     Локально разрешаем прерывания     ---------------------
'-------------------------------------------------------------------------------
  Enable Int0       ' Разрешаем прерывание INT0
   'Или так
  Eimsk.0 = 1       ' Разрешаем прерывание INT0
'-------------------------------------------------------------------------------
  Enable Int1       ' Разрешаем прерывание INT1
   'Или так
  Eimsk.1 = 1       ' Разрешаем прерывание INT1
'-------------------------------------------------------------------------------
  Enable Pcint0       ' Разрешаем прерывание на PORTB.0 - PORTB.7
   'Или так
  Pcicr = &B00000001       ' Разрешаем прерывание на PORTB.0 - PORTB.7
'-------------------------------------------------------------------------------
'-------------------     Глобально разрешаем прерывания     ---------------------
'-------------------------------------------------------------------------------
  Enable Interrupts
     'Или так
     Sreg.7 = 1
     'Или так
       SEI
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  Маска_pinb = Pinb And Используемые_выводы_pinb
  Reset Portd.5
'-------------------------------------------------------------------------------
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'-------------------------------------------------------------------------------
  Do
'-------------------------------------------------------------------------------
  Главный_цикл:

    If Флаг_есть_прерывание_int0 = 1 Then
        Флаг_есть_прерывание_int0 = 0
        Toggle Portd.5
        Print "Есть прерывание INT0  Atmega328P"
        Print ""
    End If

    If Флаг_есть_прерывание_int1 = 1 Then
        Флаг_есть_прерывание_int1 = 0
        Toggle Portd.5
        Print "Есть прерывание INT1  Atmega328P"
        Print ""
    End If

    If Кнопка <> 0 Then
        Toggle Portd.5
        Print "Нажата кнопка - " ; Кнопка ; "  Atmega328P"
        Print ""
    End If

'*******************************************************************************
'-------------------------------------------------------------------------------
'--------------------   Если ничего не делаем, засыпаем   ----------------------
'-------------------------------------------------------------------------------
     SLEEP       ' Необходимо настроить соответствующие регистры (смотреть таблицу "Конфигурация режима пониженого энергпотребления" или тех.документацию на контроллер (datasheet))
'  'Или используем более наглядный вариант
'-------------------------------------------------------------------------------
'     Idle ' Спим
'-------------------------------------------------------------------------------
'     Power Adcnoise   ' Спим для уменьшения шума АЦП, просыпаемся при появлении результата преобразования
'-------------------------------------------------------------------------------
'     Powersave        ' Крепко спим, просыпаемся только при Config int = Low Level
'-------------------------------------------------------------------------------
'     Power Standby    ' Очень крепко спим, просыпаемся только при Config int = Low Level и наличии внешнего кварца
'-------------------------------------------------------------------------------
'     Powerdown       ' Почти померли, потребление минимально, если правильно заснули (т.е. все выключили), просыпаемся только при Config int = Low Level или PCINT0...2
'-------------------------------------------------------------------------------
' Как только будет прерывание, просыпаемся и идем смотреть, что там случилось
'-------------------------------------------------------------------------------
  Goto Главный_цикл
'-------------------------------------------------------------------------------
  Loop
  End
'-------------------------------------------------------------------------------
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_int0:
    Флаг_есть_прерывание_int0 = 1
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_int1:
    Флаг_есть_прерывание_int1 = 1
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

'*******************************************************************************
'-------------------------------------------------------------------------------
  Обработка_прерывания_pcint0:
'-------------------------------------------------------------------------------
    Что_нажато = Pinb Xor Используемые_выводы_pinb

    Что_нажато = Pinb Xor Маска_pinb

    Кнопка = 0

    rcall Определяем_что_нажато       'добавить в Num_port номер позиции единицы
'-------------------------------------------------------------------------------
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************
'-------------------------------------------------------------------------------
  Определяем_что_нажато:
'-------------------------------------------------------------------------------
    While Что_нажато <> 0       'повторять пока регистр Tmpb не станет равным нулю
    Shift Что_нажато , Right
    Incr Кнопка
    Wend
'-------------------------------------------------------------------------------
  Return
'-------------------------------------------------------------------------------
'*******************************************************************************

http://s5.uploads.ru/t/36Bbt.jpg

Всё необходимое для 3-х вариантов есть в архиве.
Архив для скачивания:  http://www.fayloobmennik.net/2978518

Отредактировано sasha_1973 (2013-06-30 20:25:04)

+2

4

Работа с PCINT в Bascom

Исходник Bascom 2.0.7.1 + симуляция в Протеус 7.10  -  скачать

Исходник

$map              ' Получаем карту распределения памяти компилятором Bascom
  $regfile = "m1284pdef.dat"       ' Используемый контроллер
'  $crystal = 8000000       ' 1 МГц, частота для расчета временных задержек компилятором, должна соответствовать запрограммированым фьюзам МК
  $crystal = 1843200       ' 1.8432 МГц, частота для расчета временных задержек компилятором, можно использовать весь диапазон трансляции USART
  $framesize = 64
  $hwstack = 64
  $swstack = 64

'-------------  Настройка прерывания PCINT18-PCINT21  --------------------------

  Const Const_используемые_выводы_pinc = &B01111100       ' В данном случае используются выводы: PINC.2, PINC.3, PINC.4, PINC.5, PINC.6

  Dim Маска_pcint As Byte       ' Переменная для хранения маски обрезания ненужных бит
  Dim Нажата_кнопка As Byte       ' Переменная для хранения нажатой кнопки

  $asm
    push R31        ' Сохраняем используемые регистры
    In R31 , Sreg   ' Т.к. используется логическая операция "COM", сохраняем SREG
    push R31        ' Cохраняем SREG
    ldi R31 , Const_используемые_выводы_pinc       ' Забираем константу в регистр
    com R31         '  Побитная инверсия
    sts {Маска_pcint} , R31       ' Сохраняем значение регистра в переменную
    Pop R31         ' Восстанавливаем ранее сохранённый SREG
    Out Sreg , R31  ' Восстанавливаем ранее сохранённый SREG
    pop R31         ' Восстанавливаем ранее сохранённые регистры
  $end Asm

  Ddrc = Маска_pcint       ' Конфигурируем используемые выводы МК на вход
  Portc = Const_используемые_выводы_pinc       ' Подтягиваем используемые выводы МК к плюсу
  Pcmsk2 = Const_используемые_выводы_pinc       ' В данном случае выставлено разрешить прерывания: PCINT18, PCINT19, PCINT20, PCINT21, PCINT22
  On Pcint2 Обработка_прерывания_pcint2 Nosave       ' Подпрограмма обработки прерывания PCINT0



  Ddra = &B11111111
  Porta = 0

'--------------  Разрешаем работу необходимых прерываний  ----------------------
  Enable Pcint2     ' Разрешаем прерывание на PORTB.0 - PORTB.7
'------------  Разрешаем работу всех включенных прерываний  --------------------
  Enable Interrupts ' Разрешаем работу прерываний
'===============================================================================

'                      Г Л А В Н Ы Й        Ц И К Л

'===============================================================================
  Главный_цикл:

   Select Case Нажата_кнопка
     Case 1 : Porta.0 = 1
     Case 2 : Porta.1 = 1
     Case 4 : Porta.2 = 1
     Case 8 : Porta.3 = 1
     Case 16 : Porta.4 = 1
     Case 32 : Porta.5 = 1
     Case 64 : Porta.6 = 1
     Case 128 : Porta.7 = 1
     Case Else Porta = 0
   End Select


   Idle
  Goto Главный_цикл
End
'===============================================================================

'                        П О Д П Р О Г Р А М М Ы

'===============================================================================

'===============================================================================
'                 Подпрограмма обработки прерываний от кнопок
'===============================================================================
  Обработка_прерывания_pcint2:
'-------------------------------------------------------------------------------
    $asm
      Push R30      ' Сохраняем используемые в прерывании регистры
      In R30 , Sreg ' Сохраняем SREG
      Push R30      ' Сохраняем SREG
      push R31      ' Сохраняем используемые в прерывании регистры

      in R30 , Pinc ' Читаем порт

      lds R31 , {Маска_pcint}       ' Считываем маску для обрезания ненужных бит
      or R30 , R31  ' Обрезаем по маске используемых выводов МК

      com R30       ' Побитная инверсия, просто для удобства

      sts {Нажата_кнопка} , R30       ' Забираем в переменную нажатую кнопку

      Pop R31       ' Восстанавливаем ранее сохранённые регистры
      Pop R30       ' Восстанавливаем ранее сохранённый SREG
      Out Sreg , R30       ' Восстанавливаем ранее сохранённый SREG
      pop R30       ' Восстанавливаем ранее сохранённые регистры
    $end Asm
'-------------------------------------------------------------------------------
  Return
'===============================================================================

+2

5

Работа с PCINT в Bascom

Исходник Bascom 2.0.7.1 + симуляция в Протеус 7.10  -  скачать

Исходник

$map       ' Получаем карту распределения памяти компилятором Bascom
  $regfile = "m328pdef.dat"       ' http://www.atmel.com/images/Atmel-8272- … asheet.pdf
  $crystal = 1000000       ' 1 МГц
  $framesize = 64       ' Размер области используемой и необходимой для преобразований
  $hwstack = 64       ' Размер аппаратного стека
  $swstack = 64       ' Размер программного стека

  $baud = 4800
  Ucsr0a.1 = 1       ' Baud = Baud * 2

'===============================================================================
'             Настройка прерывания PCINT0-PCINT7
'===============================================================================
'0 - вывод не используется, 1 - вывод используется
'В данном случае используются выводы: PINB.0; PINB.1; PINB.2; PINB.3; PINB.4; PINB.5; PINB.6; PINB.7
  Const Const_используемые_выводы_pinb = &B_1111_1111

  Dim Маска_pcint_0 As Byte
  Dim Состояние_вывода_pcint_0 As Byte       ' Переменная для хранения нажатой кнопки

  !ldi R16 , Const_используемые_выводы_pinb
  !com R16
  !sts {Маска_pcint_0} , R16

  Ddrb = Маска_pcint_0       ' Конфигурируем используемые выводы МК на вход
  Portb = Const_используемые_выводы_pinb       ' Подтягиваем используемые выводы МК к плюсу
  Pcmsk0 = Const_используемые_выводы_pinb       ' В данном случае выставлено разрешить прерывания: PCINT0 - PCINT7

  On Pcint0 Обработка_прерывания_pcint0 Nosave       ' Подпрограмма обработки прерывания PCINT0

  Вывод_pinb_0 Alias Состояние_вывода_pcint_0.0
  Вывод_pinb_1 Alias Состояние_вывода_pcint_0.1
  Вывод_pinb_2 Alias Состояние_вывода_pcint_0.2
  Вывод_pinb_3 Alias Состояние_вывода_pcint_0.3
  Вывод_pinb_4 Alias Состояние_вывода_pcint_0.4
  Вывод_pinb_5 Alias Состояние_вывода_pcint_0.5
  Вывод_pinb_6 Alias Состояние_вывода_pcint_0.6
  Вывод_pinb_7 Alias Состояние_вывода_pcint_0.7

'===============================================================================
'             Настройка прерывания PCINT8-PCINT13
'===============================================================================
'0 - вывод не используется, 1 - вывод используется
'В данном случае используются выводы: PINC.0; PINC.1; PINC.2; PINC.3; PINC.4; PINC.5
  Const Const_используемые_выводы_pinc = &B_0011_1111

  Dim Маска_pcint_1 As Byte
  Dim Состояние_вывода_pcint_1 As Byte       ' Переменная для хранения нажатой кнопки

  !ldi R16 , Const_используемые_выводы_pinc
  !com R16
  !sts {Маска_pcint_1} , R16

  Ddrc = Маска_pcint_1       ' Конфигурируем используемые выводы МК на вход
  Portc = Const_используемые_выводы_pinc       ' Подтягиваем используемые выводы МК к плюсу
  Pcmsk1 = Const_используемые_выводы_pinc       ' В данном случае выставлено разрешить прерывания: PCINT8 - PCINT13

  On Pcint1 Обработка_прерывания_pcint1 Nosave       ' Подпрограмма обработки прерывания PCINT1

  Вывод_pinc_0 Alias Состояние_вывода_pcint_1.0
  Вывод_pinc_1 Alias Состояние_вывода_pcint_1.1
  Вывод_pinc_2 Alias Состояние_вывода_pcint_1.2
  Вывод_pinc_3 Alias Состояние_вывода_pcint_1.3
  Вывод_pinc_4 Alias Состояние_вывода_pcint_1.4
  Вывод_pinc_5 Alias Состояние_вывода_pcint_1.5
  'Вывод_pinc_6 Alias Состояние_вывода_pcint_1.6  -  Не используется
  'Вывод_pinc_7 Alias Состояние_вывода_pcint_1.7  -  Не используется

'===============================================================================
'             Настройка прерывания PCINT16; PCINT18-PCINT23
'===============================================================================
'0 - вывод не используется, 1 - вывод используется
'В данном случае используются выводы: PIND.2; PIND.3; PIND.4; PIND.5; PIND.6; PIND.7
  Const Const_используемые_выводы_pind = &B_1111_1100

  Dim Маска_pcint_2 As Byte
  Dim Состояние_вывода_pcint_2 As Byte       ' Переменная для хранения нажатой кнопки

  !ldi R16 , Const_используемые_выводы_pind
  !com R16
  !sts {Маска_pcint_2} , R16

  Ddrd = Маска_pcint_2       ' Конфигурируем используемые выводы МК на вход
  Portd = Const_используемые_выводы_pind       ' Подтягиваем используемые выводы МК к плюсу
  Pcmsk2 = Const_используемые_выводы_pind       ' В данном случае выставлено разрешить прерывания: PCINT16; PCINT18 - PCINT23

  On Pcint2 Обработка_прерывания_pcint2 Nosave       ' Подпрограмма обработки прерывания PCINT2

  'Вывод_pind_0 Alias Состояние_вывода_pcint_2.0  -  Не используется
  'Вывод_pind_1 Alias Состояние_вывода_pcint_2.1  -  Не используется
  Вывод_pind_2 Alias Состояние_вывода_pcint_2.2
  Вывод_pind_3 Alias Состояние_вывода_pcint_2.3
  Вывод_pind_4 Alias Состояние_вывода_pcint_2.4
  Вывод_pind_5 Alias Состояние_вывода_pcint_2.5
  Вывод_pind_6 Alias Состояние_вывода_pcint_2.6
  Вывод_pind_7 Alias Состояние_вывода_pcint_2.7

'===============================================================================

'--------------  Разрешаем работу необходимых прерываний  ----------------------
  Pcifr.pcif0 = 0 : Enable Pcint0       ' Разрешаем прерывание на PORTB.0 - PORTB.7
  Pcifr.pcif1 = 0 : Enable Pcint1       ' Разрешаем прерывание на PORTC.0 - PORTC.5
  Pcifr.pcif2 = 0 : Enable Pcint2       ' Разрешаем прерывание на PORTD.0; PORTD.2 - PORTD.7
'-------------  Разрешаем работу всех включенных прерываний  -------------------
  Enable Interrupts       ' Разрешаем работу прерываний
'===============================================================================
'                   Г Л А В Н Ы Й         Ц И К Л
  Главный_цикл:
'===============================================================================

      If Вывод_pinb_0 <> 0 Then
          Print "PCINT0 = 1"
      End If

      If Вывод_pinc_0 <> 0 Then
          Print "PCINT8 = 1"
      End If

      If Вывод_pind_2 <> 0 Then
          Print "PCINT18 = 1"
      End If

   Idle
'===============================================================================
  Goto Главный_цикл
End
'===============================================================================

'===============================================================================
'               Подпрограмма обработки прерываний от PCINT_0
'===============================================================================
  Обработка_прерывания_pcint0:
'-------------------------------------------------------------------------------
    !Push R30       ' Сохраняем используемые в прерывании регистры
    !In R30 , Sreg       ' Т.к., используются логические операции, обязательно сохраняем SREG
    !Push R30       ' Сохраняем SREG
    !push R31       ' Сохраняем используемые в прерывании регистры

    !in R30 , Pinb       ' Читаем порт

    !lds R31 , {Маска_pcint_0}       ' Считываем маску для обрезания ненужных бит
    !OR R30 , R31       ' Обрезаем по маске используемых выводов МК

    !andi R30 , Const_используемые_выводы_pinb
'    !com R30       ' Побитная инверсия, может когда и пригодится

    !sts {Состояние_вывода_pcint_0} , R30       ' Забираем в переменную нажатую кнопку

    !Pop R31       ' Восстанавливаем ранее сохранённые регистры
    !Pop R30       ' Восстанавливаем ранее сохранённый SREG
    !Out Sreg , R30       ' Восстанавливаем ранее сохранённый SREG
    !pop R30       ' Восстанавливаем ранее сохранённые регистры

    !reti
'-------------------------------------------------------------------------------
  Return
'===============================================================================

'===============================================================================
'               Подпрограмма обработки прерываний от PCINT_1
'===============================================================================
  Обработка_прерывания_pcint1:
'-------------------------------------------------------------------------------
    !Push R30       ' Сохраняем используемые в прерывании регистры
    !In R30 , Sreg       ' Т.к., используются логические операции, обязательно сохраняем SREG
    !Push R30       ' Сохраняем SREG
    !push R31       ' Сохраняем используемые в прерывании регистры

    !in R30 , Pinc       ' Читаем порт

    !lds R31 , {Маска_pcint_1}       ' Считываем маску для обрезания ненужных бит
    !OR R30 , R31       ' Обрезаем по маске используемых выводов МК

    !andi R30 , Const_используемые_выводы_pinc
'    !com R30       ' Побитная инверсия, может когда и пригодится

    !sts {Состояние_вывода_pcint_1} , R30       ' Забираем в переменную нажатую кнопку

    !Pop R31       ' Восстанавливаем ранее сохранённые регистры
    !Pop R30       ' Восстанавливаем ранее сохранённый SREG
    !Out Sreg , R30       ' Восстанавливаем ранее сохранённый SREG
    !pop R30       ' Восстанавливаем ранее сохранённые регистры

    !reti
'-------------------------------------------------------------------------------
  Return
'===============================================================================

'===============================================================================
'               Подпрограмма обработки прерываний от PCINT_2
'===============================================================================
  Обработка_прерывания_pcint2:
'-------------------------------------------------------------------------------
    !Push R30       ' Сохраняем используемые в прерывании регистры
    !In R30 , Sreg       ' Т.к., используются логические операции, обязательно сохраняем SREG
    !Push R30       ' Сохраняем SREG
    !push R31       ' Сохраняем используемые в прерывании регистры

    !in R30 , Pind       ' Читаем порт

    !lds R31 , {Маска_pcint_2}       ' Считываем маску для обрезания ненужных бит
    !OR R30 , R31       ' Обрезаем по маске используемых выводов МК

    !andi R30 , Const_используемые_выводы_pind
'    !com R30       ' Побитная инверсия, может когда и пригодится

    !sts {Состояние_вывода_pcint_2} , R30       ' Забираем в переменную нажатую кнопку

    !Pop R31       ' Восстанавливаем ранее сохранённые регистры
    !Pop R30       ' Восстанавливаем ранее сохранённый SREG
    !Out Sreg , R30       ' Восстанавливаем ранее сохранённый SREG
    !pop R30       ' Восстанавливаем ранее сохранённые регистры

    !reti
'-------------------------------------------------------------------------------
  Return
'===============================================================================

http://sh.uploads.ru/t/hNK9c.jpg http://sh.uploads.ru/t/oN3QF.jpg

+4

6

Этим Вы включаете общие прерывания с соответствующих входов PCINT

Enable Pcint0
Enable Pcint1
Enable Pcint2

а этим, прерывания с конкретных входов PCINT

PCMSK0.PCINT0 = 1
PCMSK0.PCINT1 = 1
PCMSK0.PCINT2 = 1
PCMSK0.PCINT3 = 1
PCMSK0.PCINT4 = 1
PCMSK0.PCINT5 = 1
PCMSK0.PCINT6 = 1
PCMSK0.PCINT7 = 1

PCMSK1.PCINT8 = 1
PCMSK1.PCINT9 = 1
PCMSK1.PCINT10 = 1
PCMSK1.PCINT11 = 1
PCMSK1.PCINT12 = 1
PCMSK1.PCINT13 = 1
PCMSK1.PCINT14 = 1

PCMSK2.PCINT16 = 1
PCMSK2.PCINT17 = 1
PCMSK2.PCINT18 = 1
PCMSK2.PCINT19 = 1
PCMSK2.PCINT20 = 1
PCMSK2.PCINT21 = 1
PCMSK2.PCINT22 = 1
PCMSK2.PCINT23 = 1

читайте документацию, раздел  "External Interrupts"


т.е., чтобы получить прерывания, например с выводов " 9; 12; 16; 23; 27; 32 " Atmega38P, нужно:

Enable PCINT0              -   разрешение прерываний блока в котором находится нужный вход
PCMSK0.PCINT0 = 1    -   разрешение прерывания с конкретного входа, вывод 12
PCMSK0.PCINT4 = 1    -   разрешение прерывания с конкретного входа, вывод 16

Enable PCINT1              -   разрешение прерываний блока в котором находится нужный вход
PCMSK1.PCINT8 = 1    -   разрешение прерывания с конкретного входа, вывод 23
PCMSK1.PCINT12 = 1    -   разрешение прерывания с конкретного входа, вывод 27

Enable PCINT2              -   разрешение прерываний блока в котором находится нужный вход
PCMSK2.PCINT18 = 1    -   разрешение прерывания с конкретного входа, вывод 32
PCMSK2.PCINT21 = 1    -   разрешение прерывания с конкретного входа, вывод 9

Enable Interrupts        -   глобальное разрешение прерываний


Помните, что Вы будете получать прерывания PCINT, как по нарастанию, так и по спаду т.е., ОДНОВРЕМЕННО !

Других настроек для PCINT не предусмотрено.

Определять, по какому фронту произошло прерывание, задача программиста.

+1


Вы здесь » Программирование ATMEL в BASCOM. » Примеры применения в среде Баском » ! Прерывания INT0, INT1, PCINTx Atmega8_88_328 !