5.4. Link Precompiled Object Files From Non-Ansys Fluent Sources

Ansys Fluent allows you to build a shared library for precompiled object files that are derived from external sources using the text user interface (TUI) option. For example, you can link precompiled objects derived from FORTRAN sources (.o objects from .f sources) to Ansys Fluent for use by a UDF. The following sections describe the procedures for doing this on a Windows system and a Linux system.

5.4.1. Windows Systems

  1. Follow the procedure described in Set Up the Directory Structure.

  2. Copy your precompiled object files (for example, myobject1.obj myobject2.obj) to all of the architecture/version folders you created in Step 1 (for example, win64/2d_node, win64/2d_host).


    Important:  The object files should be compiled using similar flags to those used by Ansys Fluent (for example, /c /Za).


  3. Edit the user_nt.udf files in each architecture/version folder.

5.4.2. Linux Systems

  1. Follow the procedure described in Set Up the Directory Structure.

  2. Copy your precompiled object files (for example, myobject1.o myobject2.o) to all of the architecture/version directories you created in Step 1 (for example, lnamd64/2d_node and lnamd64/2d_host).


    Important:  The object files should be compiled using similar flags to those used for Ansys Fluent. Common flags used by Ansys Fluent are: -KPIC, -O, and -ansi which often have equivalents such as -fpic, -O3, and -xansi.


  3. Using a text editor, edit the file user.udf in each version folder to set the following parameters: CSOURCES, HSOURCES, and the Ansys Fluent path.

    CSOURCES =

    Put the names of your UDF C files here. They will be calling the functions in the User Objects.

    HSOURCES =

    Put the names of your UDF H files here.

    FLUENT_INC =

    The path to your release directory.

    An excerpt from a sample user.udf is shown below:

    CSOURCES = udfexample.c
    HSOURCES = udfexample.h
    FLUENT_INC=/path/ansys_inc/v242/fluent
    

    In the previous example, path represents the directory where you installed Ansys Fluent.

  4. Using a text editor, edit the file Makefile in your src directory to set the USER_OBJECTS parameters:

    USER_OBJECTS =

    The precompiled object file(s) that you want to build a shared library for (for example, myobject1.o). Use a space delimiter to specify multiple object files (for example, myobject1.o myobject2.o).

    An excerpt from a sample Makefile is shown below:

    #-----------------------------------------------------------#
    # Makefile for user defined functions
    #
    #-----------------------------------------------------------# 
    # User modifiable section.
    #-----------------------------------------------------------# 
    include user.udf
    
    # Precompiled User Object files (for example .o files from .f sources)
    USER_OBJECTS= myobject1.o myobject2.o
      
    #-----------------------------------------------------------#
    # Build targets (do not modify below this line).
    #-----------------------------------------------------------#
      .
      .
      .
    
  5. In your library directory (for example, libudf), execute the Makefile by typing a command that begins with make and includes the architecture of the machine on which you will run Ansys Fluent, which you identified in a previous step (for example, lnamd64).

      make "FLUENT_ARCH=lnamd64"
    

    The following messages will be displayed:

    # linking to ../../src/Makefile in lnamd64/2d_node
    # building library in lnamd64/2d_node
    # linking to ../../src/Makefile in lnamd64/2d_host
    # building library in lnamd64/2d_host
    

5.4.3. Example: Link Precompiled Objects to Ansys Fluent

The following example demonstrates the linking of a FORTRAN object file test.o to Ansys Fluent, for use in a UDF named test_use.c. This particular UDF is not a practical application but has rather been designed to demonstrate the functionality. It uses data from a FORTRAN-derived object file to display parameters that are passed to the C function named fort_test. This on-demand UDF, when executed from the User-Defined Function Hooks dialog box, displays the values of the FORTRAN parameters and the common block and common complex numbers that are computed by the UDF, using the FORTRAN parameters.


Important:  Note that the names of the functions and data structures have been changed from the capital form in FORTRAN (for example, ADDAB is changed to addab_). This name "mangling" is done by the compiler and is strongly system-dependent. Note also that functions returning complex numbers have different forms on different machine types, since C can return only single values and not structures. Consult your system and compiler manuals for details.


  1. In the first step of this example, a FORTRAN source file named test.f is compiled and the resulting object file (test.o) is placed in the shared library folder for the lnamd64/2d_node version.

      libudf/lnamd64/2d_node
    

    The source listing for test.f is shown below.

      C FORTRAN function
      C test.f
      C
      C compile to .o file using:
      C f77 -KPIC -n32 -O -c test.f (irix6 & suns)
    
           REAL*8 FUNCTION ADDAB(A,B,C)
    
           REAL A
           REAL*8 B
           REAL*8 YCOM
           COMPLEX ZCOM
           INTEGER C
           INTEGER SIZE
    
           COMMON //SIZE,ARRAY(10)
           COMMON /TSTCOM/ICOM,XCOM,YCOM,ZCOM
    
           ICOM=C
           XCOM=A
           YCOM=B
           ZCOM=CMPLX(A,REAL(B))
    
           SIZE=10
           DO 100 I=1,SIZE
          ARRAY(I)=I*A
      100 CONTINUE
    
           ADDAB=(A*C)*B
           END
    
           COMPLEX FUNCTION CCMPLX(A,B)
           REAL A,B    
    
          CCMPLX=CMPLX(A,B)
           END
      
    
  2. The UDF C source file named test_use.c is placed in the source folder for the lnamd64/2d_node version:

      src/lnamd64/2d_node
      
    

    The source listing for test_use.c is as follows.

      #include "udf.h"
      #if defined(_WIN32)
         /* Visual Fortran makes uppercase functions provide lowercase
            mapping to be compatible with Linux code */
      # define addab_ ADDAB
      #endif
    
      typedef struct {float r,i;} Complex;
      typedef struct {double r,i;} DComplex;
      typedef struct {long double r,i;} QComplex; /* FORTRAN QUAD
                       PRECISION */
    
      /* FORTRAN FUNCTION */
      extern double addab_(float *a,double *b,int *c);
    
     /* NOTE on SUN machines that FORTRAN functions returning a complex
      number are actually implemented as void but with an extra
      initial argument.*/
    
      extern void ccmplx_(Complex *z,float *a,float *b);
      extern void qcmplx_(QComplex *z,float *a,float *b);
    
      /* BLANK COMMON BLOCK */
      extern struct
      {
        int size;
        float array[10];
      } _BLNK__;
    
      /* FORTRAN NAMED COMMON BLOCK */
      extern struct
      {
        int int_c;
        float float_a;
        double double_b;
        float cmplx_r;
        float cmplx_i;
      } tstcom_;
    
      DEFINE_ON_DEMAND(fort_test)
      {
        float a=3.0,float_b;
        double d,b=1.5;
        int i,c=2;
        Complex z;
        QComplex qz;
    
        d = addab_(&a,&b,&c);
        Message("\n\nFortran code gives (%f * %d) * %f = %f\n",a,c,b,d);
        Message("Common Block TSTCOM set to: %g
               tstcom_.float_a,tstcom_.double_b,tstcom_.int_c);
        Message("Common Complex Number is (%f + %fj)\n",
               tstcom_.cmplx_r,tstcom_.cmplx_i);
        Message("BLANK Common Block has an array of size
                 \n",_BLNK__.size);
        for (i=0; i <_BLNK__.size ; i++)
          {
             Message("array[%d] = %g\n",i,_BLNK__.array[i]);
          }
        float_b=(float)b;
        ccmplx_(&z,&a,&float_b);
        Message("Function CCMPLX returns Complex Number:
                   (%g + %gj)\n",z.r,z.i);
        qcmplx_(&qz,&a,&float_b);
        Message("Function QCMPLX returns Complex Number:
                   (%g + %gj)\n",qz.r,qz.i);
      }
    
  3. The user.udf is then modified to specify the UDF C source file (test_use.c) as shown below.

    CSOURCES = test_use.c
    HSOURCES = 
    FLUENT_INC=/path/ansys_inc/v242/fluent
    

    Note that in the previous example, path represents the directory where you installed Ansys Fluent.

  4. The Makefile is then modified to specify the external object file (test.o) as shown below.

    #-----------------------------------------------------------# 
    # User modifiable section.
    #-----------------------------------------------------------# 
    include user.udf
    
    # Precompiled User Object files (for example .o files from .f sources)
    USER_OBJECTS= test.o
    
  5. Finally, the Makefile is executed by issuing the following command in the libudf folder:

      make "FLUENT_ARCH=lnamd64"