Intel® Fortran Compiler
Build applications that can scale for the future with optimized code designed for Intel® Xeon® and compatible processors.
28381 Discussions

Abaqus 6.14 fortran subroutine dllimport not working

Alessandro_N_
Beginner
1,862 Views

Hi all, 

I am new to this forum. In the past I was able to call fortran subroutine written by myself from an Abaqus 6.11 user subroutine using the commands cDEC$ attributes dllexport and dllimport. However, now I am trying to do the same thing in Abaqus 6.14 and I get the following error during the linking:

vuamp.obj : error LNK2019: unresolved external symbol <subroutine_name> referenced in function vuamp

It looks like Abaqus is not able to find the .dll.

These are the steps I followed:

1) write my personal subroutine with at the top: cDEC$ attributes dllexport::name

2) create .dll and .obj with command: ifort /dll name.f

3) create .lib with command: lib /out:name.lib name.obj

4) copy .lib file in a folder I point to in the abaqus_v6.env file: add to link_sl the path to the .lib

link_sl=['LINK',
         '/nologo', '/NOENTRY', '/INCREMENTAL:NO', '/subsystem:console', '/machine:AMD64',
         '/NODEFAULTLIB:LIBC.LIB', '/NODEFAULTLIB:LIBCMT.LIB',
         '/DEFAULTLIB:OLDNAMES.LIB', '/DEFAULTLIB:LIBIFCOREMD.LIB', '/DEFAULTLIB:LIBIFPORTMD.LIB', '/DEFAULTLIB:LIBMMD.LIB',
         '/DEFAULTLIB:kernel32.lib', '/DEFAULTLIB:user32.lib', '/DEFAULTLIB:advapi32.lib',
         '/FIXED:NO', '/dll',
         #'/debug', # <-- Debugging
         '/def:%E', '/out:%U', '%F', '%A', '%L', '%B', 
         'oldnames.lib', 'user32.lib', 'ws2_32.lib', 'netapi32.lib', 'advapi32.lib',
         'C:\\lib\\6142\\name.lib']

5) Copy .dll file to C:\SIMULIA\Abaqus\6.14-2\code\bin

6) write cDEC$ attributes dllimport::name at the top of the abaqus fortran subroutine file (e.g. vuamp.f)

This same process worked for Abaqus 6.11. The only difference was that the folder where I put the .dll was C:\SIMULIA\Abaqus\6.11-3\exec.

Please let me know if you have any suggestion. 

Thanks

Alessandro

 

0 Kudos
1 Solution
Steve_Lionel
Honored Contributor III
1,862 Views

I used the command:

dumpbin -exports prova.lib

which gives me:

Dump of file prova.lib

File Type: LIBRARY

     Exports

       ordinal    name

                  PROVA

One does this from a Fortran command prompt window. By default, Intel Fortran upcases all external names on Windows. On a 32-bit build. it puts an underscore before the name but on a 64-build there is no underscore. The linker is case-sensitive, so if your ABAQUS routine is looking for "prova" it won't match "PROVA". If you can change the name in ABAQUS, that will work. Alternatively, use this in the Fortran code instead of what you have now:

cDEC$ attributes dllexport, alias:"prova" ::prova

I also recommend putting this INSIDE routine prova - it may not be recognized outside it.

The __imp__ means that you have done a DLLIMPORT and this means it wants to link to the import library. For procedures the DLLIMPORT is actually optional (though recommended) - it is required for data you are accessing from a DLL.

View solution in original post

0 Kudos
14 Replies
Steve_Lionel
Honored Contributor III
1,862 Views

Your process is incorrect. Step 2 also creates a .lib - this is what you should be linking to and not a .lib you create from the .obj.

0 Kudos
Alessandro_N_
Beginner
1,862 Views

Hi Steve, 

thanks for the quick response. Step 2 does not create a .lib file. It creates only the .obj file and the .dll file. 

To create the lib file from the .obj I followed the instructions at this link: https://software.intel.com/en-us/node/691875

So I'm afraid that is not the issue. 

Alessandro

0 Kudos
mecej4
Honored Contributor III
1,862 Views

Step 2 did create an import library file. Unfortunately, your unnecessary Step 3 created a static library and, since the name of this library file was the same as that of the import library file, the static library file overwrote the import library file.

You can verify this for yourself by listing the directory contents between each step. Furthermore, Step-1 probably created a .DEF file that is still present there. If so, you can simply use that file to recreate the import library.

0 Kudos
Alessandro_N_
Beginner
1,862 Views

Hi mecej4, 

Thanks for your response. Step 2 was not creating the .lib file because 'name' in cDEC$ attributes dllexport::name was not the same name of the subroutine. When I use the same name it creates a .lib file and I do not need Step 3. 

However, this did not solve the issue. I still get the error: vuamp.obj : error LNK2019: unresolved external symbol <subroutine_name> referenced in function vuamp

Alessandro

0 Kudos
Steve_Lionel
Honored Contributor III
1,862 Views

Zip the .lib from step 2, along with the build log from the link, and attach it here. (The .lib contains no code - it is just the DLL import linkage.)

0 Kudos
Alessandro_N_
Beginner
1,862 Views

Hi Steve, 

I attached a zip with .f, .lib, .dll, .exp files. 

Where can I find the build log from the link? Is it the error I get when I try to run the Abaqus simulation? 

Thanks,

Alessandro

0 Kudos
Steve_Lionel
Honored Contributor III
1,862 Views

If you're not using Visual Studio to build, then just copy and paste the output you get when you do the build. I want to see the EXACT and COMPLETE text of the error message and, ideally, the link command used.

I can see that prova.lib exports a name called PROVA - spelled exactly like that. 

0 Kudos
Alessandro_N_
Beginner
1,862 Views

I attached two pictures:

1) The message I get when I build (ifort /dll prova.f) 

2) The error message when I try to run the Abaqus simulation with the vuamp subroutine.

 

0 Kudos
mecej4
Honored Contributor III
1,862 Views

As of now, we know about at least one inconsistency: the DLL exports "PROVA", whereas Abaqus expects to see "prova". It is easy enough to fix this, but before doing so you should probably find out what exactly the Abaqus ABI requires. 

0 Kudos
Alessandro_N_
Beginner
1,862 Views

Interesting...

What do you exactly mean when you say the DLL "exports" PROVA? How did you figure this? 

You are saying it would be easy enough to fix this. Could you please tell me how? 

I do not know how to figure out what the Abaqus ABI requires. Also, what requirements are you referring to specifically? 

Thanks for your help!

Alessandro

0 Kudos
Alessandro_N_
Beginner
1,862 Views

Also, this is the error I get when I run the Abaqus job (slightly different from what I attached before).

Now it says "unresolved external symbol __imp_prova" even though I am calling the subroutine as "prova". What does "__imp_" mean? 

Alessandro

0 Kudos
Steve_Lionel
Honored Contributor III
1,863 Views

I used the command:

dumpbin -exports prova.lib

which gives me:

Dump of file prova.lib

File Type: LIBRARY

     Exports

       ordinal    name

                  PROVA

One does this from a Fortran command prompt window. By default, Intel Fortran upcases all external names on Windows. On a 32-bit build. it puts an underscore before the name but on a 64-build there is no underscore. The linker is case-sensitive, so if your ABAQUS routine is looking for "prova" it won't match "PROVA". If you can change the name in ABAQUS, that will work. Alternatively, use this in the Fortran code instead of what you have now:

cDEC$ attributes dllexport, alias:"prova" ::prova

I also recommend putting this INSIDE routine prova - it may not be recognized outside it.

The __imp__ means that you have done a DLLIMPORT and this means it wants to link to the import library. For procedures the DLLIMPORT is actually optional (though recommended) - it is required for data you are accessing from a DLL.

0 Kudos
mecej4
Honored Contributor III
1,862 Views

The command dumpbin /exports prova.dll will show the exported name(s).

The _imp prefix is used to signify that the symbol (usually, the decorated name of a routine name) is imported from a DLL.

The compiler has options to control the case of external symbols in the OBJ files that it generates, but I think that you should not try those options yet.

Instead, consult the Abaqus documentation for your specific Abaqus version to find out the external interface specifications. The name decorating and argument passing conventions have to match, and register saving conventions have to be honored.

0 Kudos
Alessandro_N_
Beginner
1,862 Views

Steve and mecej4, 

I tried with cDEC$ attributes dllexport, alias:"prova" ::prova and it works!

Thanks a lot for your help! 

Alessandro

 

0 Kudos
Reply