This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Assembly code for making high to a port pin

Hi all,

I am using IAR compiler. In this i developing the code in C. But for one of my rquirement i want to make high for  port pin. So that i am trying the following line of codes in the *.C files,





asm("BIS.B #01, &0x0282u"); asm("BIS.B #0, &P1OUT"); #ifdef __IAR_SYSTEMS_ASM__ (BIS.B #02,&P1OUT) #endif BIS.B #02,&P1OUT


but nothing is working. Can nayone know how to use assembly code in *.c file in IAR compiler.

 

Thanks in advance.

 

 

  • You first need to switch the pin into output direction:

    BIS.B #1, &P1DIR
    BIS.B #1, &P1OUT

    However, if you're in C already (as the 'asm' instruction implies), you can simply do

    P1DIR|=BIT0;
    P1OUT|=BIT0;
  • Thanks Jens
    but already I have set the direction using the P1DIR register. But my aim call make the GPIO pin as high while the timer interrupt occurs. So that in the Timer ISR only I need the assembly language code for making GPIO pin as high. My intension is incept the assembly code in C file. For that purpose I went through lot of documents based on their input only I wrote the code, but for me it gives error or its not working.
  • Prakash Balagangatharan said:
    asm("BIS.B #01, &0x0282u");

    This should "work".

    Prakash Balagangatharan said:
    asm("BIS.B #0, &P1OUT");

    This probably will not "work", because the assembler invoked by the c-compiler probably does not know what P1OUT is.

    Prakash Balagangatharan said:
    BIS.B #02,&P1OUT

    This will not "work", because the assembler is not invoked yet and the c-compiler itself cannot handle this.

    Prakash Balagangatharan said:
    #ifdef __IAR_SYSTEMS_ASM__ (BIS.B #02,&P1OUT) #endif

    This will not "work" if  __IAR_SYSTEMS_ASM__ is actually defined. Otherwise this sequence will be ignored-in-effect and will cause no harm.

    ---

    I use "work" to mean that the IAR compiler/linker will not complain about the insertion and will blindly generate the corresponding machine instruction in the stream of object code.  

  • Jens-Michael Gross said:
    You first need to switch the pin into output direction:

    BIS.B #1, &P1DIR
    BIS.B #1, &P1OUT

    In order to "make the GPIO pin as high", one may also need to make that pin as GPIO pin. That pin might have been setup for something other than GPIO.

    Jens-Michael Gross said:
    However, if you're in C already (as the 'asm' instruction implies), you can simply do

    P1DIR|=BIT0;
    P1OUT|=BIT0;

    Agree. The original poster probably already tried this and failed to "make the GPIO pin as high". His attempt to use 'asm' doesn't help him. The problem is somewhere else.

  • Hi OCY,

    old_cow_yellow said:
    However, if you're in C already (as the 'asm' instruction implies), you can simply do

    P1DIR|=BIT0;

    P1OUT|=BIT0;

    You were right. My intension making a GPIO pin as high when timer interrupt is occured using assembly language. If I use the C code as above it will works.

    Also for me if use the following code

    old_cow_yellow said:
    Prakash Balagangatharan
    asm("BIS.B #01, &0x0282u");

    This should "work".

    I am not getting any error, but the output is not come. For conforming the output i connected on LED in the P9.1 pin, by seeing the LED blink status i can ensure this statement is not working. But this statement is in *.C file as previously i wrote. shall i need to change any compiler setting to run asm and C code in the *.C file.

    Any guidance pls.

    Thanks

  • Hi,

     I resolved this issue as writing the code as follows

            //! to set P1.0 pin
        asm("BIS.B #00000001b, &0x0202");
            //! to clear P1.0 pin
        asm("BIC.B #00000001b, &0x0202");

    Is it correct way? pls confirm.

    Thanks.

  • Prakash Balagangatharan said:
            //! to set P1.0 pin
        asm("BIS.B #00000001b, &0x0202");
            //! to clear P1.0 pin
        asm("BIC.B #00000001b, &0x0202");

    This is correct for MSP430FR5xxx, but for msp430G2xxx, you need to substitute the 0x0202 with 0x0021. (And 0x0282 is incorrect for both chips.)

    In cases like this, using  asm("...");  in the middle of c code is entirely unnecessary. You could have used  P1OUT |= BIT0;  and  P1OUT &= ~BIT0;. They would be correct for both MSP430FR5xx and MSP430G2xxx. And this has nothing to do with whether you are writing code for ISR or not.

  • You're right, sometimes, the pins are set to module usage. However, I only remember P2.6 and P2.7 for 2x family being set to secondary function (XT1IN and XT1OUT) by default. And maybe the PU (USB) on those few with USB controller. Everything else is configured for I/O by default.
  • Using assembly is only required if you need to have exact control over the code. However, a simple C instruction is no larger or smaller than their assembly version.
    P1OUT |= BIT0 gives exactly the same as OR.B #1,P1OUT. With the advantage that in C you can use the symbolic name and don't have to deal with the absolute addresses (which differ between different MSPs, making the assembly code non-portable - which was the main reason for your problem.)

**Attention** This is a public forum