how to solve this numeric problem in vba

how to solve this numeric problem in vba

i have got a value calculated by fortran dll and export to vba, however, the digit is more than 14, (is 15), then
in excel , it just told me that "OVERFLOW".

The value I have defined it as double, no matter I change it to single, it return one more digit than the limit.
Can anyone help me?
Thx

17 posts / 0 new
Last post
For more complete information about compiler optimizations, see our Optimization Notice.

If the Fortran value is defined as REAL*8 or DOUBLE PRECISION and the VBA value is defined as Double, then you shouldn't have a problem. Those are equivalent data types.

When you debug the Fortran DLL what is the value being returned to the calling VBA routine?

Mike

I have set the value in fortran as real*8 and
vba as double.

however, the value obtained from vba is overflow.
i have counted the digits which is more than 14 digits.

Where are you seeing these digits that you are counting and finding to be more than 14?

Describe the steps you are taking to run your application up to the point where it overflows.

Are you using a debug or a release configuration of your Fortran DLL?

It would help a lot if you could post an example of your VBA and Fortran code that exhibits this problem.

Mike

Declare Sub kachadll Lib "D:MatthewomegaPkachapkachadllDebugkachadll.dll" (tim45 As Double, str45 As Double, smpa45 As Double, bigomega As Double, smallm As Double, fac As Integer)

Could you tell me how to use the debugger for dll?
i think the the data tranfer for that dll is okay, however, after it transfer to vba, it just say overflow.

do u also know how to cut the digits in Fortran?
thx

So far so good. Maybe you need to include the Fortran Sub line and the variable declarations.

If you are seeing a certain number of digits visually, that is irrelevant. The Double data type takes 8 bytes of memory regardless of whether you are in VB or Fortran or how much is displayed to you.

I would guess that the data types are not exactly the same. I am going to guess that the fac as integer is the problem. In VB, the Integer variable type takes 2 bytes of memory. The default Integer in Fortran takes 4 bytes, though you can set compiler switches to change this default, or declare the variable in Fortran to only take two bytes.

If this is the case that Fortran is expecting a 4 byte integer and VB is passing 2, maybe you could change the variable of fac to Long in VB which would be the same as an integer in Fortran.

but i think there is no problem for fac because i didn't put it in the message box or in the cells in excel spreadsheets. The problem is the smallm , i need to show it in the cells , once i show it, the error message comes
if i didn't show it or use it to do calculation in vba, there is no problem.

thx

I agree with sdahl that you should post at least the declaration of your Fortran subroutine.

Based on your last post it sounds like the call to the Fortran DLL is successful and that the error occurs once you are back in the Excel environment and attempting to display the value of VBA variable smallm. Please post the VBA code you are using to show smallm's value.

I think that rather than specifying VB6.EXE as the executable for your debug session you want to specify the Excel executable. Excel should start your VBA code. For Office XP you would specify something similar to:

C:Program FilesMicrosoft OfficeOffice10EXCEL.EXE.

The exact location will depend on the version of MS Office that you are using.

Mike

subroutine KACHADLL(tim45,str45,smpa45,bigomega,smallm,fac1)

!DEC$ ATTRIBUTES DLLEXPORT::kachadll
!DEC$ ATTRIBUTES ALIAS:'kachadll' :: kachadll

use numerical_libraries
use dflib
integer :: m,np,imain,jmain,kmain,kkmain
integer :: counting2,NumCreep,count
REAL*8,DIMENSION(199) :: TIM,STR,CRT
REAL*8,DIMENSION(199) :: EXTIM,STRAN,RES,CRATE,SIG,SIGMA
REAL*8,DIMENSION(199) :: RESN,RT
integer fac1
real*8::tim45(fac1,1),str45(fac1,1)
real*8::smpa45
REAL*8,DIMENSION(2) :: XX
REAL*8 :: STMIN,TRUP,TR,AAK,smpa,bm,bn,bdelta,bk,bphi,&
sumbm,sumbdelta,etff,BBK,BBN,BBDEV,BBCORR,bba,bbnu
REAL*8,DIMENSION(20) :: STRUP2,BBM,BBDELTA,BBPHI,BBSTRESS,BBTF,&
LTETFF,logs,STRUP
REAL*8,DIMENSION(250,40):: ARRAY

REAL*8 :: CRMIN,TMCR,CRRUP
real*8:: bigomega,smallm

The above is the declaration in FORTRAN

VBA Module:

Declare Sub kachadll Lib "D:MatthewomegaPkachapkachadllDebugkachadll.dll" (tim45 As Double, str45 As Double, smpa45 As Double, bigomega As Double, smallm As Double, fac1 As Long)

VBA Main:
Sub CommandButton8_Click()

Dim tim45() As Double
Dim str45() As Double
Dim smpa45 As Double
Dim fac1 As Long
Dim Max As Integer
Dim j As Single
Dim k As Single
Dim bigomega As Double
Dim smallm As Double
Dim aa As Double

Call kachadll(tim45(1, 1), str45(1, 1), smpa45, bigomega, smallm, fac1)

The problem happened in the following line: "OVERFLOW"

Worksheets("sheet2").Cells(16, 7).Value = smallm

Thx!

One more thing on how to use the debugger for the .dll. You need to do a Debug build, which it looks like you did since your VB Declare is pointing at the debug folder.

In the Fortran environment, select the Project..Settings menu. On the dialog go to the Debug tab. In the entry for "Executable for debug session:" enter your path to VB6.EXE. Something like:

C:Program FilesMicrosoft Visual StudioVB98VB6.EXE

Then run your Fortran program. To actually step through Fortran code, you need to set a break point at the point you would like to start debugging. You can't step from VB directly into Fortran, but you can do the equivalent by having the breakpoint set.

Try to use other placeholder names in the declaration part. Please post how you redim the arrays in VBA.

HoVi

ReDim tim45(1 To Max + 1, 1 To 1)
ReDim str45(1 To Max + 1, 1 To 1)

I think it is not the problem of this array, but it is the problem of smallm

If you don't like to reveal the full VBA code,
I attach a working example as an Excel file containing a function "multiplytheelements" and a F90-file containing the source code for an DLL that should be named HVTEST.DLL.

/check:bounds /compile_only /dbglibs /debug:full
/fltconsistency /fpconstant /dll /nologo /traceback
/warn:argument_checking /warn:nofileopt

hope this helps

Holger Viebrok

Firstly, thx your file.

i can cut the digit e.g. 1.543e-3 in fortran now, i can cut it into 1.54e-3

smallm=1.543e-4
smallm2=-(floor(log10(smallm)))
smallm=(int((10.**(smallm2+2)*smallm))/(10.**(smallm2+2)))

, however, the problem is still "OVERFLOW",

If I made no mistake, the result of your expression is zero. What are doing with the result?

i think you need to declare
smallm2 as integer
and smallm as real.

Do you think it is possible to do the internal write and read within dll?

Leave a Comment

Please sign in to add a comment. Not a member? Join today