- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
So, I am trying to access a C function from F90, with the following code:
SUBROUTINE sub1() USE,INTRINSIC :: iso_c_binding ! interface to c library INTERFACE ! library function prototype ! DBfile *DBCreate (char *pathname, int mode, int target, char *fileinfo, int filetype) TYPE(C_PTR) FUNCTION DBCreate_f(pathname,mode,fileformat,fileinfo,filetype) BIND(C,NAME="DBCreate") IMPORT :: C_PTR,C_CHAR,C_INT IMPLICIT NONE CHARACTER(KIND=C_CHAR) :: pathname(*) INTEGER(KIND=C_INT),VALUE :: mode INTEGER(KIND=C_INT),VALUE :: fileformat CHARACTER(KIND=C_CHAR) :: fileinfo(*) INTEGER(KIND=C_INT),VALUE :: filetype END FUNCTION DBCreate_f ! library function prototype ! int DBClose (DBfile *dbfile) INTEGER(KIND=C_INT) FUNCTION DBClose_f(dbfile) BIND(C,NAME="DBClose") IMPORT :: C_INT,C_PTR IMPLICIT NONE TYPE(C_PTR) :: dbfile END FUNCTION DBClose_f END INTERFACE CHARACTER(LEN=...) :: string11 CHARACTER(LEN=...,KIND=C_CHAR) :: string1 INTEGER(C_INT) :: val1,val2,val3 CHARACTER(LEN=...) :: string21 CHARACTER(LEN=...,KIND=C_CHAR) :: string2 TYPE(C_PTR) :: retval1_ptr INTEGER(C_INT) :: retval2 retval1_ptr=C_NULL_PTR !====================================================================== ! call to first interface function !====================================================================== WRITE(string11,FMT='(a)') "blahblahblah" WRITE(UNIT=string1,FMT='(a,a)') TRIM(string11),C_NULL_CHAR val1=1 val2=2 WRITE(string21,FMT='(a)') "BLAHBLAHBLAH" WRITE(UNIT=string2,FMT='(a,a)') TRIM(string21),C_NULL_CHAR val3=3 retval1_ptr=DBCreate_f(string1,val1,val2,string2,val3) ! this is line 372 in the original file ! DBCreate returns a DBfile pointer on success and NULL on failure. IF (.NOT.C_ASSOCIATED(retval1_ptr)) CALL terminate(...) !====================================================================== ! call to second interface function !====================================================================== retval2=DBClose_f(retval1_ptr) ! DBClose returns zero on success and -1 on failure. IF (retval2==-1) CALL terminate(...) END SUBROUTINE sub1
However, in the link stage, I get the error:
module1.o: In function `sub1':
module1.f90:372: undefined reference to `DBCreate'
Several notes:
- It is my understanding that C_PTR can be used to return scalar pointers of _any_ type, and since I don't need to access any of the data pointed at by this pointer directly, I thought the above would be ok.
- There are two calls to the library, and only one of them is having a problem. However, running nm on the .a file verified that the function DBCreate is actually in the file.
- I tried this with various versions of ifort, from early 12.xxx to 14.xxx, and they all exhibit the same problem.
Any thoughts? Thanks.
Link Copied
2 Replies
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
You did not show the link command line, so we do not know if you specified that the library containing the function DBCreate should be searched while building the application.
It is not the type of the returned value from DBCreate that is an issue, but the address of the routine itself, which the linker needs to resolve in order to produce a valid a.out.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
So, it turns out that the developers of this library do some strange munging of the name of that single function . . .
Thanks!
Reply
Topic Options
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page