simulavr-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Simulavr-devel] irq handling is broken in simulavr


From: Knut Schwichtenberg
Subject: Re: [Simulavr-devel] irq handling is broken in simulavr
Date: Fri, 25 Jan 2013 16:38:04 +0100
User-agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130105 Thunderbird/17.0.2

Hi,

please have a look to the following part I copied from the Mega32A CPU description:

6.7.1 Interrupt Response Time
The interrupt execution response for all the enabled AVR interrupts is four clock cycles mini- mum. After four clock cycles the program vector address for the actual interrupt handling routine is executed. During this four clock cycle period, the Program Counter is pushed onto the Stack. The vector is normally a jump to the interrupt routine, and this jump takes three clock cycles. If an interrupt occurs during execution of a multi-cycle instruction, this instruction is completed before the interrupt is served. If an interrupt occurs when the MCU is in sleep mode, the interrupt execution response time is increased by four clock cycles. This increase comes in addition to the
start-up time from the selected sleep mode.

A return from an interrupt handling routine takes four clock cycles. During these four clock cycles, the Program Counter (two bytes) is popped back from the Stack, the Stack Pointer is
incremented by two, and the I-bit in SREG is set.

Also please have a look to avr-libc. If they change the SP and reload it the sequence of assembler instructions take the delay into account.

Cheers,
Knut

Am 25.01.2013 13:21, schrieb Klaus Rudolph:
Hi Petr,

back again from my little lab:

I executed the follwing code on a atmega32 (real device on stk500 )


   1 #include <avr/io.h>
   2 #include <avr/interrupt.h>
   3
   4 #undef _SFR_IO8
   5 #define _SFR_IO8(x) (x)
   6 #undef _SFR_IO16
   7 #define _SFR_IO16(x) (x)
   8
   9
  10 .global main
  11 main:
  12     ldi r16, 0xff          ; all pins output
  13     out DDRB, r16          ; all pins output
  14     ldi r16, 0x01          ; one pin on
  15     out PORTB, r16         ; initial only 1 pin
  16
  17     ldi r17, 0x55
  18     sei                    ; enable interrupts
  19     ldi r16, (1<<UDRIE)    ; lets generate a usart data register
empty irq
  20     out UCSRB, r16         ; which should exactly now take place BUT ->
  21     out PORTB, r17         ; if this instruction is executed, we
will see 0x55 on portb!
  22
  23 ; normaly never execute any of the following instructions, we caught
into irq handler
  24     ldi r17, 0x0f;         ; if irq will not be executed or comes back
  25     out PORTB, r17         ; we see 0x0f on port b which should not
happen
  26     ret                    ; this will result in going back to
ctors_end -> exit
  27
  28 .global USART_UDRE_vect
  29 USART_UDRE_vect:
  30    rjmp USART_UDRE_vect
  31
  32 .global stopsim
  33 stopsim:
  34     reti
  35

The result is:
PORTB shows 0x55 pattern!

That is exactly what I expect but seems first unbelievable :-)

What we have: After raising the irq on line 20 we have one more
instruction executed which writes the port value to the 0x55 pattern.
The reason for this is not manipulating the I flag in the instruction
before. So it looks that every pending interrupt will execute a single
instruction on normal program flow before entering the irq handler.

If there is no coding error or an interpretation issue I think my patch
is exactly doing what the real device do in respect of the instruction
following the pending irq.

What I could not check is the timing behavior for the wait states of the
next instructions. Maybe it is possible to setup a timer and read back
the counter after execution or some other idea. But I think that is not
so important in the moment (for me).

I will do some more testcases on real device and on simulavr and make
unit tests for them.

Please tell me if you could find any mistakes!

Regards
  Klaus



_______________________________________________
Simulavr-devel mailing list
address@hidden
https://lists.nongnu.org/mailman/listinfo/simulavr-devel




reply via email to

[Prev in Thread] Current Thread [Next in Thread]