On 2016-01-20 12:23-0000 Arjen Markus wrote: > As for your idea for diambiguation: that ought to work, I think. I will have > a close look at that aspect.
Here is the code I used to implement my idea: ... interface plstransform module procedure plstransform_impl end interface plstransform private :: plstransform_impl ... contains ... subroutine plstransform_impl( proc_single, proc_data_single, proc_double, proc_data_double, data ) procedure(pltransform_proc_single), optional :: proc_single procedure(pltransform_proc_data_single), optional :: proc_data_single procedure(pltransform_proc_double), optional :: proc_double procedure(pltransform_proc_data_double), optional :: proc_data_double type(c_ptr), optional, intent(in) :: data interface subroutine interface_plstransform( proc, data ) bind(c, name = 'c_plstransform' ) import :: c_funptr, c_ptr type(c_funptr), value, intent(in) :: proc type(c_ptr), value, intent(in) :: data end subroutine interface_plstransform end interface if( .not. present(proc_single) .and. .not. present(proc_data_single) & .and. .not. present(proc_double) .and. .not. present(proc_data_double) & .and. .not. present(data) ) then call interface_plstransform( c_null_funptr, c_null_ptr ) elseif( present(proc_single) .and. .not. present(proc_data_single) & .and. .not. present(proc_double) .and. .not. present(proc_data_double) & .and. .not. present(data) ) then pltransform_single => proc_single call interface_plstransform( c_funloc(pltransformf2c_single), c_null_ptr ) elseif( .not. present(proc_single) .and. present(proc_data_single) & .and. .not. present(proc_double) .and. .not. present(proc_data_double) & .and. present(data) )then pltransform_data_single => proc_data_single call interface_plstransform( c_funloc(pltransformf2c_data_single), data ) elseif( .not. present(proc_single) .and. .not. present(proc_data_single) & .and. present(proc_double) .and. .not. present(proc_data_double) & .and. .not. present(data) ) then pltransform_double => proc_double call interface_plstransform( c_funloc(pltransformf2c_double), c_null_ptr ) elseif( .not. present(proc_single) .and. .not. present(proc_data_single) & .and. .not. present(proc_double) .and. present(proc_data_double) & .and. present(data) ) then pltransform_data_double => proc_data_double call interface_plstransform( c_funloc(pltransformf2c_data_double), data ) else write(error_unit,"(a)") "f95 plstransform ERROR: one of the following valid argument choices not used:" write(error_unit,"(a)") "(1) no arguments;" write(error_unit,"(a)") "(2) a single-precision coordinate_transform callback;" write(error_unit,"(a)") "(3) a single-precision coordinate_transform callback and c_loc of defined data type;" write(error_unit,"(a)") "(4) a double-precision coordinate_transform callback; or" write(error_unit,"(a)") "(5) a double-precision coordinate_transform callback and c_loc of defined data type." return endif end subroutine plstransform_impl ... I was pretty proud of that implementation, but there is a "slight" problem with it which is it does not work! :-( After doing some experiments commenting out certain parts it turns out that gfortran (and I assume all other Fortran compilers) treats the first four arguments as completely interchangeable as far as disambiguation is concerned. So the library builds OK based on the disambiguation between 0, 1, 2, 3, and 4 callbacks in the argument list, but when an example specifies just one callback, the first of the possibilities is selected which of course does not match in type (because our examples currently use just double-precision callbacks. Even if I comment out all the single types, gfortran still cannot disambiguate between proc_double and proc_data_double, and apparently just assumes the first because under those conditions example 19 (which does not use the data form of callback) compiles OK, but example 22 (which does use the data form) fails to compile with the message /home/software/plplot/HEAD/plplot.git/examples/f95/x22f.f90:232.56: call plstransform( transform_data, c_loc(data)) 1 Error: There is no specific subroutine for the generic 'plstransform' at (1) This is really peculiar behaviour that I have alluded to before. Clearly, the gfortran compiler enforces the rule that the callback function arguments supplied by the calling routine must match exactly in number and type with what is expected by the library, but that compiler refuses to use that known information to disambiguate. So for this particular case we use the presence or absence of data in the argument list to disambiguate (i.e., we use the method presently implemented on master tip). So the question is whether this peculiar behaviour is due to a gfortran bug or due to an issue with the Fortran standard for disambiguation, and I hope you will continue to pursue that question with your Fortran contacts. Meanwhile, I will throw away the above "good" idea and continue with the (double-precision only) status quo for plstransform (and plslabelfunc). Alan __________________________ Alan W. Irwin Astronomical research affiliation with Department of Physics and Astronomy, University of Victoria (astrowww.phys.uvic.ca). Programming affiliations with the FreeEOS equation-of-state implementation for stellar interiors (freeeos.sf.net); the Time Ephemerides project (timeephem.sf.net); PLplot scientific plotting software package (plplot.sf.net); the libLASi project (unifont.org/lasi); the Loads of Linux Links project (loll.sf.net); and the Linux Brochure Project (lbproject.sf.net). __________________________ Linux-powered Science __________________________ ------------------------------------------------------------------------------ Site24x7 APM Insight: Get Deep Visibility into Application Performance APM + Mobile APM + RUM: Monitor 3 App instances at just $35/Month Monitor end-to-end web transactions and take corrective actions now Troubleshoot faster and improve end-user experience. Signup Now! http://pubads.g.doubleclick.net/gampad/clk?id=267308311&iu=/4140 _______________________________________________ Plplot-devel mailing list Plplot-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/plplot-devel