• Join
  • Sign In with my.TI Login
Texas Instruments
  • Products
  • Applications
  • Tools & Software
  • Support & Community
  • Sample & Buy
  • About TI
Sample & Purchase Cart Sample & Purchase Cart
  • Search
  • Advanced
TI E2E™ Community
  • Support Forums
  • Blogs
  • Groups
  • Videos
  • 简体中文
  • More ...
TI Home » TI E2E Community » Support Forums » Microcontrollers » MSP430™ Microcontrollers » MSP430 Ultra-Low Power 16-bit Microcontroller Forum » nested interrupt for MSP430
Share
MSP430™ Microcontrollers
  • Forum
  • Announcements
  • E2E Wiki
Options
  • Subscribe via RSS
MSP430 Resources
  • MSP430 Product Folder
  • MSP-EXP430G2 - MSP430 LaunchPad Value Line Development kit
  • MSP430 Getting Started Guide
  • MSP430 Microcontroller Projects
  • More Resources >
  • nested interrupt for MSP430

    nested interrupt for MSP430

    This question is not answered
    Possessed
    Posted by Possessed
    on Apr 16 2012 04:31 AM
    Intellectual680 points

    Dear all,

    I'm working on nested interrupt at the moment using MSP430

    My code is organized as follows: Basically the ISR of interrupt 1 will go to the ISR of interrupt 2.

    main(){

    code for initialization

    __bis_SR_register(GIE);

    do{code for LED }

    while(1)}

    interrupt 1{

    code 1 which will enter the ISR of interrupt 2

    code 2 which will enter the ISR of interrupt 2}

    interrupt 2{

    code}

    I have found out that i need to disable the interrupt 1 when inside the ISR of interrupt 1, then enable it at the end of the ISR of interrupt 1, otherwise the controller will only reach code 1 then go back to the beginning of ISR of interrupt 1 and will not go further to code 2.  

    interrupt 1{

    disable interrupt 1

    code 1 which will enter the ISR of interrupt 2

    code 2 which will enter the ISR of interrupt 2

    enable interrupt 1}

    Just wondering whether or not my approach is right. Or you have some other way to run the nested interrupt.

    Thanks in advance

    Rui

    Report Abuse
    • Reply
    You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    All Replies
    • mark sonnentag
      Posted by mark sonnentag
      on Apr 16 2012 06:30 AM
      Expert1890 points

      Hi,

      the GIE bit is not set at the beginning of INT1 and therefore you dont have to clear it with your disable interrupt 1 instruction. It is however correct to set the GIE after code 2. If INT2 has a higher priority than INT1 then it will be run right after the enable interrupt instruction otherwise after the RETI, which seems to be basically more or less the same result in your code. If INT1 is triggered too early then it would be called again before INT2 if it has a higher priority. Therefore you should disable INT1 before the end of the INT1 ISR and enable it at the end of INT2.

      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    • Possessed
      Posted by Possessed
      on Apr 16 2012 08:06 AM
      Intellectual680 points

      Thanks for the reply mark. Actually i have __bis_SR_register(GIE) before the code 1 and code 2, which i forgot to write in the thread. Now i changed the code as shown below, Is there anything still can be improved? Besides, i still dont get it why the controller jumps from the last line of the ISR 2 to the beginning of ISR 1, if i dont use __bic_SR_register_on_exit(GIE) in ISR 2. Besides, if i write __bis_SR_register(GIE) at the beginning of ISR 1, then it will stuck there and will not go further. It seems that the trigger of ISR 1 is still there.

      main(){

      code for initialization

      __bis_SR_register(GIE);

      do{code for LED }

      while(1)}

      interrupt 1 (Port interrupt){

      some codes ....

      __bis_SR_register(GIE);  //enable GIE 1

      code 1 which will enter the ISR of interrupt 2

      __bis_SR_register(GIE);  //enable GIE 2

      code 2 which will enter the ISR of interrupt 2

      enable interrupt 1 or  __bis_SR_register(GIE); }

      interrupt 2 (timer interrupt){

      code

      __bic_SR_register_on_exit(GIE);}

      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    • mark sonnentag
      Posted by mark sonnentag
      on Apr 16 2012 09:17 AM
      Expert1890 points

      The port interrupt is an interrupt vector and the INT flag is only reset if you read the interrupt vector or clear the flag "manually".

      u8 portSource = P1IV;

      or P1IFG &= ~BITX



      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    • Jens-Michael Gross
      Posted by Jens-Michael Gross
      on Apr 16 2012 12:33 PM
      Guru140135 points

      Possessed
      My code is organized as follows: Basically the ISR of interrupt 1 will go to the ISR of interrupt 2.

      That's a very, very strange setup.

      Why is the code in interrupt 2 placed in an ISR at all? You cannot (!) call an ISR directly. Never. Because an ISR requires the status register placed on stack after the return address. This is mandatory for the RETI instruction at the end of an ISR to work.
      And you cannot do it in software. At least not without some rather complex hand-tweaked assembly code hack.

      You can, however, call a normal funciton from inside an ISR. It is not recommended, however, since it means a huge impact on execution time and stack space requirements for the ISR. And ISRs have to be short, ast interruptions of main, not separate parallel tasks. (use an RTOS with task switching for this kind of code)

      Nevertheless, your setup is not what nested interrupts are about. "Nested interrupts" means that you allow your current ISR to be interrupted by another interrupt. You do not call a different ISR, you allow a different ISR to be executed if a second (different!) interrupt occurs while you are still busy working on the current one. Which may or may not happen and is independent fron the first ISRs code.
      Somethimes this is necessary (e.g. if you have an ISR that does some work before done, and a timer ISR that needs to always be executed as fast as possible when a timer interrupt aoccurs), but you need to exactly know what you're doing, as the kind of problems that may arise from this are almost not debuggable. It's highly advanced expert stuff.

      _____________________________________
      Before posting bug reports or ask for help, do at least quick scan over this article. It applies to any kind of problem reporting. On any forum. And/or look here.
      If you cannot discuss your problem in the public, feel free to start a private conversation: click on my name and then 'start conversation'. But please do so only if you really cannot do it in a public thread, as I usually read all threads. And I prefer to answer where others can profit from it (or contribute to it) too.

      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    • old_cow_yellow
      Posted by old_cow_yellow
      on Apr 16 2012 13:14 PM
      Guru25715 points

      I am just guessing. You connected a push button to one of the pins to generate an interrupt. And you want to use a timer to avoid sensing the bounces of that button.

      If that is more or less what you intend to do, you do not need to “nest” your ISR. Instead, you could “chain” the ISR as follows:

      main()
      {
        ...
        set up pin interrupt;
        ...
        enable GIE;
        ... // do whatever
      }

      pin_interrupt_isr()
      {
        disable pin interrupt;
        ... // do whatever you need to do
        set up timer interrupt;
      }

      timer_interrupt_isr()
      {
        disable timer interrupt;
        enable pin interrupt; // again
      }

      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    • Possessed
      Posted by Possessed
      on Apr 17 2012 04:19 AM
      Intellectual680 points

      Jens-Michael Gross

      Possessed
      My code is organized as follows: Basically the ISR of interrupt 1 will go to the ISR of interrupt 2.

      That's a very, very strange setup.

      Why is the code in interrupt 2 placed in an ISR at all? You cannot (!) call an ISR directly. Never. Because an ISR requires the status register placed on stack after the return address. This is mandatory for the RETI instruction at the end of an ISR to work.
      And you cannot do it in software. At least not without some rather complex hand-tweaked assembly code hack.

      You can, however, call a normal funciton from inside an ISR. It is not recommended, however, since it means a huge impact on execution time and stack space requirements for the ISR. And ISRs have to be short, ast interruptions of main, not separate parallel tasks. (use an RTOS with task switching for this kind of code)

      Nevertheless, your setup is not what nested interrupts are about. "Nested interrupts" means that you allow your current ISR to be interrupted by another interrupt. You do not call a different ISR, you allow a different ISR to be executed if a second (different!) interrupt occurs while you are still busy working on the current one. Which may or may not happen and is independent fron the first ISRs code.
      Somethimes this is necessary (e.g. if you have an ISR that does some work before done, and a timer ISR that needs to always be executed as fast as possible when a timer interrupt aoccurs), but you need to exactly know what you're doing, as the kind of problems that may arise from this are almost not debuggable. It's highly advanced expert stuff.

      Thanks for your kind reply. Perhaps my description leads some misunderstanding, but what i want to do just you allow your current ISR to be interrupted by another interrupt, as you said. I also know that normally the interrupt should be kept as short as possible, however, in my case, i need to use buttom to send some signal, which need lots of coding, i can not shorten my code inside the interrupt 1.  My second timer interrupt is used to monitor the the behavior of interrupt 1, if the interrupt 1 stuck somewhere, the timer interrupt will be enabled.

      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    • Possessed
      Posted by Possessed
      on Apr 17 2012 04:56 AM
      Intellectual680 points

      Thanks for your code and your guess is very close :), I tried your code, and it works fine. The big difference between yours and mine is that you move the line enable pin_interrupt into the timer_interrupt_isr() from the end of pin_interrupt_isr(). Am i right that this is the reason my code is nested?

      Beside, GIE will be disable after interrupt has been triggered, but why enable pin_interrupt is still set when it jumps back from timer_interrupt_isr() to pin_interrupt_isr()?

      Thanks in advance

      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    • Jens-Michael Gross
      Posted by Jens-Michael Gross
      on Apr 17 2012 10:11 AM
      Guru140135 points

      Possessed
      in my case, i need to use buttom to send some signal, which need lots of coding, i can not shorten my code inside the interrupt 1

      In most cases, you can. The ISR can set a global flag and exit, and main detects the flag and does the time-consuming code. And of course can be interrupted by the second interrupt.

      The problem with nested interrupts is that your ISR can be interrupted by itself, so it mus tbe reentrant. And the cause for the interrupt must be cleard, or it will immediately interrupt itself. Causing a stack overflow faster than the eye can blink.

      However, if you disabled the interrupt that triggered the ISR, you may set GIE (enable itnerrupts) again inside the ISR and allow it to be interrupted by a different ISR.

      Note that intrruption of an already running ISR has nothing to do with interrupt priorities. Those are only important if two interrupts compete for being executed. E.g. if both are pending while interrupts are disabled (like during ISR execution woth whiel GIE is clear) and then you enable interrupts globally (set GIE or exit the current ISR).

      _____________________________________
      Before posting bug reports or ask for help, do at least quick scan over this article. It applies to any kind of problem reporting. On any forum. And/or look here.
      If you cannot discuss your problem in the public, feel free to start a private conversation: click on my name and then 'start conversation'. But please do so only if you really cannot do it in a public thread, as I usually read all threads. And I prefer to answer where others can profit from it (or contribute to it) too.

      Report Abuse
      • Reply
      You have posted to a forum that requires a moderator to approve posts before they are publicly available.
    TI E2E™ Community
    • Support Forums
    • Blogs
    • Videos
    • Groups
    • Site Support & Feedback
    • Settings
    TI E2E™ Community Groups
    • TI University Program
    • Make the Switch
    • Microcontroller Projects
    • Motor Drive & Control
    Other Communities
    • Deyisupport
    • Designsomething.org
    • beagleboard.org
    • TI on Element 14
    • TI on TechXchangeSM
    Other Technical & Support Resources
    • WEBENCH® Design Center
    • Product Information Centers
    • Technical Documents
    • TI Design Network
    • TI Technical Articles
    • TI Training

    All content and materials on this site are provided "as is". TI and its respective suppliers and providers of content make no representations about the suitability of these materials for any purpose and disclaim all warranties and conditions with regard to these materials, including but not limited to all implied warranties and conditions of merchantability, fitness for a particular purpose, title and non-infringement of any third party intellectual property right. TI and its respective suppliers and providers of content make no representations about the suitability of these materials for any purpose and disclaim all warranties and conditions with respect to these materials. No license, either express or implied, by estoppel or otherwise, is granted by TI. Use of the information on this site may require a license from a third party, or a license from TI.

    Content on this site may contain or be subject to specific guidelines or limitations on use. All postings and use of the content on this site are subject to the Terms of Use of the site; third parties using this content agree to abide by any limitations or guidelines and to comply with the Terms of Use of this site. TI, its suppliers and providers of content reserve the right to make corrections, deletions, modifications, enhancements, improvements and other changes to the content and materials, its products, programs and services at any time or to move or discontinue any content, products, programs, or services without notice.

    Follow Us Texas Instruments on Facebook Texas Instruments on Twitter Texas Instruments on LinkedIn Texas Instruments on Google+
    TI Worldwide | Contact Us | my.TI Login | Site Map | Corporate Citizenship | mobile m.ti.com (Mobile Version)

    TI is a global semiconductor design and manufacturing company. Innovate with 100,000+ analog ICs and
    embedded processors, along with software, tools and the industry’s largest sales/support staff.

    © Copyright 1995-2013 Texas Instruments Incorporated. All rights reserved.
    Trademarks | Privacy Policy | Terms of Use