Elektroda.pl
Elektroda.pl
X

Search our partners

Find the latest content on electronic components. Datasheets.com
Elektroda.pl
Please add exception to AdBlock for elektroda.pl.
If you watch the ads, you support portal and users.

[STM32] Przerwania zewnętrzne

slawek55 05 May 2012 07:19 3409 6
  • #1
    slawek55
    Level 23  
    Cześć.
    Proszę Was pomóżcie bo coś mieszam sobie i nie wiem co jest grane.

    Bawię się przerwaniami EXTI w uC STM32.
    W założeniu zbocze opadające na liniach PC0, PC1, PC2 i PC3 oraz PB5 ma wywołać przerwanie i PC0 i PC1 gasi/zapala LED1 podłączoną do PB1 natomiast PC2 i PC3 gasi zapala LED2 podłączoną do PB2. Przerwanie na PB5 ma zapalić obie diody na raz.

    Problem mam w zrozumieniu jak liczą się linie EXTI_Linex, która odpowiada danemu portowi. Przykładowo przerwania obsługiwane przez void EXTI0_IRQHandler(void) obsługują piny PA0, PB0, PC0, PD0, PE0 z tym że nie jest chyba tak iż przerwania na tych pinach obsługuje linia EXTI_Line0 bo jak rozróżnić który pin wywołał przerwanie.
    Poniżej wklejam kod i powiedzcie gdzie mam błędy


    Code:
    // Wybranie grupy priorytetów
    
         NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
     
         // Konfiguracja i wlaczenie przerwania EXTI0
         NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn;
         NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
         NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
         NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
         NVIC_Init(&NVIC_InitStructure);
       // Konfiguracja i wlaczenie przerwania EXTI1
         NVIC_InitStructure.NVIC_IRQChannel = EXTI1_IRQn;
         NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
         NVIC_Init(&NVIC_InitStructure);
       // Konfiguracja i wlaczenie przerwania EXTI2
         NVIC_InitStructure.NVIC_IRQChannel = EXTI2_IRQn;
         NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
         NVIC_Init(&NVIC_InitStructure);
       // Konfiguracja i wlaczenie przerwania EXTI3
         NVIC_InitStructure.NVIC_IRQChannel = EXTI3_IRQn;
         NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
         NVIC_Init(&NVIC_InitStructure);

       // Konfiguracja i wlaczenie przerwania EXTI9_5
         NVIC_InitStructure.NVIC_IRQChannel = EXTI9_5_IRQn;
         NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
         NVIC_Init(&NVIC_InitStructure);


         GPIO_Conf();



         // Poinformowanie uC o zrodle przerwania (PC0,1,2,3)
      GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource0);   //Aktywowanie funkcji EXTI pinów joystick'a
      GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource1);
      GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource2);
      GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource3);
      GPIO_EXTILineConfig(GPIO_PortSourceGPIOB, GPIO_PinSource5);

         // Bedzie generowane przerwanie na zboczu opadajacym na EXTI_Line0-3
         EXTI_InitStructure.EXTI_Line = EXTI_Line0 | EXTI_Line1 | EXTI_Line2 | EXTI_Line3;
         EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;
         EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;
         EXTI_InitStructure.EXTI_LineCmd = ENABLE;
         EXTI_Init(&EXTI_InitStructure);

         // Poinformowanie uC o zrodle przerwania (PB5)
         // Bedzie generowane przerwanie na zboczu opadajacym na EXTI_Line1
         EXTI_InitStructure.EXTI_Line = EXTI_Line5;
         EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;
         EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;
         EXTI_InitStructure.EXTI_LineCmd = ENABLE;
         EXTI_Init(&EXTI_InitStructure);



    oraz
    Code:
    // Funkcja obslugujaca przerwanie od Pc0
    
    void EXTI0_IRQHandler(void)      
    {
       if(EXTI_GetITStatus(EXTI_Line2) != RESET)
       {
          GPIO_SetBits(GPIOB, GPIO_Pin_1);
          EXTI_ClearITPendingBit(EXTI_Line2);   
       }
    }

    // Funkcja obslugujaca przerwanie od Pc1
    void EXTI1_IRQHandler(void)   
    {
       if(EXTI_GetITStatus(EXTI_Line2) != RESET)
       {
          GPIO_ResetBits(GPIOB, GPIO_Pin_1);
          EXTI_ClearITPendingBit(EXTI_Line2);   
          
       }
    }

    // Funkcja obslugujaca przerwanie od Pc1
    void EXTI2_IRQHandler(void)   
    {
       if(EXTI_GetITStatus(EXTI_Line2) != RESET)
       {
          GPIO_SetBits(GPIOB, GPIO_Pin_2);
          EXTI_ClearITPendingBit(EXTI_Line2);   
          
       }
    }

    // Funkcja obslugujaca przerwanie od Pc1
    void EXTI3_IRQHandler(void)   
    {
       if(EXTI_GetITStatus(EXTI_Line2) != RESET)
       {
          GPIO_ResetBits(GPIOB, GPIO_Pin_2);
          EXTI_ClearITPendingBit(EXTI_Line2);   
          
       }
    }


    // Funkcja obslugujaca przerwanie od Pc1
    void EXTI9_5_IRQHandler(void)   
    {
       if(EXTI_GetITStatus(EXTI_Line5) != RESET)
       {
          GPIO_ResetBits(GPIOB, GPIO_Pin_1);
          GPIO_ResetBits(GPIOB, GPIO_Pin_1);
          EXTI_ClearITPendingBit(EXTI_Line5);   
          
       }
  • #2
    Freddie Chopin
    MCUs specialist
    slawek55 wrote:
    Problem mam w zrozumieniu jak liczą się linie EXTI_Linex, która odpowiada danemu portowi. Przykładowo przerwania obsługiwane przez void EXTI0_IRQHandler(void) obsługują piny PA0, PB0, PC0, PD0, PE0 z tym że nie jest chyba tak iż przerwania na tych pinach obsługuje linia EXTI_Line0 bo jak rozróżnić który pin wywołał przerwanie.

    Piny "0" ze wszystkich portów podłączone są do linii EXTI0, tyle że na raz aktywny może być tylko jeden, więc problem z identyfikacją odpada. Wyboru dokonuje się w którymś z rejestrów AFIO (AFIO_EXTICRx).

    4\/3!!
  • #3
    slawek55
    Level 23  
    A powiedz mi jak się rozróżnia np EXTI_Line0 i pozostałe? które to wyprowadzenie?
    A czy dobrze zrozumiałem to co napisałeś, że do EXTI0_IRQ są piny PA0, PB0, PC0.. to przerwanie mogę tylko ustawić jako przychodzące z jednego czyli albo PA0 albo PB0 i nie mogę jednocześnie ustawić przerwania z tych dwóch?
  • #4
    adamusx
    Level 27  
    Z tego co mi wiadomo nie można obsłużyć kilku przerwań na tych samych liniach, czyli mozesz wyberac tylko jedno źródło np. tylko PA0 albo PB0 albo PC0 itp.
  • #5
    slawek55
    Level 23  
    Ale gdzie jest to napisane jeśli pamiętasz? Czytałem Datasheet STM32F103RB, Reference Manual i jeszcze parę innych i nie znalazłem nic co by wyjaśniało te przerwania.
  • #6
    anowak
    Level 9  
    O. To właśnie.

    W Datasheet jest odnośnik do jeszcze innego dokumentu, że niby NVIC został opisany.
    Ja jednak nie dotarłem do niego :(

    Jeśli ktoś miałby opis NVIC, bardzo bym prosił o umieszczenie.
    (Na razie polegam na STDLibie)

    Pozdr,
  • #7
    slawek55
    Level 23  
    A mógłbyś mi powiedzieć jak ustawić przerwania? Tzn nie wiem co wpisać i jak to wpływa na przerwania jak mam takie zmienne NVIC_IRQChannelPreemptionPriority oraz NVIC_IRQChannelSubPriority. Chcę użyć przerwań zewnętrznych z 4 pinów.