Author Topic: Fortran loc function: can it be compatibly reproduced with NASM?  (Read 269 times)

Offline mjrice

  • Jr. Member
  • *
  • Posts: 17
I ask the subject line question because, as I understand it, function parameters are located in different registers depending upon whether they are ints or floats. How would a function, maddr, know where to get its parameter, since it must return the machine addresses of both ints and floats? And Fortran passes by reference, seemingly a pointer to a pointer, i.e., pointer to a machine address. Is there some flag to determine this?

Offline azagaros

  • Jr. Member
  • *
  • Posts: 8
Re: Fortran loc function: can it be compatibly reproduced with NASM?
« Reply #1 on: June 06, 2018, 06:48:13 PM »
Which OS, and which bit level? Pointers are considered integers, return vectors are rax for the first one

Linux/Unix and win64 have abi to follow for the pattern of the registers and they are both different.
32 bit follow a c based convention.

in the 64 bit Linux /Unix function call, rax is the count of floats put in xmm0 to xmm7.  The other arguments have a specific map.
http://refspecs.linuxbase.org/elf/x86_64-abi-0.21.pdf pg 19 has other description.

Windows I do not have any information. 

You sound like you are loading FORTRAN code some where and calling the function from assembly. That would follow the calling convention of the OS.
« Last Edit: June 06, 2018, 06:53:04 PM by azagaros »

Offline mjrice

  • Jr. Member
  • *
  • Posts: 17
Re: Fortran loc function: can it be compatibly reproduced with NASM?
« Reply #2 on: June 06, 2018, 07:28:41 PM »
Looks like this is going to be a short thread.

I haven't programmed any fortran or nasm in at least ten years and coming back to it after that long and from 32-bit to 64-bit has been a bit overwhelming. But I persisted. The problem I was having was caused by my accidentally misdeclaring the maddr function in my fortran code as real, making me think the maddr function was at fault. See below for  the code for the maddr function plus two fortran examples of its usage compared with fortran's loc function for both an x86-64 integer and an x86-64 real.  If you see any slipups, please let me know.

Michael

Nasm machine address function:

global maddr_

section .text  ;return the (64-bit integer) machine address of a variable

maddr_:
  push rbp
  mov  rax, rdi
  pop  rbp
  ret

=======Tested with loc in gfortran=======

Machine address of x86-64 integer variable

      integer, external :: maddr
      integer i,j
      integer k
      k=33
      i=loc(k)
      j=maddr(k)
      write(*,*) i,j
      end

nasm -f elf64 maddr.asm -o maddr.o && gfortran maddrtest.f90 maddr.o && ./a.out
  2099635748  2099635748



Machine address of x86-64 real variable

      integer, external :: maddr
      integer i,j
      real c
      c=17.5
      i=loc(c)
      j=maddr(c)
      write(*,*) i,j
      end

nasm -f elf64 maddr.asm -o maddr.o && gfortran maddrtest.f90 maddr.o && ./a.out
  1430344396  1430344396

Offline azagaros

  • Jr. Member
  • *
  • Posts: 8
Re: Fortran loc function: can it be compatibly reproduced with NASM?
« Reply #3 on: June 06, 2018, 08:03:34 PM »
What I think you want in that assembly code: You have stated that is returning address to a variable?
Code: [Select]
;mov rax, rdi
;mov xmm0, [rax] ;to put the value some where
;or
mov xmm0, [rdi] ; Where floats are put
mov rax, 1          ; the count of reals in xmm0 to xmm7, possible count of 8
return
This would return the value and not the address.

Offline mjrice

  • Jr. Member
  • *
  • Posts: 17
Re: Fortran loc function: can it be compatibly reproduced with NASM?
« Reply #4 on: June 12, 2018, 03:51:46 AM »
Sorry to be so tardy with a reply. I don't recall seeing your post in my email, so I may have accidentally deleted it.

I found that if I run the code I posted multiple times I can get identical negative addresses for both the loc function and the maddr function.

Also, if I just code

write(*,*) loc(k), maddr(k)

instead of putting the returned addresses in variables i and j to be written, the two resulting addresses no longer match.

Going to have to do some digging.