Frage

Ich verwende Indy 9 mit Delphi 5. In meiner Anwendung, die ich mit einem Netzwerkgerät über UDP kommunizieren wollen. So verwende ich UDPServer comp. in einer Klasse, die aus TThread abgeleitet ist. Als ich in dem folgenden Code ähnlich schreibe dann die CPU-Auslastung beträgt 100%.

im Thread:

while not terminated do begin
  if GetMessage(Msg, 0, 0, 0) then begin
    if Msg.message = WM_UDPMSG then
      Break
    else
      DispatchMessage(Msg);
  end;
end;

und OnUDPRead Ereignis:

  try    
    // Processing the data here
  except
    PostThreadMessage(ThreadId, WM_UDPMSG, 0, 0);
  end;

Wenn ich Sleep-Funktion in der while-do-Schleife oder in OnUDPRead Ereignis verwenden, gibt es keine Änderung. Immer noch die CPU-Auslastung beträgt 100%.

Meine Thread-Priorität ist normal.

Wie kann ich mein Problem lösen?

War es hilfreich?

Lösung

Das Problem, das Sie haben, ist, weil Sie die UDP-Daten in dem GUI-Thread sind empfangen, wollen aber die Daten in einem anderen Thread zu verarbeiten.

Das eigentliche Problem ist, dass Ihre eine asynchrone Komponente in einer blockierenden Art und Weise zu nutzen versuchen. Die bessere Lösung wäre eine echte Blockierung UDP Kommunikationsbibliothek zu verwenden, wie Synapse . Dann ist es sehr leicht, einfach wartet auf neue Daten in Ihrem Thread zu erhalten.

Sie könnten nur schreiben:

while not Terminated do
begin
  BytesRead := FSocker.RecvBufferEx(@(Buffer[0]), BufferSize, Timeout);
  if (BytesRead = 0) then
  begin
    // continue or exit if the receiving Failed
    case FSocket.LastError of
      0, WSAETIMEDOUT: Continue;
      WSAECONNRESET, WSAENETRESET,
        WSAENOTCONN, WSAECONNABORTED,
        WSAENETDOWN:
        begin
          CloseConnection;
          Exit;
        end;
    else
      CloseConnection;
      Exit;
    end;    
  end;
  // process the data in the buffer
end;

Andere Tipps

Ich bin nicht intim mit delphi-Code, aber Sie sind ein Besetzt warten Mechanismus, der Ihre CPU ist das Schleifen.

Die Einführung verbirgt sich ein Schlaf oder eine Verzögerung der Schleife nur das Problem. Ich schlage vor, mit einer besseren Methode für Ihre Nachrichten / Ereignisse zu empfangen. Viele Lösungen existieren, wie die Beobachter-Listener Muster oder Schemata fädeln warten und benachrichtigen.


Einige hilfreiche Links in Reaktion auf Ihren Kommentar:

1 Sie eine Version von Indy benötigen neuer als 9.0.0.18, denke ich. Größere haben show-stopping Threading-Bugs. Dazu gehören auch alle Versionen von Indy geliefert mit Delphi bis Version 7.

2 Werfen Sie einen Blick auf dem Beispielcode, wie mit Indy zu arbeiten.

http://www.indyproject.org/demos/index.html

Gibt es eine Version von GetMessage, die wartet (blockiert den Thread), bis eine Nachricht eintrifft?

Ich weiß nicht, die Version von Massage. Aber es erklärt in Windows.pas wie folgt

function GetMessage; external user32 name 'GetMessageA';

Dieses Projekt ist sehr großes Projekt. So aktualisieren Indy ist schwierig für mich. Aber wenn Sie sicher, dass das Problem wegen der alten Version von Indy ist, werde ich es aktualisieren.

Ich habe auf all Indy-Demos sieht. Diese Demos sind sehr einfach. In meinem Projekt habe ich sehr schnelle Datenübertragung. (Wie Echtzeit-Audio-Recorder)

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top