Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Chris Miller on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

overflow trying to get file length 1

Status
Not open for further replies.

1DMF

Programmer
Jan 18, 2005
8,795
GB
I have defined a var as Long to hold file size so I can use the sysmeter for a progress bar when downloading a file via wininet.dll

However I am getting a buffer overflow when requesting file size, how do I resolve this?

code...
Code:
Function FTPGet(ByVal HostName As String, _
    ByVal UserName As String, _
    ByVal Password As String, _
    ByVal LocalFileName As String, _
    ByVal RemoteFileName As String, _
    ByVal sDir As String, _
    ByVal sMode As String) As Boolean
    
    'On Error GoTo Err_Function
        
' Declare variables
Dim hConnection, hOpen, hFile  As Long ' Used For Handles
Dim iSize As Long ' Size of file for download
Dim Retval As Variant ' Used for progress meter
Dim iLoop As Long ' Loop for downloading chunks
Dim iFile As Integer ' Used for Local file handle
Dim FileData(BUFFER_SIZE - 1) As Byte ' buffer array of BUFFER_SIZE (100) elements 0 to 99

' Open Internet Connecion
hOpen = InternetOpen("FTP", 1, "", vbNullString, 0)

' Connect to FTP
hConnection = InternetConnect(hOpen, HostName, INTERNET_DEFAULT_FTP_PORT, UserName, Password, INTERNET_SERVICE_FTP, IIf(PassiveConnection, INTERNET_FLAG_PASSIVE, 0), 0)

' Change Directory
Call FtpSetCurrentDirectory(hConnection, sDir)

' Open Remote File
hFile = FtpOpenFile(hConnection, RemoteFileName, GENERIC_READ, IIf(sMode = "Binary", FTP_TRANSFER_TYPE_BINARY, FTP_TRANSFER_TYPE_ASCII), 0)

' Check for successfull file handle
If hFile = 0 Then
    MsgBox "Internet - Failed!"
    ShowError
    FTPGet = False
    GoTo Exit_Function
End If

' Set Download Flag to True
FTPGet = True

' Set file size
iSize = LOF(hFile) <---- crashes here



"In complete darkness we are all the same, only our knowledge and wisdom separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!
 
it's ok I worked it out thanks :)

For anyone who is interested...
Code:
Function FTPDel(ByVal HostName As String, _
    ByVal UserName As String, _
    ByVal Password As String, _
    ByVal RemoteFileName As String, _
    ByVal sDir As String) As Boolean
    
    On Error GoTo Err_Function
        
' Declare variables
Dim hConnection, hOpen, hFile  As Long ' Used For Handles

' Open Internet Connecion
hOpen = InternetOpen("FTP", 1, "", vbNullString, 0)

' Connect to FTP
hConnection = InternetConnect(hOpen, HostName, INTERNET_DEFAULT_FTP_PORT, UserName, Password, INTERNET_SERVICE_FTP, IIf(PassiveConnection, INTERNET_FLAG_PASSIVE, 0), 0)

' Change Directory
Call FtpSetCurrentDirectory(hConnection, sDir)

' Open Remote File
Call FtpDeleteFile(hConnection, RemoteFileName)

' Close Internet Connection
Call InternetCloseHandle(hOpen)
Call InternetCloseHandle(hConnection)

FTPDel = True

Exit Function

Err_Function:
MsgBox "Error in FTPDel : " & Err.Description
Exit Function

End Function
Function FTPGet(ByVal HostName As String, _
    ByVal UserName As String, _
    ByVal Password As String, _
    ByVal LocalFileName As String, _
    ByVal RemoteFileName As String, _
    ByVal sDir As String, _
    ByVal sMode As String) As Boolean
    
    On Error GoTo Err_Function
        
' Declare variables
Dim hConnection, hOpen, hFile  As Long ' Used For Handles
Dim iSize As Long ' Size of file for download
Dim Retval As Variant ' Used for progress meter
Dim iRead As Long ' Used by InternetReadFile to report bytes downloaded
Dim iLoop As Long ' Loop for downloading chunks
Dim iFile As Integer ' Used for Local file handle
Dim FileData(BUFFER_SIZE - 1) As Byte ' buffer array of BUFFER_SIZE (100) elements 0 to 99

' Open Internet Connecion
hOpen = InternetOpen("FTP", 1, "", vbNullString, 0)

' Connect to FTP
hConnection = InternetConnect(hOpen, HostName, INTERNET_DEFAULT_FTP_PORT, UserName, Password, INTERNET_SERVICE_FTP, IIf(PassiveConnection, INTERNET_FLAG_PASSIVE, 0), 0)

' Change Directory
Call FtpSetCurrentDirectory(hConnection, sDir)

' Open Remote File
hFile = FtpOpenFile(hConnection, RemoteFileName, GENERIC_READ, IIf(sMode = "Binary", FTP_TRANSFER_TYPE_BINARY, FTP_TRANSFER_TYPE_ASCII), 0)

' Check for successfull file handle
If hFile = 0 Then
    MsgBox "Internet - Failed!"
    ShowError
    FTPGet = False
    GoTo Exit_Function
End If

' Set Download Flag to True
FTPGet = True

' Set file size
iSize = FtpGetFileSize(hFile, 0)

' Get next file handle number
iFile = FreeFile

' Open local file
Open LocalFileName For Binary Access Write As iFile

' Iinitialise progress meter
Retval = SysCmd(acSysCmdInitMeter, "Downloading File (" & RemoteFileName & ")", iSize / 1000)

' Loop file size
For iLoop = 1 To iSize \ BUFFER_SIZE
        
    ' Update progress meter
    Retval = SysCmd(acSysCmdUpdateMeter, (BUFFER_SIZE * iLoop) / 1000)

    ' Read chunk from FTP checking for success
    If InternetReadFile(hFile, FileData(0), BUFFER_SIZE, iRead) = 0 Then
        MsgBox "Download - Failed!"
        ShowError
        FTPGet = False
       GoTo Exit_Function
    Else
        ' Check buffer was read
        If iRead <> BUFFER_SIZE Then
            MsgBox "Download - Failed!"
            ShowError
            FTPGet = False
            GoTo Exit_Function
        End If
    End If
    
    'put file data
    Put iFile, , FileData
    
Next iLoop

' Handle remainder using MOD

    ' Update progress meter
    Retval = SysCmd(acSysCmdUpdateMeter, iSize / 1000)
    
    ' Write remainder to file checking for success
    If InternetReadFile(hFile, FileData(0), iSize Mod BUFFER_SIZE, iRead) = 0 Then
        MsgBox "Download - Failed!"
        ShowError
        FTPGet = False
        GoTo Exit_Function
    Else
        ' Check buffer was read
        If iRead <> iSize Mod BUFFER_SIZE Then
            MsgBox "download - Failed!"
            ShowError
            FTPGet = False
            GoTo Exit_Function
        End If
    End If
               
    ' Put file data
    Put iFile, , FileData
    
Exit_Function:

' remove progress meter
Retval = SysCmd(acSysCmdRemoveMeter)

'close local file
Close iFile

'close remote file
Call InternetCloseHandle(hFile)

' Close Internet Connection
Call InternetCloseHandle(hOpen)
Call InternetCloseHandle(hConnection)

Exit Function

Err_Function:
MsgBox "Error in FTPGet : " & Err.Description
GoTo Exit_Function

End Function

This is VBA in MS Access ;-)

"In complete darkness we are all the same, only our knowledge and wisdom separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!
 
I would expect that it's because the LOF() function is expecting an Integer as the file handle rather than a Long.

Hope this helps

HarleyQuinn
---------------------------------
Carter, hand me my thinking grenades!

You can hang outside in the sun all day tossing a ball around, or you can sit at your computer and do something that matters. - Eric Cartman

Get the most out of Tek-Tips, read FAQ222-2244: How to get the best answers before posting.

 
You well beat me to that one there 1DMF [wink]

HarleyQuinn
---------------------------------
Carter, hand me my thinking grenades!

You can hang outside in the sun all day tossing a ball around, or you can sit at your computer and do something that matters. - Eric Cartman

Get the most out of Tek-Tips, read FAQ222-2244: How to get the best answers before posting.

 
I realised (I think) that LOF is a local file operation, and FtpGetFileSize was required to work out the FTP size of file.

I've declared it as
Code:
Public Declare Function FtpGetFileSize Lib "wininet.dll" _
(ByVal hFile As Long, ByRef lpdwFileSizeHigh As Long) As Long

Though I'm still confused over what lpdwFileSizeHigh refers to?

When I call it I use
Code:
' Set file size
iSize = FtpGetFileSize(hFile, 0)

As the declaration is 'ByRef' , I even tried
Code:
' Set file size
iSize = FtpGetFileSize(hFile, [b]iSize[/b])

But both worked returning the correct filesize, so can anyone explain what the second var is required and what i'm meant to supply, as zero works it makes no sense to me!

"In complete darkness we are all the same, only our knowledge and wisdom separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!
 
Having never used FtpGetFileSize this is just 'off the cuff' so to speak.

Basically, lpdwFileSizeHigh is a pointer to hold the high-order unsigned long integer (which, as declared ByRef, will be populated by the function) and the function itself returns the low-order unsigned long integer of the filesize.

So what you're essentially doing in your example is setting iSize in the function, then setting it again with the return value for the function (so both will return the same).

The reason I would think why they are both returned is to allow you to work with a file size of up to 64 bits which is too big to fit in a 32-bit unsigned long integer (which is a file about 4gb in size).

Hope this helps

HarleyQuinn
---------------------------------
Carter, hand me my thinking grenades!

You can hang outside in the sun all day tossing a ball around, or you can sit at your computer and do something that matters. - Eric Cartman

Get the most out of Tek-Tips, read FAQ222-2244: How to get the best answers before posting.

 
ahh, this makes sense
(which is a file about 4gb in size).

As i saw a thread while hunting for info on declaring the wininet function where someone moaned about if failing with files 4gb+

"In complete darkness we are all the same, only our knowledge and wisdom separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top