Fortran pointer as an argument to interface procedure
- by icarusthecow
Im trying to use interfaces to call different subroutines with different types, however, it doesnt seem to work when i use the pointer attribute. for example, take this sample code
 MODULE ptr_types
     TYPE, abstract :: parent
        INTEGER :: q
     END TYPE
     TYPE, extends(parent) :: child
        INTEGER :: m
     END TYPE
     INTERFACE ptr_interface
        MODULE PROCEDURE do_something
     END INTERFACE
     CONTAINS
        SUBROUTINE do_something(atype)
           CLASS(parent), POINTER :: atype
           ! code determines that this allocation is correct from input
           ALLOCATE(child::atype)
           WRITE (*,*) atype%q
        END SUBROUTINE
  END MODULE
  PROGRAM testpass
     USE ptr_types
     CLASS(child), POINTER :: ctype
     CALL ptr_interface(ctype)
  END PROGRAM
This gives error 
Error: There is no specific subroutine for the generic 'ptr_interface' at (1)
however if i remove the pointer attribute in the subroutine it compiles fine. Now, normally this wouldnt be a problem, but for my use case i need to be able to treat that argument as a pointer, mainly so i can allocate it if necessary.
Any suggestions? Mind you I'm new to fortran so I may have missed something
edit: forgot to put the allocation in the parents subroutine, the initial input is unallocated
EDIT 2
this is my second attempt, with caller side casting
    MODULE ptr_types
       TYPE, abstract :: parent
        INTEGER :: q
        END TYPE
        TYPE, extends(parent) :: child
          INTEGER :: m
        END TYPE
        TYPE, extends(parent) :: second
           INTEGER :: meow
        END TYPE
        CONTAINS
           SUBROUTINE do_something(this, type_num)
              CLASS(parent), POINTER :: this
              INTEGER type_num
              IF (type_num == 0) THEN
                 ALLOCATE (child::this)
              ELSE IF (type_num == 1) THEN
                 ALLOCATE (second::this)
              ENDIF
           END SUBROUTINE
     END MODULE
     PROGRAM testpass
        USE ptr_types
        CLASS(child), POINTER :: ctype
        SELECT TYPE(ctype)
        CLASS is (parent)
           CALL do_something(ctype, 0)
        END SELECT
        WRITE (*,*) ctype%q
     END PROGRAM
however this still fails. in the select statement it complains that parent must extend child. Im sure this is due to restrictions when dealing with the pointer attribute, for type safety, however, im looking for a way to convert a pointer into its parent type for generic allocation. Rather than have to write separate allocation functions for every type and hope they dont collide in an interface or something.
hopefully this example will illustrate a little more clearly what im trying to achieve, if you know a better way let me know