You should read data from the socket in "chunks". Here's a snippet from asynchronous socket data transfer
Private PACKET_SIZE As UInt16 = 4096
.
.
SyncLock Client.GetStream
Reader = New BinaryReader(Client.GetStream)
'next we expect a pass-through byte
Client.GetStream.Read(ReadByte, 0, 1)
PassThroughByte = ReadByte(0)
'next expect length of data (Int32)
NData = Reader.ReadInt32
LenData = NData
'now comes the data, save it in a memory stream
MStream = New MemoryStream
While NData > 0
RaiseEvent TransferProgress(Me, PassThroughByte, CSng(1.0 - NData / LenData))
LData = Me.Client.GetStream.Read(ReadBuffer, 0, PACKET_SIZE)
MStream.Write(ReadBuffer, 0, LData)
NData -= LData
End While
'Continue the asynchronous read from the NetworkStream
Me.Client.GetStream.BeginRead(ReadByte, 0, 1, AddressOf ReceiveOneByte, Nothing)
End SyncLock
and I suppose you are able to grab the idea i.e. how the chunks are read from the socket in the while loop.
Teme64
Veteran Poster
1,031 posts since Aug 2008
Reputation Points: 218
Solved Threads: 203
Use BB code tags to present your source code.
Read this article .
__avd
Posting Genius (adatapost)
8,648 posts since Oct 2008
Reputation Points: 2,136
Solved Threads: 1,241
Sorry for so unclear answer.
Here's the code with proper type definitions. And this code is receiving i.e. your server side code
Private PACKET_SIZE As UInt16 = 4096
.
.
Dim Reader As BinaryReader
Dim ReadBuffer(PACKET_SIZE - 1) As Byte
Dim NData As Int32
Dim MStream As MemoryStream
Dim LData As Int32
Reader = New BinaryReader(Client.GetStream)
' Read Length of data (Int32)
NData = Reader.ReadInt32
' Now comes the data, save it in a memory stream
MStream = New MemoryStream
While NData > 0
LData = Me.Client.GetStream.Read(ReadBuffer, 0, PACKET_SIZE)
MStream.Write(ReadBuffer, 0, LData)
NData -= LData
End While
And your client side code changes a bit
Dim fileStream As FileStream = File.Open([filename], FileMode.Open, FileAccess.Read, FileShare.Read)
Dim reader As BinaryReader = New BinaryReader(fileStream)
Dim fileLength As Int32 = CInt(fileStream.Length)
Dim sendBytes(fileLength - 1) As Byte
reader.Read(sendBytes, 0, fileLength)
' Send length first
serverStream.WriteInt32(fileLength)
' Now, send the data
serverStream.Write(sendBytes, 0, fileLength)
since you have to send the length of the data first.
Teme64
Veteran Poster
1,031 posts since Aug 2008
Reputation Points: 218
Solved Threads: 203
btw, i'm Using vb 2005. sorry not to tell U before.
I was assuming VB.2005.at the client side, there is some error (the red one).
Oops!
Here's the modified client code. You can't send the whole file at once. You have to also send data in "chunks" (like you noticed in one of your messages). This is basically same code as yours. Instead of "serverStream" I've used a binary writer ("Writer") which writes to socket's data stream i.e. System.Net.Sockets.NetworkStream. You had declared serverStream As System.Net.Sockets.NetworkStream I guess
Private PACKET_SIZE As UInt16 = 4096
.
.
Dim ByteArray() As Byte ' Data buffer
Dim Fs As FileStream = New FileStream(FilePath, FileMode.Open, FileAccess.Read)
Dim Reader As New BinaryReader(Fs)
Try
Dim Writer As New BinaryWriter(Me.Client.GetStream) ' Get socket's stream
'send size of file
Writer.Write(CInt(Fs.Length))
'Send the file data
Do
'read data from file
ByteArray = Reader.ReadBytes(PACKET_SIZE)
'write data to Network Stream
Writer.Write(ByteArray)
Loop While ByteArray.Length = PACKET_SIZE
'make sure all data is sent
Writer.Flush()
Writer.Close()
Reader.Close()
Catch ex As Exception
' Handle errors
End Try
The advantage of using binary writer is that you have more overloaded Write methods. Actually the code needs only Write(value As Integer) method not found in NetworkStream class to send the length of the data.
Teme64
Veteran Poster
1,031 posts since Aug 2008
Reputation Points: 218
Solved Threads: 203
Hi! Nice to hear that you got answer to your problem. Could you please mark the thread as solved. Thank you!
allow me to ask another question:
Not related to sockets. Please, start a new thread for a new question.
That's not to say, I wouldn't answer the question. I would gladly help with that other question too. It's just that peopledo look for these Questions&Answers with DaniWeb's search or some other way. And if somebody looks for help in question "if I want to send an animated GIF format picture, how do I save the picture in deatination folder?", they hardly look for it in a thread with title "[socket programming]..." :) That's the reason why you should always start a new thread :)
Teme64
Veteran Poster
1,031 posts since Aug 2008
Reputation Points: 218
Solved Threads: 203