probleme entre ReceiveNetworkData et SendNetworkData
Publié : mar. 09/oct./2012 15:02
Bonjour a tous,
J'essaye depuis 1 semaine de faire un programme de transfert de fichier entre 2 machines en LAN.
Mon but est de transférer des fichiers d'une machine a une autre et inversement (autrement dit, client/serveur serveur/client)
Pour la connexion entre les 2, j'ai réussi sans trop de soucis.
Le soucis maintenant, c'est que le transfert de petit fichier fonctionne, mais le transfert d'un plus gros (j'ai testé sur 1 fichier de 1.7Mo) ne fonctionne pas.
Voici mes codes client/serveur (attention, c'est un peu long) :
Code serveur :
Code CLIENT :
J'ai mis les 2 fichiers icones ici : http://hlm05.free.fr/pb
Si vous voulez tester, prenez 2 de vos pc qui arrivent a communiquer en reseau (c'est le minimum
), lancer le serveur sur l'un sans modifier le code et modifier dans le client la ligne :
En mettant l'adresse de votre pc qui a lancé le serveur.
En fait, mon exemple va tenter de copier le fichier c:\windows\explorer.exe du pc SERVEUR vers le pc CLIENT quand vous cliquez 2 fois sur un fichier.
Si vous n’êtes pas bloqué, vous devriez arriver sur une fenêtre avec des transfert possible.
Si vous choisissez, a droite, d'aller dans C:\ puis essayer de cliquer sur un fichier, le transfert va s’exécuter.
Et la est le problème. Il va se lancer mais ne va jamais récupérer l’intégralité de explorer.exe. Il peut bloquer a 10Ko ou 500Ko, mais ne va jamais au bout.
En fait, je pense que le réseau (au boulot) est tellement lent (si, si, 5 Ko/s, c'est très lent) qu'il envoi bien le fichier sur le réseau, mais finit par se perdre.
Quelqu'un connaitrait une solution ?
Je sais, le sujet est très long, mais la, je sèche.
J'essaye depuis 1 semaine de faire un programme de transfert de fichier entre 2 machines en LAN.
Mon but est de transférer des fichiers d'une machine a une autre et inversement (autrement dit, client/serveur serveur/client)
Pour la connexion entre les 2, j'ai réussi sans trop de soucis.
Le soucis maintenant, c'est que le transfert de petit fichier fonctionne, mais le transfert d'un plus gros (j'ai testé sur 1 fichier de 1.7Mo) ne fonctionne pas.
Voici mes codes client/serveur (attention, c'est un peu long) :
Code serveur :
Code : Tout sélectionner
Enumeration
#reseau
#repertoire
#fichier
EndEnumeration
Global taille_buffer.l = 4096
Global Dim Drive_Nom.s(25),nombre_disque
Global adresse_ip_client.s
Global ConnexionID.l
Procedure GetAllDrives()
MaskDrive = GetLogicalDrives_()
Mask = 1
lpFileSystemNameBuffer.s = Space(256)
nombre_disque=0
For i.l = 65 To 97
If MaskDrive & Mask
wNom$=Chr(i)+":\"
wNom2$ = Chr(i) + ":"
wType=GetDriveType_(WNom$)
If wtype=#DRIVE_FIXED
nombre_disque=nombre_disque+1
Drive_Nom(nombre_disque)= wNom2$
EndIf
EndIf
Mask << 1
Next i
EndProcedure
Procedure.s enumere_repertoire(Directory$)
Protected Dim fichiers_dans_repertoire.s(10000)
Protected i_enumere.l = 0
Protected string_renvoyer.s = "|DD"
If ExamineDirectory(#repertoire, Directory$, "*.*")
While NextDirectoryEntry(#repertoire)
If DirectoryEntryType(#repertoire) = #PB_DirectoryEntry_File ; si fichier
fichiers_dans_repertoire(i_enumere) = DirectoryEntryName(#repertoire)
i_enumere + 1
Else ; si repertoire
If chiffre_depart = 0 And DirectoryEntryName(#repertoire) <> "."
string_renvoyer = string_renvoyer + "?d.."
chiffre_depart = 1
EndIf
If DirectoryEntryName(#repertoire) <> "."
string_renvoyer = string_renvoyer + "?d" + DirectoryEntryName(#repertoire)
EndIf
EndIf
Wend
FinishDirectory(#repertoire)
For x_enumere = 0 To i_enumere-1
string_renvoyer = string_renvoyer + "?f" + fichiers_dans_repertoire(x_enumere)
Next x_enumere
OpenFile(#fichier,"c:\test.txt")
WriteStringN(#fichier,string_renvoyer)
CloseFile(#fichier)
ProcedureReturn string_renvoyer
EndIf
EndProcedure
If InitNetwork() = 0
MessageRequester("Error", "Can't initialize the network !", 0)
End
EndIf
Port = 5900
*Buffer = AllocateMemory(taille_buffer)
If CreateNetworkServer(#reseau, Port)
MessageRequester("PureBasic - Server", "Server created (Port "+Str(Port)+").", 0)
Repeat
Delay(10)
SEvent = NetworkServerEvent()
If SEvent
ClientID = EventClient()
Select SEvent
Case #PB_NetworkEvent_Connect
ConnexionID = OpenNetworkConnection(IPString(GetClientIP(ClientID)), Port)
Case #PB_NetworkEvent_Data
FillMemory(*Buffer, taille_buffer)
ReceiveNetworkData(ClientID, *Buffer, taille_buffer)
If FindString(PeekS(*Buffer),"|chargeDD",1) = 1 ; si |chargeDD -> renvoi list des disque sur le pc
If ClientID
GetAllDrives()
drive_tempo.s = "|chargerDD"
For i=1 To nombre_disque
drive_tempo = drive_tempo + "|" + Drive_Nom(i)
Next i
SendNetworkString(ConnexionID, drive_tempo)
Else
MessageRequester("","pas de ConnectionID")
EndIf
EndIf
If FindString(PeekS(*Buffer),"|DD",1) = 1 ; si |DD -> renvoi list des disque sur le pc
SendNetworkString(ConnexionID,enumere_repertoire( Mid(PeekS(*Buffer),4,Len(PeekS(*Buffer))-3)))
EndIf
If FindString(PeekS(*Buffer),"|renvoi",1) = 1
fichier.s = "c:\windows\explorer.exe"
*buffer_fichier = AllocateMemory(FileSize(fichier) )
ReadFile(#fichier,fichier)
ReadData(#fichier,*buffer_fichier,FileSize(fichier) )
MessageRequester("",Str(FileSize(fichier)))
CloseFile(#fichier)
SendNetworkData(ConnexionID, *buffer_fichier, FileSize(fichier) )
EndIf
Case #PB_NetworkEvent_File
MessageRequester("PureBasic - Server", "Client "+Str(ClientID)+" has send a file via the network !", 0)
ReceiveNetworkFile(ConnexionID, "C:\TEST_Network.ftp3")
Case #PB_NetworkEvent_Disconnect
MessageRequester("PureBasic - Server", "Client "+Str(ClientID)+" has closed the connection...", 0)
Quit = 1
EndSelect
EndIf
Until Quit = 1
MessageRequester("PureBasic - Server", "Click to quit the server.", 0)
CloseNetworkServer(#reseau)
Else
MessageRequester("Error", "Can't create the server (port in use ?).", 0)
EndIf
End
Code CLIENT :
Code : Tout sélectionner
Enumeration
#reseau
EndEnumeration
Enumeration
#Window_transfert
EndEnumeration
Enumeration
#ListView_trans_pclocal
#Text_trans_pclocal
#Text_trans_pcdistant
#ListView_trans_pcdistant
#Text_trans_message
#ProgressBar_trans_fichier
#ProgressBar_trans_total
#Button_trans_envoi_fichier
#Button_trans_reception_fichier
EndEnumeration
Enumeration
#Font_Text_trans_pclocal
#Font_Text_trans_pcdistant
EndEnumeration
Enumeration
#fichier
EndEnumeration
; *********************** repertoire
Enumeration
#Window_transfert
EndEnumeration
Enumeration
#ListView_trans_pclocal
#Text_trans_pclocal
#Text_trans_pcdistant
#ListView_trans_pcdistant
#Text_trans_message
#ProgressBar_trans_fichier
#ProgressBar_trans_total
#Button_trans_envoi_fichier
#Button_trans_reception_fichier
#repertoire
EndEnumeration
Enumeration
#Font_Text_trans_pclocal
#Font_Text_trans_pcdistant
EndEnumeration
DataSection
Image_ButtonImage_1:
IncludeBinary ".\dossier.ico"
Image_ButtonImage_2:
IncludeBinary ".\fichier.ico"
EndDataSection
Global Port = 5900
Global Dim type_fichier.b(200000)
Global fichier_a_recuperer.s
Global ClientID.l
repertoire_de_depart.s = ""
Procedure OpenWindow_Window_transfert()
If OpenWindow(#Window_transfert, 0, 0, 683, 508, "Transferts", #PB_Window_SizeGadget|#PB_Window_TitleBar|#PB_Window_SystemMenu)
ExplorerListGadget(#ListView_trans_pclocal, 0, 30, 260, 415,"",#PB_Explorer_MultiSelect)
TextGadget(#Text_trans_pclocal, 75, 0, 100, 20, "PC LOCAL")
TextGadget(#Text_trans_pcdistant, 485, 5, 120, 20, "PC DISTANT")
ListIconGadget(#ListView_trans_pcdistant, 420, 30, 260, 415,"small icon",240,#PB_ListIcon_MultiSelect)
TextGadget(#Text_trans_message, 0, 445, 680, 20, "Message d'envoi", #PB_Text_Border|#PB_Text_Center)
ProgressBarGadget(#ProgressBar_trans_fichier, 0, 465, 680, 20, 0, 100, #PB_ProgressBar_Smooth)
ProgressBarGadget(#ProgressBar_trans_total, -5, 485, 685, 20, 0, 100, #PB_ProgressBar_Smooth)
ButtonGadget(#Button_trans_envoi_fichier, 270, 160, 140, 25, "Envoi des fichiers >>>")
ButtonGadget(#Button_trans_reception_fichier, 270, 220, 140, 25, "<<< Reception des fichiers")
; Gadget Fonts
SetGadgetFont(#Text_trans_pclocal, LoadFont(#Font_Text_trans_pclocal, "Microsoft Sans Serif", 14, #PB_Font_Bold|#PB_Font_HighQuality))
SetGadgetFont(#Text_trans_pcdistant, LoadFont(#Font_Text_trans_pcdistant, "Microsoft Sans Serif", 14, #PB_Font_Bold|#PB_Font_HighQuality))
EndIf
SetClassLong_(WindowID(#Window_transfert), #GCL_STYLE, GetClassLong_(WindowID(#Window_transfert), #GCL_STYLE) | #CS_DBLCLKS)
EndProcedure
Procedure.s repertoire_retour(repertoire$)
nom_temporaire.s
For k_1=1 To 70
If StringField(repertoire$, k_1, "\") = ""
For k_2 = 1 To k_1-2
nom_temporaire = nom_temporaire + StringField(repertoire$, k_2, "\")
nom_temporaire = nom_temporaire + "\"
Next k_2
ProcedureReturn nom_temporaire
EndIf
Next k_1
EndProcedure
Procedure lecteurs_initiaux(recup_init.s)
ClearGadgetItems(#ListView_trans_pcdistant)
drive.s
For i=3 To 26
drive = StringField(recup_init,i,"|")
If drive <> ""
AddGadgetItem(#ListView_trans_pcdistant,-1,drive,ImageID(CatchImage(#PB_Any, ?Image_ButtonImage_1)))
EndIf
Next i
EndProcedure
Procedure recuperation_fichier(valeur)
SetGadgetText(#Text_trans_message,"Envoi en cours")
WindowEvent()
transfert_fichier = 1
ReceiveNetworkFile(ClientID, "C:\TEST_Network.ftp3")
SetGadgetText(#Text_trans_message,Str( FileSize("C:\TEST_Network.ftp3") ) )
transfert_fichier = 0
EndProcedure
; **************** repertoire
Global taille_buffer.l = 4096
OpenWindow_Window_transfert()
If InitNetwork() = 0
MessageRequester("Error", "Can't initialize the network !", 0)
End
EndIf
*Buffer = AllocateMemory(taille_buffer)
ConnectionID = OpenNetworkConnection("10.19.10.1", Port) ; adresse ou l'on se connecte
If ConnectionID
SendNetworkString(ConnectionID, "|chargeDD")
Else
MessageRequester("PureBasic - Client", "Serveur distant introuvable.", 0)
End
EndIf
Global pour_test.l = 0
If CreateNetworkServer(#reseau, Port)
; MessageRequester("PureBasic - Server", "Server created (Port "+Str(Port)+").", 0)
EndIf
Repeat
Delay(10)
event = WindowEvent()
SEvent = NetworkServerEvent()
Select event
Case #PB_Event_CloseWindow
EventWindow = EventWindow()
If EventWindow = #Window_transfert
CloseWindow(#Window_transfert)
Quit = 1
EndIf
Case #WM_LBUTTONDBLCLK
If GetGadgetState(#ListView_trans_pcdistant) <> -1
If type_fichier(GetGadgetState(#ListView_trans_pcdistant)) = 0 ; (si repertoire)
If GetGadgetItemText(#ListView_trans_pcdistant,GetGadgetState(#ListView_trans_pcdistant)) <> ".." ; si pas ..
repertoire_de_depart = repertoire_de_depart + GetGadgetItemText(#ListView_trans_pcdistant,GetGadgetState(#ListView_trans_pcdistant)) + "\"
SendNetworkString(ConnectionID, "|DD" + repertoire_de_depart)
Else
repertoire_de_depart = repertoire_retour(repertoire_de_depart)
If Len(repertoire_de_depart) > 0
SendNetworkString(ConnectionID, "|DD" + repertoire_de_depart)
Else
SendNetworkString(ConnectionID, "|chargeDD")
EndIf
retour_attente:
SEvent = NetworkServerEvent()
If SEvent <> #PB_NetworkEvent_Data
Goto retour_attente
EndIf
EndIf
Else ; si fichier
MessageRequester("","reception")
fichier_a_recuperer = "|renvoi" + repertoire_de_depart + GetGadgetItemText(#ListView_trans_pcdistant,GetGadgetState(#ListView_trans_pcdistant))
SendNetworkString(ConnectionID, fichier_a_recuperer)
EndIf
EndIf
EndSelect
If SEvent
ClientID = EventClient()
Select SEvent
Case #PB_NetworkEvent_Connect
; MessageRequester("PureBasic - Server", "Connexion nouveau client ! " + Str(ConnectionID) + " Port :" + Str(GetClientPort(ConnectionID)), 0)
Case #PB_NetworkEvent_Data
; MessageRequester("","client - reception")
FillMemory(*Buffer,taille_buffer)
NbReAlloc = 1
res.l
Debug "********"
Repeat
res = ReceiveNetworkData(ClientID, *Buffer + ((NbReAlloc - 1) * taille_buffer), taille_buffer)
Debug res
; If res = taille_buffer
NbReAlloc + 1
*Buffer = ReAllocateMemory(*Buffer, NbReAlloc * taille_buffer)
; EndIf
Until NetworkServerEvent() <> #PB_NetworkEvent_Data
OpenFile(#fichier,"c:\fichier.txt")
FileSeek(#fichier,Lof(#fichier))
WriteString(#fichier,PeekS(*Buffer))
CloseFile(#fichier)
If FindString(PeekS(*Buffer),"|chargerDD")
lecteurs_initiaux(PeekS(*Buffer))
ElseIf FindString(PeekS(*Buffer),"|DD")
tempo.s = PeekS(*Buffer)
ClearGadgetItems(#ListView_trans_pcdistant)
For i = 2 To 10000
If StringField(tempo,i,"?") <> ""
If Mid( StringField(tempo,i,"?") , 1,1) = "d"
AddGadgetItem(#ListView_trans_pcdistant,-1,Mid( StringField(tempo,i,"?") , 2, Len( StringField(tempo,i,"?") )-1 ),ImageID(CatchImage(#PB_Any, ?Image_ButtonImage_1)))
EndIf
If Mid( StringField(tempo,i,"?") , 1,1) = "f"
type_fichier(i-2) = 1
AddGadgetItem(#ListView_trans_pcdistant,-1,Mid( StringField(tempo,i,"?") , 2, Len( StringField(tempo,i,"?") )-1 ),ImageID(CatchImage(#PB_Any, ?Image_ButtonImage_2)))
EndIf
EndIf
Next i
; FillMemory(*Buffer, taille_buffer)
EndIf
; FreeMemory(*Buffer)
Case #PB_NetworkEvent_File
MessageRequester("PureBasic - Server", "Client "+Str(ClientID)+" has send a file via the network !", 0)
CreateThread(@recuperation_fichier(),1)
Case #PB_NetworkEvent_Disconnect
MessageRequester("PureBasic - Server", "Client "+Str(ClientID)+" deconnecter du client.", 0)
Quit = 1
EndSelect
EndIf
Until Quit = 1
Si vous voulez tester, prenez 2 de vos pc qui arrivent a communiquer en reseau (c'est le minimum

Code : Tout sélectionner
ConnectionID = OpenNetworkConnection("10.19.10.1", Port) ; adresse ou l'on se connecte
En fait, mon exemple va tenter de copier le fichier c:\windows\explorer.exe du pc SERVEUR vers le pc CLIENT quand vous cliquez 2 fois sur un fichier.
Si vous n’êtes pas bloqué, vous devriez arriver sur une fenêtre avec des transfert possible.
Si vous choisissez, a droite, d'aller dans C:\ puis essayer de cliquer sur un fichier, le transfert va s’exécuter.
Et la est le problème. Il va se lancer mais ne va jamais récupérer l’intégralité de explorer.exe. Il peut bloquer a 10Ko ou 500Ko, mais ne va jamais au bout.
En fait, je pense que le réseau (au boulot) est tellement lent (si, si, 5 Ko/s, c'est très lent) qu'il envoi bien le fichier sur le réseau, mais finit par se perdre.
Quelqu'un connaitrait une solution ?
Je sais, le sujet est très long, mais la, je sèche.