|
技术交流 | 电路欣赏 | 工控天地 | 数字广电 | 通信技术 | 电源技术 | 测控之家 | EMC技术 | ARM技术 | EDA技术 | PCB技术 | 嵌入式系统 驱动编程 | 集成电路 | 器件替换 | 模拟技术 | 新手园地 | 单 片 机 | DSP技术 | MCU技术 | IC 设计 | IC 产业 | CAN-bus/DeviceNe |
请问在ATMANAVR中,进中断后是自动保护现场吗? |
作者:liu_xw217 栏目:单片机 |
我还用加CLI()和SEI()吗! 多谢谢 |
2楼: | >>参与讨论 |
作者: sailz 于 2005/8/12 16:56:00 发布:
我的看法 默认方式是关闭了中断, 就是说中断无法被打断. 自动保护现场,恩. |
3楼: | >>参与讨论 |
作者: testcode 于 2005/8/13 5:43:00 发布:
应该吧 GCCAVR中,中断后是自动保护现场 |
4楼: | >>参与讨论 |
作者: 勇敢的心 于 2005/8/13 7:46:00 发布:
atmanavr的编译器就是gcc 注意gcc中的SIGNAL和INTERRUPT的区别 |
5楼: | >>参与讨论 |
作者: zlei 于 2005/8/13 8:49:00 发布:
SIGNAL和INTERRUPT的区别 SIGNAL和INTERRUPT的自动保护现场应该没有区别吧!是否自动保护现场和关键字"naked"有关 SIGNAL: Introduces an interrupt handler function that runs with GLOBAL interrupts initially disabled. INTERRUPT: Introduces an interrupt handler function that runs with GLOBAL interrupts initially enabled. This allows interrupt handlers to be interrupted. 中断函数都会自动保护现场的,两者主要区别就是在ISR中,INTERRUPT多了一条sei语句,这样就允许ISR被其他中断所中断。 下面是测试程序 //! Interrupt handler for tcnt0 overflow interrupt SIGNAL(SIG_OVERFLOW0) { Timer0Reg0++; // increment low-order counter // increment pause counter TimerPauseReg++; // if a user function is defined, execute it too if(TimerIntFunc[TIMER0OVERFLOW_INT]) TimerIntFunc[TIMER0OVERFLOW_INT](); } 汇编代码如下: 633 .LFE20: 635 .GLOBAL __vector_9 637 __vector_9: 638 .LFB21: 639 .LM70: 640 /* prologue: frame size=0 */ 641 02b0 1F92 PUSH __zero_reg__ 642 02b2 0F92 PUSH __tmp_reg__ 643 02b4 0FB6 in __tmp_reg__,__SREG__ 644 02b6 0F92 PUSH __tmp_reg__ 645 02b8 1124 clr __zero_reg__ 646 02BA 2F93 PUSH r18 647 02bc 3F93 PUSH r19 648 02be 4F93 PUSH r20 649 02c0 5F93 PUSH r21 650 02c2 6F93 PUSH r22 651 02c4 7F93 PUSH r23 652 02c6 8F93 PUSH r24 653 02c8 9F93 PUSH r25 654 02ca AF93 PUSH r26 655 02cc BF93 PUSH r27 656 02ce EF93 PUSH r30 657 02d0 FF93 PUSH r31 658 /* prologue end (size=17) */ 659 .LM71: 660 02d2 8091 0000 lds r24,Timer0Reg0 661 02d6 9091 0000 lds r25,(Timer0Reg0)+1 662 02da A091 0000 lds r26,(Timer0Reg0)+2 663 02de B091 0000 lds r27,(Timer0Reg0)+3 664 02e2 0196 adiw r24,1 665 02e4 A11D adc r26,__zero_reg__ 666 02e6 B11D adc r27,__zero_reg__ 667 02e8 8093 0000 sts Timer0Reg0,r24 668 02ec 9093 0000 sts (Timer0Reg0)+1,r25 669 02f0 A093 0000 sts (Timer0Reg0)+2,r26 670 02f4 B093 0000 sts (Timer0Reg0)+3,r27 671 .LM72: 672 02f8 8091 0000 lds r24,TimerPauseReg 673 02fc 9091 0000 lds r25,(TimerPauseReg)+1 674 0300 A091 0000 lds r26,(TimerPauseReg)+2 675 0304 B091 0000 lds r27,(TimerPauseReg)+3 676 0308 0196 adiw r24,1 677 030A A11D adc r26,__zero_reg__ 678 030c B11D adc r27,__zero_reg__ 679 030e 8093 0000 sts TimerPauseReg,r24 680 0312 9093 0000 sts (TimerPauseReg)+1,r25 681 0316 A093 0000 sts (TimerPauseReg)+2,r26 682 031a B093 0000 sts (TimerPauseReg)+3,r27 683 .LM73: 684 031e 8091 0000 lds r24,TimerIntFunc 685 0322 9091 0000 lds r25,(TimerIntFunc)+1 686 0326 892B or r24,r25 687 0328 29F0 breq .L44 688 .LM74: 689 032A E091 0000 lds r30,TimerIntFunc 690 032e F091 0000 lds r31,(TimerIntFunc)+1 691 0332 0995 icall 692 .L44: 693 /* epilogue: frame size=0 */ 694 0334 FF91 pop |
6楼: | >>参与讨论 |
作者: zlei 于 2005/8/13 8:57:00 发布:
如果不想保护现场,看看EMPTY_INTERRUPT就知道如何实现了 #ifdef __cplusplus #define EMPTY_INTERRUPT(signame) \ extern "C" void signame(void); \ void signame (void) __attribute__ ((naked)); \ void signame (void) { __asm__ __volatile__ ("reti" ::); } #else #define EMPTY_INTERRUPT(signame) \ void signame (void) __attribute__ ((naked)); \ void signame (void) { __asm__ __volatile__ ("reti" ::); } #endif 同样的测试代码 |
7楼: | >>参与讨论 |
作者: hotpower 于 2005/8/13 10:30:00 发布:
当然也可不保护就是危险些 |
8楼: | >>参与讨论 |
作者: sailz 于 2005/8/15 10:38:00 发布:
我又学到东西了 INTERRUPT和SIGNAL的区别. 在atmanavr的帮助文件里有简略介绍. |
|
|
免费注册为维库电子开发网会员,参与电子工程师社区讨论,点此进入 |
Copyright © 1998-2006 www.dzsc.com 浙ICP证030469号 |