# TARGET VARIANT DISPATCH

Offloading Compiler Directive: Conditionally calls a procedure offload variant if the device is free; otherwise, executes the procedure on the host. This directive is an Intel® language extension. This feature is only available for ifx.

!$OMP TARGET VARIANT DISPATCH [clause[[,] clause]]

CALL subr (...)

-or-

!$OMP TARGET VARIANT DISPATCH [clause[[,] clause]]

var = func (...)

clause | Is one or more of the following: DEVICE (integer-expression) NOWAIT SUBDEVICE ([integer-constant ,] integer-expression [ : integer-expression [ : integer-expression] ] ) USE_DEVICE_PTR (ptr-list)

This directive causes the compiler to emit conditional dispatch code around the associated subroutine or function call that follows the directive. If the default device is available, the variant version is called. If DEVICE (integer-expression) is specified, the variant is called only if device integer-expression is available. If SUBDEVICE is specified, the variant is called only if the specified tiles or compute slices are available. If both DEVICE(n) and SUBDEVICE are specified, the variant is called only if the specified tiles or compute slices are available on device n. Otherwise, the base version of the procedure is called on the host.

The NOWAIT clause, if present, indicates calls to the procedure can occur asynchronously. If NOWAIT is not present, calls occur synchronously.

The name of the subroutine or function associated with the TARGET VARIANT DISPATCH directive must have appeared in a DECLARE VARIANT directive in the specification part of the calling scope. The interface of the variant procedure must be accessible in the base procedure where the DECLARE VARIANT directive appears.

The procedure called in the statement following the TARGET VARIANT DISPATCH directive must have an explicit interface accessible at the call site.

The variant version of the procedure has an identical interface as the base function, except the variant has an additional argument in the last position which is of type C_PTR. This final argument does not appear in the TARGET VARIANT DISPATCH call, rather, the compiler inserts it if the variant is called.

## Example

    MODULE vecadd
      INTEGER,PARAMETER  :: n = 1024
    CONTAINS
      FUNCTION vecadd_gpu_offload (ptr)RESULT (res)
        USE,INTRINSIC :: ISO_C_BINDING, ONLY : c_ptr
        !$DEC ATTRIBUTES NOINLINE :: vecadd_gpu_offload
        REAL              :: res
        REAL,DIMENSION(n) :: a, b
        INTEGER           :: k

        res   = a(k) + b(k)
        PRINT *, "GPU version of vecadd called"
      END FUNCTION vecadd_gpu_offload

      FUNCTION vecadd_base ()RESULT (res)
        !$DEC ATTRIBUTES NOINLINE :: vecadd_base
        !$OMP DECLARE VARIANT (vecadd_gpu_offload) match(construct={target variant dispatch}&
        !$OMP&                ,device = {arch (gen)} )
        REAL              :: res
        REAL,DIMENSION(n) :: a, b
        INTEGER           :: k

        Res   = a(k) + b(k)
        PRINT *, "CPU version of vecadd called"
      END FUNCTION vecadd_base
    END MODULE vecadd

    PROGRAM main
      USE vecadd
      REAL    :: result = 0.0

      !$OMP TARGET VARIANT DISPATCH
      result = vecadd_base ()
      !$OMP END TARGET VARIANT DISPATCH

      IF (result == 1048576.0) then
        PRINT *, "PASSED: correct results"
      ELSE
        PRINT *, "FAILED: incorrect results"
      ENDIF
    END PROGRAM

Parent topic: T to Z

## See Also

OpenMP Fortran Compiler Directives
Syntax Rules for Compiler Directives
DECLARE VARIANT