Menu

#774 Out/in instructions

None
open
nobody
None
5
2022-03-07
2022-02-27
No

The z80 has In/out instructions that should be possible to inline with standard c sources in order to develop efficient code.
the __asm command is of reduced use when the port or the value have to be taken by the c environment
Other compilers use special instructions/functions that the compiler replaces by out/in outir/inir
could this be added to sdcc ?
I was trying to implement a macro using #define and ___asm___ but apparently there is no way to pass define parameters into asm code

Discussion

  • Philipp Klaus Krause

    You can place variables in the named address space __sfr (see section 3.5.2 in the manual). SDCC will use out/in to access them.

     

    Last edit: Philipp Klaus Krause 2022-02-28
  • Ragozini Arturo

    Ragozini Arturo - 2022-02-28

    Thanks ! Does it support also outir and inir?

     
    • Philipp Klaus Krause

      Currently, the code generation only uses in and out, no ini, ind, inir, indr, outi, outd, outir or outdr. It does use both variants of in and out, though.

       
  • Ragozini Arturo

    Ragozini Arturo - 2022-02-28

    I see also the the sfr solution cannot have the port number as a variable...

    This statement
    __sfr __at 0x98 DataPort;
    does not accept a port number from a C variable

     
    • Philipp Klaus Krause

      The correct way to handle this would be to have a pointer to I/O-space (so you could cast your variable to that pointer type). Unfortunately, that currently doesn't work:

      https://sourceforge.net/p/sdcc/bugs/3160/

      When that issue gets fixed, outi / outir / ini / inir might then be used to make the access more efficient.

       

      Last edit: Philipp Klaus Krause 2022-03-01
  • Ragozini Arturo

    Ragozini Arturo - 2022-03-01

    Would it be possible, in general, to allow inline functions where the pre-compiler is able to replace strings or other parameters in the ASM statement?
    I was trying something like this:

    #define  outir(port,count,addr) __asm__("ld c,#port");__asm__("ld   b,#count");__asm__("ld  hl,#addr");__asm__("outir");
    

    The macro fails, as the pre-compiler is not able to replace strings within the __asm__ instructions. I know that the above macro would give errors for non constants parameters, but it would simplify some loops I have now and the overhead of a function call would almost double the CPU cost of the action.

    This is another a possible example: I need to access to banked data and I need to use the bank number. In asm it goes like this:

        // access paged data 
        __asm
        ld  a,#b_DataLevelMap
        ld (#0x9000),a                  ; memory mapper register
        ld (#_curr_bank),a
        __endasm;   
    

    where DataLevelMap is a label in a different bank. I would like to define a small macro where the string "DataLevelMap" can be replaced with any other banked label.
    I would define a macro like this:

    #define  Pageswap(label) __asm__("ld a,#b_label");__asm__("ld (#0x9000),a");__asm__("ld (#_curr_bank),a");
    

    The above macro fails, as the pre-compiler is not able to replace strings within the __asm__ instructions. The overhead of a function call would almost double the CPU cost of the action.

    Are there workarounds?

     

    Last edit: Maarten Brock 2022-03-07
    • Sebastian Riedel

      Maybe use assembly macros? That will definitely ruin jr

      void nofunction() __naked{
      __asm
      .macro moutir port,count,addr
      ld c,#port
      ld b,#count
      ld hl,#addr
      outir
      .endm
      __endasm;
      }
      

      called as

      __asm
      moutir 0 0 0
      __endasm;
      

      Or put them in an assembly file and include it in a header.

      void nofunction() __naked{
      __asm
      .include "mymacros.inc"
      __endasm;
      }
      

      I don’t know if there is a better solution, I usually don’t mix assembly and C.

       
  • Maarten Brock

    Maarten Brock - 2022-03-07
    • Description has changed:

    Diff:

    --- old
    +++ new
    @@ -1,5 +1,5 @@
     The z80 has In/out instructions that should be possible to inline with standard c sources  in order to develop efficient code. 
    -the __asm command is of reduced use when the port or the value have to be taken by the c environment 
    +the \_\_asm command is of reduced use when the port or the value have to be taken by the c environment 
     Other compilers use special instructions/functions that the compiler replaces by out/in outir/inir 
     could this be added to sdcc ?
    -I was trying to implement a macro using #define and ___asm___ but apparently there is no way to pass define parameters into asm code
    +I was trying to implement a macro using #define and \_\_\_asm\_\_\_ but apparently there is no way to pass define parameters into asm code
    
    • Group: -->
     

Log in to post a comment.

MongoDB Logo MongoDB