Search code examples
assemblymacrospicmplab

create high-level IF ELSE ENDIF with macros in PIC16 assembly


I tried to simulate IF() .... ELIF .... ENDIF in assembly for PIC16F84, but it doesn't seem to work for more than one usage. I tried to use something like this in two places, but it gives some error that a label is duplicated. Shouldn't the parameter from the macro be replaced in the labels too? (name in true_name:)

_f macro name
  btfsc EQUAL,0
  goto true_name
  goto false_name
  true_name:
endm

_lse macro name
  goto next_name
  false_name:
endm

_ndif macro name
  goto next_name
  next_name:
endm

;; usage example
_f label1
  ...
_lse label1
  ...
_ndif 

Solution

  • I kinda solved this problem with MPLAB variables, here's an example for testing equality between a register and a literal:

    _f_equal_literal macro register,literal,name
        movlw literal
        subwf register,0
        btfss STATUS,2 ;bit indicating result is zero
        goto _false#v(name)
        endm
    
    _lse macro name
        goto _next#v(name)
    _false#v(name):
        endm
    
    _ndif macro name
    _next#v(name):
        endm
    

    Notice that I didn't use goto _true#v(name) and _true#v(name): label, you'll just have to figure if you need btfss or btfsc.

    You can have a single _lse and _ndif macro, and have multiple macros for _f statements.

    GJ's solution doesn't have a next label, so the true branch will execute the false branch.


    You need to define a variable for each if-else-endif construct. It might even useful if the variable name describes what the if-else-endif is used for.

    Example:

    variable testing_something=123

    _f_equal_literal some_register,some_value,testing_something
                    ...       
    
    _lse testing_something
                    ...        
    
    _ndif testing_something