Hello everybody!
If you please could help with this problem. I am writing a timer32 interrupt handler and try to use inline assembly.
I wrote the simplest code, which triggers a port pin high and then low at the minimal possible time interval. One instruction turns it on, the next one - off. The code is very simple.
The problem is when I used a debugger (msp432 launchpad), I saw that the compiler actually had changed my code!!! I saw that it stored the values to registers, different from what I wrote AND the worst thing was, the compiler thought that writing #1 to the port ( STRB r1, [r0] ) was totally redundant, since the next instruction writes a zero there, so the compiler simply dumped that instruction. So it changes my assembly code! Could please anyone tell me how to force the compiler to stop playing a smart ass and to implement my inline assembly code exactly the way it is written and do all the instructions I write? Thank you!!!
void T32_INT1_IRQHandler(void){ __asm{ MOV R0, #0x40004c03 //DIO port address MOV r1, #1 MOV r2, #0 STRB r1, [r0] //Port pin High STRB r2, [r0] //Port pin Low } }
Why use inline assembly?
Why not just write it in "proper" assembler?
Hi Andy. I have thought about it already. Just the thing is, quick switching the pin is the only place I need such a quick implementation. Writing the whole function in asm would be real ass-pain.
have you actually tried doing it in 'C'?
Stanislav Ossovsky said:Writing the whole function in asm would be real ass-pain.
And inline assembler is pure plain sailing, eh?!
You don't have to write it all yourself from scratch - do it in 'C', and take what the compiler does ...
Writing a critical part in assembler would be good. What happens in C is the compiler switches the output pin on, then writes zero to a register and then writes it to the output. So it is much longer. What I wanted was to write one and zero in two registers and then write to the output in a row, without spending time in between for loading a zero into a register. This is a critical part. The switching operation must be the quickest possible. So I guess there is no way to do so in inline asm?
Why bother fighting with the arcane details of inline assembler?
If it needs to be in assembler, then do it in assembler.
www.avrfreaks.net/.../2800826
https://www.avrfreaks.net/comment/2839056#comment-2839056
Yeah. I guess it is true. I thought just sprinkling two-three instructions into a C source would be easy enough, which turns out not to be the case. So I will write the whole thing in asm... After all, it will give me a nice stimulus to keep the interrupt routine as short as possible :)
Thanks!
I've not tried it in uvision, but it's common to need volatile blocks to tell the compiler to not fiddle with inline assembler. Without this it will go though the optimizer. Does this:__asm volatile { ... }
__asm volatile { ... }
... work any better?
HTH, Pete
Hello Pete! I have thought about it also, alas, to no avail. The instruction was still missing. But the funny thing was that when I finally wrote the code in pure asm and the instruction was finally implemented, there was no visible difference in pin jerking speed, whether the on and off instructions went in a row, or had a MOV in between! Perhaps the internal guts of the MSP432 are wired in such a way that it can move some number to a register while storing another number somewhere else? Or perhaps my oscilloscope bullsh*ts.