Hi,

There is a design problem in the networking component (and in Gambas streams 
generally). You cannot send data on demand. Annoying if you want to write a 
file server for example...

So I'm trying to solve that in Gambas 3 - I'm afraid I won't be able to 
backport it to Gambas 2...

I added a "Write" event to the Socket class. This event is raised after you 
have wrote something on the Socket, *and* when writing is possible again.

During the event handler of the "Write" event, you must write the data you 
want to sent in small pieces. If you write too much data during one want, you 
may block!

The "Write" event will be raised once, unless you actually write something 
during its event handler. Then it will be raised again.

A better solution is setting the Blocking property of the Socket to False, and 
then writing inside the Write event handler until an error is raised. 

If this error is actually the write() system call telling that the internal 
buffer is full, then the Write event will be raised later again. Otherwise 
this a true error and the socket is closed.

Only the Socket class is fixed, but I'd like to find a solution for every 
stream. I'm not sure I will, because File, Process and Socket are very 
different beasts.

Anyway this is better than nothing at the moment!

So here is a little example of how the ServerSocket example was modified:

-------------------------------------------------------------------------

Public Sub Server_Connection(Host As String)

  Dim Obj As Socket

  Obj = Server.Accept()
  Obj.Blocking = False
  ...
  
End

Public Sub Socket_Read()

  Dim sBuf As String

  ' Read the request
  Read #Last, sBuf, Lof(Last)
  ' Use the new Socket Tag property to register what we already sent
  Last.Tag = [0, sBuf]
  ' Call the write handler by hand to start the writing
  Socket_Write
    
End

Public Sub Socket_Write()

  Dim hSocket As Socket = Last
  Dim iInd As Integer
  
  ' If we write nothing, the Write event won't be raise again
  If IsNull(hSocket.Tag) Then Return
  
  iInd = hSocket.Tag[0]
  
  ' Write 1000 lines of text
  Do
    Inc iInd
    If iInd > 1000 Then
      hSocket.Tag = Null
      Return
    Endif
    
    Try Print #hSocket, iInd; ":";; hSocket.Tag[1]; Space$(512)

    ' If there is an error, we break
    ' If the error is actually a write buffer full, do not worry, the
    ' Write event will be raised again

    If Error Then Break

  Loop
  
  hSocket.Tag[0] = iInd

End

-------------------------------------------------------------------------

I hope the way of using that new feature is clear!

Regards,

-- 
Benoît

------------------------------------------------------------------------------
OpenSolaris 2009.06 is a cutting edge operating system for enterprises 
looking to deploy the next generation of Solaris that includes the latest 
innovations from Sun and the OpenSource community. Download a copy and 
enjoy capabilities such as Networking, Storage and Virtualization. 
Go to: http://p.sf.net/sfu/opensolaris-get
_______________________________________________
Gambas-user mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/gambas-user

Reply via email to