ネットワークに悩まされているプログラムを書きました。マルチスレッドで使用しました。問題はスレッド出力です。プログラムは混合です。また、出力が正しく表示されません。
2 つのサンプル プログラムを作成しましたが、どちらも正しく動作しません。
プログラム 1
unit Unit1;
interface
uses
Windows, Classes, IdBaseComponent, IdComponent, IdTCPConnection, IdTCPClient,
IdRawBase,IdRawClient, IdIcmpClient, Messages, SysUtils, Variants, Graphics, Controls, Forms,
Dialogs,StdCtrls,ExtCtrls;
type
TPSThread=class(TThread)
protected
procedure execute; override;
end;
type
TForm1 = class(TForm)
Button1: TButton;
Edit1: TEdit;
Edit2: TEdit;
Edit3: TEdit;
Edit4: TEdit;
Edit5: TEdit;
Memo1: TMemo;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
Procedure WndProc(var Message: TMessage); Override;
{ Public declarations }
end;
var
Form1: TForm1;
PortG:Integer;
HostG:string;
FormG:TForm;
WM_Msg_PS:DWORD;
implementation
{$R *.dfm}
procedure TPSThread.execute;
var
IcmpClient:TIdIcmpClient;
TCPClient:TIdTCPClient;
HostT:string;
PortT:Integer;
ActiveServer:Boolean;
begin
inherited;
HostT:=HostG;
PortT:=PortG;
IcmpClient:= TIdIcmpClient.Create();
try
with IcmpClient do
begin
ReceiveTimeout := 5000;
Protocol := 1;
ProtocolIPv6 := 0;
PacketSize := 1024;
Host:=HostT;
end;
IcmpClient.Ping(HostT,Random(1024));
if IcmpClient.ReplyStatus.BytesReceived=0 then
begin
SendMessage(FormG.Handle, WM_Msg_PS, Integer(HostT+'*'+IntToStr(1)+'#'), 0);
ActiveServer:=False;
end
else
ActiveServer:=True;
finally
IcmpClient.Free;
end;
if ActiveServer then
begin
TCPClient:=TIdTCPClient.Create(nil);
try
with TCPClient do
begin
Host:=HostT;
Port:=PortT;
try
Connect;
try
IOHandler.WriteLn('salam');
SendMessage(FormG.Handle, WM_Msg_PS, Integer(HostT+'*'+IntToStr(2)+'#'), 0);
finally
Disconnect;
end;
except
SendMessage(FormG.Handle, WM_Msg_PS, Integer(HostT+'*'+IntToStr(3)+'#'), 0);
end;
end;
finally
TCPClient.Free;
end;
end;
end;
procedure PS_System(FormNameForMessage:TForm;HostP:string;PortP:Integer);
var
PSThread:TPSThread;
begin
HostG:=HostP;
PortG:=PortP;
FormG:=FormNameForMessage;
PSThread:=TPSThread.Create(false);
PSThread.FreeOnTerminate:=true;
PSThread.Resume;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
Memo1.Clear;
PS_System(form1,Edit1.Text,4321);
PS_System(form1,Edit2.Text,4321);
PS_System(form1,Edit3.Text,4321);
PS_System(form1,Edit4.Text,4321);
PS_System(form1,Edit5.Text,4321);
end;
procedure TForm1.WndProc(var Message: TMessage);
var Id:byte;
Ip:string;
begin
if Message.Msg= WM_Msg_PS then
begin
Ip:=copy(String(Message.WParam),1,pos('*',String(Message.WParam))-1);
id:=strtoint(copy(String(Message.WParam),pos('*',String(Message.WParam))+1,(pos('#',String(Message.WParam))-pos('*',String(Message.WParam))-1)));
case id of
1:
begin
Memo1.Lines.Add(' Server '+ip+' Is inactive ');
//ShowMessage(' Server '+ip+' Is inactive ');
end;
2:
begin
Memo1.Lines.Add(' Message was sent successfully to server '+ip);
//ShowMessage(' Message was sent successfully to server '+ip);
end;
3:
begin
Memo1.Lines.Add(' Send message to the server fails '+ip);
//ShowMessage(' Send message to the server fails '+ip);
end;
end;
end;
inherited;
end;
end.
プログラム 2
unit Unit1;
interface
uses
Windows, Classes, IdBaseComponent, IdComponent, IdTCPConnection, IdTCPClient,
IdRawBase,IdRawClient, IdIcmpClient, Messages, SysUtils, Variants, Graphics, Controls, Forms,
Dialogs,StdCtrls,ExtCtrls;
type
TPSThread=class(TThread)
protected
procedure execute; override;
end;
type
TForm1 = class(TForm)
Button1: TButton;
Edit1: TEdit;
Edit2: TEdit;
Edit3: TEdit;
Edit4: TEdit;
Edit5: TEdit;
Memo1: TMemo;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
PortG:Integer;
HostG:string;
WM_Msg_PS:DWORD;
implementation
{$R *.dfm}
procedure IsInactiveServer(M:string);
begin
Form1.Memo1.Lines.Add(' Server '+M+' Is inactive ');
//ShowMessage(' Server '+M+' Is inactive ');
end;
procedure SentSuccessfullyToServer(M:string);
begin
Form1.Memo1.Lines.Add(' Message was sent successfully to server '+M);
//ShowMessage(' Message was sent successfully to server '+M);
end;
procedure SendMessageFails(M:string);
begin
Form1.Memo1.Lines.Add(' Send message to the server fails '+M);
//ShowMessage(' Send message to the server fails '+M);
end;
procedure TPSThread.execute;
var
IcmpClient:TIdIcmpClient;
TCPClient:TIdTCPClient;
HostT:string;
PortT:Integer;
ActiveServer:Boolean;
begin
inherited;
HostT:=HostG;
PortT:=PortG;
IcmpClient:= TIdIcmpClient.Create();
try
with IcmpClient do
begin
ReceiveTimeout := 5000;
Protocol := 1;
ProtocolIPv6 := 0;
PacketSize := 1024;
Host:=HostT;
end;
IcmpClient.Ping(HostT,Random(1024));
if IcmpClient.ReplyStatus.BytesReceived=0 then
begin
IsInactiveServer(HostT);
ActiveServer:=False;
end
else
ActiveServer:=True;
finally
IcmpClient.Free;
end;
if ActiveServer then
begin
TCPClient:=TIdTCPClient.Create(nil);
try
with TCPClient do
begin
Host:=HostT;
Port:=PortT;
try
Connect;
try
IOHandler.WriteLn('salam');
SentSuccessfullyToServer(HostT);
finally
Disconnect;
end;
except
SendMessageFails(HostT);
end;
end;
finally
TCPClient.Free;
end;
end;
end;
procedure PS_System(HostP:string;PortP:Integer);
var
PSThread:TPSThread;
begin
HostG:=HostP;
PortG:=PortP;
PSThread:=TPSThread.Create(false);
PSThread.FreeOnTerminate:=true;
PSThread.Resume;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
Memo1.Clear;
PS_System(Edit1.Text,4321);
PS_System(Edit2.Text,4321);
PS_System(Edit3.Text,4321);
PS_System(Edit4.Text,4321);
PS_System(Edit5.Text,4321);
end;
end.
ありがとう しかし、私の問題は ping ではありません 私の問題は送信メッセージです。また、スレッド送信メッセージにも干渉します。部品があれば、ping を削除します。ここでも追加の問題があります。