Laden...

Länge eines byte[] bestimmen, den ein Socket schickt

Erstellt von icedre vor 17 Jahren Letzter Beitrag vor 17 Jahren 13.341 Views
I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren
Länge eines byte[] bestimmen, den ein Socket schickt

Hi,

also folgendes Problem:
Ein Sender schickt eine Nachricht in form eines byte Array's. Jetzt initialisiert der Empfänger einen neuen Stream:


Stream NeuerStream = TcpClient.GetStream();

Wenn ich nun die Nachricht abrufen will, muss ich ein neues byte Array erstellen, damit ich NeuerStream.Read() aufrufen kann... Jetzt würd ich gern wissen, wie groß das zu erstellende Array sein muss, damit ich nicht irgend eine Standard Größe nehmen muss (z.B. 256).
Wie kann ich raus finden, welche größe mein byte Array haben soll?
Vielen Dank für die Hilfe!

Gruss

F
722 Beiträge seit 2005
vor 17 Jahren

Stream.Length

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Unbehandelte Ausnahme: System.NotSupportedException: Dieser Stream unterstützt keine Suchvorgänge.

M
1.439 Beiträge seit 2005
vor 17 Jahren

NetworkStream.Socket.Available

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

^^
Ich arbeite mit einem System.IO.Stream, nicht mit einem System.Net.Sockets.NetworkStream....

M
1.439 Beiträge seit 2005
vor 17 Jahren

Dann änder halt deinen Code auf


NetworkStream NeuerStream = TcpClient.GetStream();

😁

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Also, TcpClient.GetStream() liefert mir als Rückgabewert einen NetworkStream, dann könnt ich auch folgendes machen:


TCPClient.GetStream().Length

Leider ohne Erfolg... selbe Fehlermeldung:


Unbehandelte Ausnahme: System.NotSupportedException: Dieser Stream unterstützt keine Suchvorgänge.

M
1.439 Beiträge seit 2005
vor 17 Jahren

Du sollst auch nicht die Länge abfragen! Das wird dir immer eine Exception werfen, denn Windows kann ja nicht hellsehen. Du kannst nur abfragen, wie viele Bytes im Empfangspuffer sind. und NetworkStream.Socket.Available scheint mir das zu bewerkstelligen.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Edit:
Also ich habs gerade mit dem NetworkStream versucht, da gibt es leider auch nur NetworkStream.Length, also kein NetworkStream.Socket.Available.
Bei dem Length steht in der Hilfe folgendes: "Die Länge der im Stream verfügbaren Daten. Diese Eigenschaft wird derzeit nicht unterstützt und löst eine NotSupportedException aus."
Was soll das??? Bin ich jetzt gezwungen .NET 2.0 zu benutzen, oder kann ich mein Problem anders lösen? - Vielen Dank für hilfreiche Vorschläge, P.S. ich benutz .NET 1.1 und VS 2003 Prof.

Gruss

Edit2:
Ich dachte, mit dem Length kann ich die Anzahl der Bytes abfragen, dass ich nicht schon im Voraus die Länge abrufe kann ist klar 😄...

M
1.439 Beiträge seit 2005
vor 17 Jahren

NetworkStream.Socket && Socket.Available gibt es bereits seit .Net 1.0...

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Also, kann es sein, dass ich dieses Available nicht hab, weill ich einen TcpClient benutze???

M
1.439 Beiträge seit 2005
vor 17 Jahren

TcpClient.Available gibts erst ab .Net 2.0.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Schade, hab ich mir's doch gedacht... trotzdem danke!
Was hab ich denn sonst noch für Möglichkeiten.... ?(

M
1.439 Beiträge seit 2005
vor 17 Jahren

Warum willst du nicht Socket.Available verwenden?

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Naja, weil ich jetzt die ganze Zeit mit TcpClient und TcpListener gearbeitet habe und das auch für mein Programm vollkommen reichen würde... Für diese kleine Funktion jetzt auf die Sockets zu swtichen 8o ... Die Sockets wären viel zu "mächtig" für mein Programm, das wäre mit Kanonen auf Spatzen geschossen...
Wenn ich keine andere Möglichkeit hab, muss ich ne Standardgröße definieren, z.B. 256, und werde dann den String anhand eines Terminierungssymbol trennen und dann erst ausgeben.... Naja, das wär ziemlich hässlich 🙁 ....

M
1.439 Beiträge seit 2005
vor 17 Jahren

Ich dachte du arbeitest (auch) mit einem (Network)Stream!?

M
1.439 Beiträge seit 2005
vor 17 Jahren

Btw.: Das Problem hat jedes Protokoll. Meistens wird am Anfang die Anzahl der Bytes übertragen, sodass der Client/Server weiß wie viel Bytes er lesen muss.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Jo, also wie oben beschrieben:
Stream NeuerStream = TcpClient.GetStream();
Ich erstell einen neuen Stream, mit dem ich die Nachricht empfang:
NeuerStream.Read(byteArray, 0, Länge_der_Bytes)
Jetzt hab ich eben noch die Methode Stream.ReadByte() gefunden, die gibt mir ne Zahl zurück, aber leider nicht die gesuchte Länge....


Stream.ReadByte-Methode 
Liest ein Byte aus dem Stream und erhöht die Position im Stream um ein Byte, oder gibt -1 zurück, wenn das Ende des Streams erreicht ist.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Original von marsgk
Ich dachte du arbeitest (auch) mit einem (Network)Stream!?

TcpClient.GetStream() liefert einen NetworkStream

M
1.439 Beiträge seit 2005
vor 17 Jahren

NetworkStream.Socket ist protected. Hab das übersehen.
Du kannst dir den Socket aber über TcpClient.Client holen und dann Socket.Available aufrufen.
Stream.ReadByte macht genau das, was der Name schon sagt. Die Methode ließt nur ein byte, mehr nicht.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Also ich kann dir leider in keinster Weise folgen.... TcpClient.Client kann ich nirgens finden...

P
157 Beiträge seit 2006
vor 17 Jahren

Schon mal die Hilfe bemüht? Bei mir werden 25 Ergebnisse gefunden 😉

Habe mir jetzt nicht alle angesehen aber zumindest der erste Eintrag zeigt das TcpClient.Client von den Frameworks 1.0, 1.1, 2.0 unterstützt wird.

Gruß
purplestar

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Original von purplestar
Schon mal die Hilfe bemüht? Bei mir werden 25 Ergebnisse gefunden 😉

Habe mir jetzt nicht alle angesehen aber zumindest der erste Eintrag zeigt das TcpClient.Client von den Frameworks 1.0, 1.1, 2.0 unterstützt wird.

Gruß
purplestar

Also, die Suche musst du mir unbedingt zeigen...
Ich bekomm leider nur folgendes:
* KLICK *

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

So... also hab gerade folgendes raus gefunden:


// Antwort in Buffer lesen
byte[] b = new byte[tcpClient.ReceiveBufferSize]; 
nwStream.Read(b, 0, (int) tcpClient.ReceiveBufferSize);
string returndata = Encoding.ASCII.GetString(bytes); 

Das ruft mir die Standardgröße ab... Und dann werd ich meinen String einfach trimmen

P
157 Beiträge seit 2006
vor 17 Jahren

Hallo icedre,

ich habe die Suche von meinem installiertem Visual Studio 2005 Standard verwendet. Mein Suchbegriff war 'TcpClient.Client'.

Du scheinst mittlerweile einen Weg gefunden zu haben Dein Problem zu lösen, viel Erfolg dabei 🙂

Gruß
purplestar

Original von icedre

Original von purplestar
Schon mal die Hilfe bemüht? Bei mir werden 25 Ergebnisse gefunden 😉

Habe mir jetzt nicht alle angesehen aber zumindest der erste Eintrag zeigt das TcpClient.Client von den Frameworks 1.0, 1.1, 2.0 unterstützt wird.

Gruß
purplestar

Also, die Suche musst du mir unbedingt zeigen...
Ich bekomm leider nur folgendes:

>

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

^^
Jo, hab es gerade in meinem VS 2003 gesucht und gefunden 👍
Vielen Dank! - Also, so wie ich das sehe erstellen die ne neue Klasse, die von TcpClient erbt, mit er man dann auf die Protected Methoden und Eigenschaften eines Socket zugreifen kann.... Ist das korrekt??? - Sorry, aber das Thema Vererbung mach ich leider erst...
Nochmal's Danke!

P
157 Beiträge seit 2006
vor 17 Jahren

Original von icedre
^^
...Also, so wie ich das sehe erstellen die ne neue Klasse, die von TcpClient erbt, mit er man dann auf die Protected Methoden und Eigenschaften eines Socket zugreifen kann.... Ist das korrekt??? - Sorry, aber das Thema Vererbung mach ich leider erst...
Nochmal's Danke!

Nicht ganz. Von der existierenden Klasse TcpClient wird eine Instanz erzeugt oder man sagt auch, ein Objekt instantiiert


TcpClient client = new TcpClient(server, port);

Wird ein Objekt von einer Klasse erzeugt erkennt man das immer an dem Schlüsselwort new.

Das sind wichtige Grundlagen, hier openbook: Praxis Objektorientierung, erfährst Du mehr.

Da Sockets verschiedene Protokolle bzw. Arten von Verbindungen verstehen, gibt es halt so Klassen wie TcpClient, die abgestimmt auf Tcp Clientverbindungen sind und mit diesen entsprechend umgehen können.

Auch zum Thema Sockets verrät Dir die Hilfe sehr viel mehr.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

So, also erstaml wieder vielen Dank... Zur Übersicht halber hier mal die ganze Idee:
Ich hab ein Server:


TcpListener Listener = new TcpListener(4788);
Listener.start();

Sobald eine neue Verbindung rein kommt, wird ein neuer TcpClient erstellt:


TcpClient Client = Listener.AcceptTcpClient();

Zu diesem Client soll nun der Stream erstellt werden:


Stream ClientStream = Client.GetStream ();

Damit jetzt keine Verwirrung entsteht:
Ich möchte jetzt eine Klasse erstellen, ganz nach dem folgendem Beispiel:


// This derived class demonstrates the use of three protected methods belonging to the TcpClient class
public class MyTcpClientDerivedClass : TcpClient{

// Constructor for the derived class.
public MyTcpClientDerivedClass() : base(){
}
public void UsingProtectedMethods(){

  // Uses the protected 'Active' property belonging to the TcpClient base class 
  // to determine if a connection is established. 
  if (this.Active){
      // Calls the protected 'Client' property belonging to the TcpClient base class.
      Socket s = this.Client;
      // Uses the Socket returned by Client to set an option that is not available using TcpClient.
      s.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.Broadcast, 1);
  }
  // To free all resources, calls the protected virtual method Dispose belonging to the TcpClient base class.
 this.Dispose(true);
 GC.SuppressFinalize(this);

}

}

Und anstatt des o.g.


TcpClient Client = Listener.AcceptTcpClient();

Möchte ich jetzt das hier machen:


MyTcpClientDerivedClass Client = Listener.AcceptTcpClient();

...
Wenn ich nun total falsch liege, bitte verbessert mich so gut wie es geht 😉
Vielen Dank!

Q
214 Beiträge seit 2006
vor 17 Jahren

Hallo,

Das ruft mir die Standardgröße ab... Und dann werd ich meinen String einfach trimmen

Das Problem an deiner Methode ist, dass die Standard-Buffer-Größe 8 KiB beträgt. Wenn du aber Daten sendest, die größer als 8 KiB sind, wie z.B. Fotos, so liest du nicht den gesamten Stream aus, sondern nur die ersten 8 KiB des Fotos.

Aber die Methode Read() gibt doch soweit ich weiß die Anzahl an gelesen Bytes zurück. Einfach eine Schleife laufen lassen, bis Read 0 (oder war es -1 🤔 ) zurückgibt und den Buffer dann z.B. in einer Arraylist zwischenspeichern.

Sonst je nach Art der zu empfangenen Daten ist StreamReader ganz praktisch.
Werden bei dir Befehle z.B. mit einem Zeilenumbruch abgeschlossen (bei vielen Protokollen ist dies der Fall), kannst du .ReadLine() benutzen, um so den gesamten Befehl zu erhalten.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

^^
Ich werd das mal mit Read() und der Schleife versuchen...
ReadLine hat ich zuerst benutzt, das reicht ber nicht aus.
Danke!

Edit:
Stream.Read() gibt die Anzahl der gelesenen Bytes zurück und genau das brauch ich schon vor dem Lesen :evil: Teufelskreis........

Q
214 Beiträge seit 2006
vor 17 Jahren

Hallo,
wie gesagt. Du musst halt solange in deinen Buffer lesen, bis Read keine Bytes mehr ausliest, und diesen Buffer dann in ein dynamischen Buffer (dynamische Speicherstruktur) (z.B. Arraylist oder unter .NET 2 besser ein List<byte>) abspeichern.
Nach diesem Auslesen steht in deiner Speicherstruktur alles was gesendet wurde.

B
1.529 Beiträge seit 2006
vor 17 Jahren

besser ein List<byte>

Besser nicht. Jedes Byte einzeln zu verwalten ist Ressourcen-Verschwendung.
Besser ist Queue<byte[]>. Dann hat man auch eine unabänderbare Eingangsreihenfolge.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Danke für die Antworten!
Also ich habs eben mal folgendermaßen versucht:


int i, j;
i=1;
j=1;
byte[] Nachricht = new byte[j];
while(Stream.Read(Nachricht, 0, i) == j)
{
  i++;
  j++;
  Nachricht = new byte[j];
}

Leider werden ja die Bytes sofort aus dem Buffer 'raus' geschrieben, also hat das so nicht funktioniert... Schade!
Ich muss noch weiter rum probieren... 🤔

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

So also ich bin hier echt am verzweifeln....
Hab jetzt den folgenden Algorithmus entworfen:


			System.Collections.ArrayList tempArrayList = new System.Collections.ArrayList();
			byte[] tempByte = new byte[1];
			while(ServerStream.Read(tempByte, 0, 1) > 0)
			{
				tempArrayList.Add(System.Text.Encoding.ASCII.GetString(tempByte));
				Console.Write(System.Text.Encoding.ASCII.GetString(tempByte));
			}

Ich bekomm meine Nachricht angezeigt, aber das Programm bleibt einfach "stehen", d.h. Code nach der while Schleife wird enfach nicht mehr ausgeführt, es bleibt einfach hängen.... wobei es doch bei -1 (gibt die Read() Funktion zurück, wenn der Stream leer ist) aus der Schleife gehen sollte....
Ich weiß leider keinen Rat mehr....

M
1.439 Beiträge seit 2005
vor 17 Jahren

ReadByte gibt -1 zurück, wenn man am Ende angelangt ist. Bei einem NetworkStream, dann wenn er geschlossen wird.

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

Ahhaa, also soll ich jetzt anstatt des Stream einen NetworkStream nehmen???
Danke!

Edit: Mit NetworkStream funktioniert es leider auch nicht, selbe Problem wie oben....

S
1.047 Beiträge seit 2005
vor 17 Jahren

kannst du mal irgendwie den vollständigen code posten?
verfolge das jettz shcon ne weile hier mit und frag mich echt wo das problem ist... nicht persönlich nehmen bitte

nachtrag:
probiers mal hiermit

TcpClient client = new TcpClient(...);
NetworkStream netStream = client.GetStream();
byte[] buffer = new byte[1024];

MemoryStream memStream = new MemoryStream(buffer.Length);

int numRead = 0;
do {
    numRead = netStream.Read(buffer, 0, buffer.Length);
    memStream.Write(buffer, 0, numRead);
} while (numRead > 0);
String text = Encoding.ASCII.GetString(memStream.GetBuffer(),0,(int)memStream.Length);
I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

@sheitman
Freut mich, dass du dich dafür interessierst...
Also, dafür muss ich ein wenig ausholen...
Meine Idee ist es, einen kleinen Instant Messenger zu schreiben, an dem sich die Clients im Netz registrieren. Dabei gibt es eine Server Anwendung, die auf einem bestimmten Port lauscht und die Anfragen der Clients entgegen nimmt: Ein Client verbindet sich zum Server, der Server gibt eine Antwort (in dem Fall einen String) und der Client gibt eine Rückantwort (mit seinen Infos, IP, Benutzernamen, usw.).
Die Grundidee hab ich von einem Bsp von MSDN:
* KLICK *

Dieses Beispiel bau ich nun nach meinen Bedürfnissen aus. Ich hab mal die Projektmappe hoch geladen. Darin ist eine Server Anwendung und eine Client Anwendung. Zum Testen muss zuerst der Server gestartet werden, dann kann man die Client Anwendung direkt aus Visual Studio debuggen.
Umgebungsdetails: Visual Studio 2003 Prof, .NET 1.1, Win 2000 Prof
Vielen Dank!

Hier die Projekt Datei:
* DOWNLOAD *

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

nachtrag:
probiers mal hiermit

TcpClient client = new TcpClient(...);
NetworkStream netStream = client.GetStream();
byte[] buffer = new byte[1024];

MemoryStream memStream = new MemoryStream(buffer.Length);

int numRead = 0;
do {
    numRead = netStream.Read(buffer, 0, buffer.Length);
    memStream.Write(buffer, 0, numRead);
} while (numRead > 0);
String text = Encoding.ASCII.GetString(memStream.GetBuffer(),0,(int)memStream.Length);

Dann hab ich aber das Problem mit der Standardgröße von 1024 und hab keine Dynamik...

S
1.047 Beiträge seit 2005
vor 17 Jahren

die 1024 sind nur für den puffer

die eigentlich nachricht wird zunächst in einem memorystream gespeichert... seine größe wächst dynamisch mit. nach der übertragung wird ja auch der inhalt vom memorystream bentuzt um die nachricht in text wieder umzuwandeln.

nachtrag:
ok, das hang wieder in der schleife, da ein kleiner deadlock vorhanden war...
der server wollte nach dem write sofort daten lesen, während der client aber auch nochmal daten lesen wollte, und read anscheinden nicht abbricht wenn keien daten vorhanden sind.. von daher tut es dieses nun

Client:

//Verbindung zum Server aufbauen
TcpClient client = new TcpClient("localhost", 4711);
//Hole den Stream für's lesen und schreiben
NetworkStream netStream = client.GetStream();
//Puffer für Nachrichtenteile
byte[] buffer = new byte[1024];
//Zwischenspeicher für die Nachricht im byte-Format
MemoryStream memStream = new MemoryStream(buffer.Length);
//Nachricht einlesen und zwischenspeichern
int numRead = 0;
do {
    numRead = netStream.Read(buffer, 0, buffer.Length);
    memStream.Write(buffer, 0, numRead);
} while (numRead > 0 && netStream.DataAvailable);
//Nachricht in String konvertieren
String text = Encoding.ASCII.GetString(memStream.ToArray());
Console.WriteLine("Nachricht vom Server: {0}", text);
//Client Infos an Server schicken
byte[] nachricht = Encoding.ASCII.GetBytes ("Benutzer_Info: " + Convert.ToString(IPAdresse()));
//Sende die Bytes zum Server
netStream.Write(nachricht, 0, nachricht.Length );
//Schließe die Verbindung zum Server
client.Close ();
Console.Write("\t Beenden... [ENTER]");
Console.ReadLine();

Server:

//Setze Flag für "Thread läuft"
this.running = true;
//Hole den Stream für's schreiben
NetworkStream ClientStream = this.TCPClient.GetStream ();
byte[] nachricht = Encoding.ASCII.GetBytes("Hallo");
//Sende die Bytes zum Client
ClientStream.Write(nachricht, 0, nachricht.Length);
ClientStream.Flush();
//Client Infos empfangen
byte[] buffer = new byte[1024];
//Zwischenspeicher für die Nachricht im byte-Format
MemoryStream memStream = new MemoryStream(buffer.Length);
//Nachricht einlesen und zwischenspeichern
int numRead = 0;
do {
    numRead = ClientStream.Read(buffer, 0, buffer.Length);
    memStream.Write(buffer, 0, numRead);
} while (numRead > 0 && ClientStream.DataAvailable);
//Wandle den Inhalt des Byte-Array in ein String um
string stringClientNachricht = Encoding.ASCII.GetString(memStream.ToArray());
//Gib die Nachricht des Servers auf der Console aus
Console.WriteLine(stringClientNachricht);
//Neuen Client mit den Infoes in die ClientListe rein schreiben
ClientListe.Add(stringClientNachricht);			
//Schließe die Verbindung zum Client
this.TCPClient.Close ();
//Setze das Flag "Thread läuft" zurück
this.running = false;

was noch eingebaut werden sollte ist exception management und verwendung von using()

edit:
noch paar fehler entfernt, servercode hinzugefügt

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

^^
Vielen Dank!
Ich werd es mal ausprobieren und Rückmeldung geben.
Fehler abfangen und Kosmetik kommt alles noch.. ist schließlich noch alles in der Beta Phase... 😁

Edit:
Also, das mit den 1024... Was ist, wenn im Stream mehr als 1024 drin sind???
Du kannst doch dann nur 1024 Bytes raus lesen, wenn du das byte Array mit 1024 erstellst...

S
1.047 Beiträge seit 2005
vor 17 Jahren

hab den code oben nochmal geändert, warn noch paar änderungen drin

also die 1024 bei memorystream bedeutet folgendes

Die Anfangsgröße des internen Arrays in Bytes.

buffer, das byte[1024] wird ja immer wieder benutzt
ich lese zeichen in buffer ein, und schreibe diese dann in den memorystream,
dann les ich wieder zeichen in buffer ein und schreib sie wieder in den memory stream, usw.

von daher ist dir größe von buffer unwichtig... deine daten landen erstmal alle im memorystream
mit dem wird dann weiter gearbeitet....

probier es mit einer längern nachrichtaus, wirst sehen es funktioniert...
mach schrittweises durchgehen mit dem debuger und schau dir den inhalt an... oder les mal ein buch für dateioperationen^^

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

^^
So, alles klar! Hab's mir gerade genauer angeschaut!
Super, vielen Dank für die Mühe!

Ich hab's jetzt folgendermaßen gemacht:
Anstatt auf die -1 von Read() zu warten, ist die Abbruchbedingung NetworkStream.DataAvailable.
Funktioniert 1A!:


			System.Collections.ArrayList tempArrayList = new System.Collections.ArrayList();
			byte[] tempByte = new byte[1];
			while(ServerStream.DataAvailable)
			{
				ServerStream.Read(tempByte, 0, 1);
				tempArrayList.Add(System.Text.Encoding.ASCII.GetString(tempByte));
				Console.Write(System.Text.Encoding.ASCII.GetString(tempByte));
			}

Nochmals Danke!

S
1.047 Beiträge seit 2005
vor 17 Jahren

Ich hab's jetzt folgendermaßen gemacht:
Anstatt auf die -1 von Read() zu warten, ist die Abbruchbedingung NetworkStream.DataAvailable.

würd ich nicht machen... hatte ich auch so gehabt aber da kam es zu problemen

das problem ist, das du die abfrage machst ob daten verfügbar sind und ein false zurück bekommst, wei lder server noch nicht so weit war um zu senden...

deshalb hab ich auch keine while schleife genommen sondern eine do schleife
das read wartet so lange bis daten ankommen, damit wäre das problem der zeit schon mal gelöst

um nun den deadlock zu verhindern das client und server beide lesen ha bich das dataavailable in di eabbruchbedingung der do...while schleife mit rein gebaut

also ich würds so lassen wie ich es gepostet hab, weil anders gabs bei mir ab und an probleme 🙂

nachtrag:
seh gerade das du ja deine alte schleife weiterhin benutzt... hät ich mir die mühe auch sparen können 🙁

nagut, mal ne anmerkung zu deiner schleife:
es ist unsinnig mit einem byte array der länge 1 zu arbeiten, weil es auch eine methode gibt die nur das nächste byte ausliest...
dann ist es eh unsinnig byteweise auszulesen, der networkstream hat einen internen lesebuffer von 8kbyte... d.h. du kansnt locker immer ein paar kbyte gleichzeitig abfragen... genau das was ich mit dem buffer gemacht habe

I
icedre Themenstarter:in
106 Beiträge seit 2006
vor 17 Jahren

^^
Also, die Methode, die da oben von mir steht ist nicht die, die ich verwende, dass war nur mal so ein Gedankengang vonmir...
Natürlich ist es sinnvoller immer gleich mehr bytes auszulesen, aber dann werden auch immer gleich die Leerzeilen mit gelsen und das soll ja vermieden werden...
Deswegen mach ich es im Moment so, dass ich als Abbruchbedingung das DataAvailable in einer do...while Schleife benutze und mit den Stream byte-Weise auslese.
Gruss

A
28 Beiträge seit 2006
vor 17 Jahren
Tcp

Ich sehe das der Artikel schon alt ist - aber falls es doch noch wen interessiert...

Ich habe auch so meine Probleme mit dem TcpListener gehabt ... ic bin umgestiegen auf den TcpChannel/HttpChannel
kann sein das es den erst seit 2005 gibt... aber er ist mit der Handhabung (finde ich) viel einfacher...

MFG Thomas