小弟编写了一个实时传送信息软件。遇到一个小问题。
问题:就是客户端与服务端连接上以后,在客户端输入传送的消息后,按回车发送消息!(发送消息是由回车来触发的)问题就出现了(刚编译好时,在本地机上没有出现什么问题,在两台机子上调试时,就出现“list index out of bounds(1)"错误。以后连在本地机上也会出现这样问题。)我怀疑是服务器接受客户端的消息时出现的错误。本程序在win2000和delphi6编译
服务器端:
unit Unit1;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, ScktComp, ComCtrls, StdCtrls;type
TForm1 = class(TForm)
m1: TMemo;
Label4: TLabel;
edtSend: TEdit;
Label1: TLabel;
btnSend: TButton;
Label2: TLabel;
Label3: TLabel;
cbxID: TComboBox;
btnOneSend: TButton;
S1: TStatusBar;
Server: TServerSocket;
procedure ServerAccept(Sender: TObject; Socket: TCustomWinSocket);
procedure ServerClientConnect(Sender: TObject;
Socket: TCustomWinSocket);
procedure ServerClientRead(Sender: TObject; Socket: TCustomWinSocket);
procedure ServerClientDisconnect(Sender: TObject;
Socket: TCustomWinSocket);
procedure ServerClientError(Sender: TObject; Socket: TCustomWinSocket;
ErrorEvent: TErrorEvent; var ErrorCode: Integer);
procedure btnSendClick(Sender: TObject);
procedure btnOneSendClick(Sender: TObject);
procedure FormCreate(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;var
Form1: TForm1;implementation{$R *.dfm}procedure TForm1.ServerAccept(Sender: TObject; Socket: TCustomWinSocket);
var
TempStr:pchar;//指向字符的指针
begin
TempStr:=pchar('欢迎来到聊天室 '#13#10);
socket.SendText(TempStr);
TempStr:=pchar('######################################'#13#10);
socket.SendText(TempStr);
TempStr:=pchar('你发送所有的消息将发给所有在线的用户'#13#10);
socket.SendText(Tempstr);
end;procedure TForm1.ServerClientConnect(Sender: TObject;
Socket: TCustomWinSocket);
var
strIp,strHost:string;
Count:Integer;
begin
strIp:=Socket.RemoteAddress;
strHost:=Socket.RemoteHost;
M1.Lines.Add('有人加入聊天室,来自:');
M1.Lines.Add(#9'SocketID:'+Inttostr(Socket.SocketHandle)); cbxID.Items.Add(Inttostr(Socket.SocketHandle));
M1.Lines.Add(#9'IP地址:'+strIp);
M1.Lines.Add(#9'主机名:'+strHost);
Count:=Server.Socket.ActiveConnections;
S1.Panels.Items[1].Text:='在线人数:'+IntToStr(Count);
end;procedure TForm1.ServerClientRead(Sender: TObject;//务器接受客户端的消息
Socket: TCustomWinSocket);
var
p:pchar;
length:longint;
Count,i:Integer;
//sbuf:string;begin
p:=nil;
//p:=AllocMem(socket.ReceiveLength);
while socket.ReceiveLength>0 do begin Getmem(p,length); //分配内存
try
length:=socket.ReceiveLength;//了解到达缓冲区的字节数
socket.ReceiveBuf(p^,socket.ReceiveLength); //接受信息
Count:=Server.Socket.ActiveConnections; //转发信息
for i:=0 to Count-1 do
Server.Socket.Connections[1].SendBuf(p^,length);
finally
FreeMem(p);
end;
end;
end;procedure TForm1.ServerClientDisconnect(Sender: TObject;
Socket: TCustomWinSocket);
var
Count:Integer;
IDIndex:Integer;begin
M1.Lines.Add('用户离线');
M1.Lines.Add(' SocketID:'+Inttostr(Socket.SocketHandle));
IDIndex:=cbxID.Items.IndexOf(Inttostr(socket.SocketHandle));
cbxID.Items.Delete(IDIndex); //在ID记录中清除
//this event happens before user leave
Count:=Server.Socket.ActiveConnections-1;
S1.Panels.Items[1].Text:='在线用户:'+IntToStr(Count);
end;procedure TForm1.ServerClientError(Sender: TObject;
Socket: TCustomWinSocket; ErrorEvent: TErrorEvent;
var ErrorCode: Integer);
begin
//Eroor Conditions
Case ErrorCode of
10054:M1.Lines.Add('one connection is reset by remote side.');//处理错误情况
Else
M1.Lines.Add('发生错误,错误代码:'+InttoStr(errorCode));
end;
ErrorCode:=0; //消除错误代码end;procedure TForm1.btnSendClick(Sender: TObject);
var
i:integer;
Count:Integer;
begin
Count:=Server.Socket.ActiveConnections;
for i:=0 to Count-1 do
Server.Socket.Connections[i].SendText(edtSend.Text);//信息转发end;procedure TForm1.btnOneSendClick(Sender: TObject);
var
ID:Integer;
Socket:TCustomWinSocket;
begin
if cbxID.Text ='' then
begin
application.MessageBox('没有指定要发送的用户','提示',mb_ok+mb_iconinformation);
abort;
end;
//Create a socket with exist socket handle
ID:=strtoint(cbxID.text);
//create a socket with exist socket handle
Socket:=TCustomWinSocket.Create(ID);//根据Socket对象创建连接
Socket.SendText(EdtSend.Text);
end;procedure TForm1.FormCreate(Sender: TObject);
begin
//start server when application run
Server.Active:=true;
S1.Panels.Items[0].Text :='服务器启动的主机名:' + Server.Socket.LocalHost+' 端口:'+inttostr(Server.Port);
self.Caption:=S1.Panels.Items[0].Text;
Application.Title:=S1.Panels.Items[0].Text;
S1.Panels.Items[1].Text:='在线人数:'+IntToStr(Server.Socket.ActiveConnections);
end;end.
问题:就是客户端与服务端连接上以后,在客户端输入传送的消息后,按回车发送消息!(发送消息是由回车来触发的)问题就出现了(刚编译好时,在本地机上没有出现什么问题,在两台机子上调试时,就出现“list index out of bounds(1)"错误。以后连在本地机上也会出现这样问题。)我怀疑是服务器接受客户端的消息时出现的错误。本程序在win2000和delphi6编译
服务器端:
unit Unit1;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, ScktComp, ComCtrls, StdCtrls;type
TForm1 = class(TForm)
m1: TMemo;
Label4: TLabel;
edtSend: TEdit;
Label1: TLabel;
btnSend: TButton;
Label2: TLabel;
Label3: TLabel;
cbxID: TComboBox;
btnOneSend: TButton;
S1: TStatusBar;
Server: TServerSocket;
procedure ServerAccept(Sender: TObject; Socket: TCustomWinSocket);
procedure ServerClientConnect(Sender: TObject;
Socket: TCustomWinSocket);
procedure ServerClientRead(Sender: TObject; Socket: TCustomWinSocket);
procedure ServerClientDisconnect(Sender: TObject;
Socket: TCustomWinSocket);
procedure ServerClientError(Sender: TObject; Socket: TCustomWinSocket;
ErrorEvent: TErrorEvent; var ErrorCode: Integer);
procedure btnSendClick(Sender: TObject);
procedure btnOneSendClick(Sender: TObject);
procedure FormCreate(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;var
Form1: TForm1;implementation{$R *.dfm}procedure TForm1.ServerAccept(Sender: TObject; Socket: TCustomWinSocket);
var
TempStr:pchar;//指向字符的指针
begin
TempStr:=pchar('欢迎来到聊天室 '#13#10);
socket.SendText(TempStr);
TempStr:=pchar('######################################'#13#10);
socket.SendText(TempStr);
TempStr:=pchar('你发送所有的消息将发给所有在线的用户'#13#10);
socket.SendText(Tempstr);
end;procedure TForm1.ServerClientConnect(Sender: TObject;
Socket: TCustomWinSocket);
var
strIp,strHost:string;
Count:Integer;
begin
strIp:=Socket.RemoteAddress;
strHost:=Socket.RemoteHost;
M1.Lines.Add('有人加入聊天室,来自:');
M1.Lines.Add(#9'SocketID:'+Inttostr(Socket.SocketHandle)); cbxID.Items.Add(Inttostr(Socket.SocketHandle));
M1.Lines.Add(#9'IP地址:'+strIp);
M1.Lines.Add(#9'主机名:'+strHost);
Count:=Server.Socket.ActiveConnections;
S1.Panels.Items[1].Text:='在线人数:'+IntToStr(Count);
end;procedure TForm1.ServerClientRead(Sender: TObject;//务器接受客户端的消息
Socket: TCustomWinSocket);
var
p:pchar;
length:longint;
Count,i:Integer;
//sbuf:string;begin
p:=nil;
//p:=AllocMem(socket.ReceiveLength);
while socket.ReceiveLength>0 do begin Getmem(p,length); //分配内存
try
length:=socket.ReceiveLength;//了解到达缓冲区的字节数
socket.ReceiveBuf(p^,socket.ReceiveLength); //接受信息
Count:=Server.Socket.ActiveConnections; //转发信息
for i:=0 to Count-1 do
Server.Socket.Connections[1].SendBuf(p^,length);
finally
FreeMem(p);
end;
end;
end;procedure TForm1.ServerClientDisconnect(Sender: TObject;
Socket: TCustomWinSocket);
var
Count:Integer;
IDIndex:Integer;begin
M1.Lines.Add('用户离线');
M1.Lines.Add(' SocketID:'+Inttostr(Socket.SocketHandle));
IDIndex:=cbxID.Items.IndexOf(Inttostr(socket.SocketHandle));
cbxID.Items.Delete(IDIndex); //在ID记录中清除
//this event happens before user leave
Count:=Server.Socket.ActiveConnections-1;
S1.Panels.Items[1].Text:='在线用户:'+IntToStr(Count);
end;procedure TForm1.ServerClientError(Sender: TObject;
Socket: TCustomWinSocket; ErrorEvent: TErrorEvent;
var ErrorCode: Integer);
begin
//Eroor Conditions
Case ErrorCode of
10054:M1.Lines.Add('one connection is reset by remote side.');//处理错误情况
Else
M1.Lines.Add('发生错误,错误代码:'+InttoStr(errorCode));
end;
ErrorCode:=0; //消除错误代码end;procedure TForm1.btnSendClick(Sender: TObject);
var
i:integer;
Count:Integer;
begin
Count:=Server.Socket.ActiveConnections;
for i:=0 to Count-1 do
Server.Socket.Connections[i].SendText(edtSend.Text);//信息转发end;procedure TForm1.btnOneSendClick(Sender: TObject);
var
ID:Integer;
Socket:TCustomWinSocket;
begin
if cbxID.Text ='' then
begin
application.MessageBox('没有指定要发送的用户','提示',mb_ok+mb_iconinformation);
abort;
end;
//Create a socket with exist socket handle
ID:=strtoint(cbxID.text);
//create a socket with exist socket handle
Socket:=TCustomWinSocket.Create(ID);//根据Socket对象创建连接
Socket.SendText(EdtSend.Text);
end;procedure TForm1.FormCreate(Sender: TObject);
begin
//start server when application run
Server.Active:=true;
S1.Panels.Items[0].Text :='服务器启动的主机名:' + Server.Socket.LocalHost+' 端口:'+inttostr(Server.Port);
self.Caption:=S1.Panels.Items[0].Text;
Application.Title:=S1.Panels.Items[0].Text;
S1.Panels.Items[1].Text:='在线人数:'+IntToStr(Server.Socket.ActiveConnections);
end;end.
是指相应的客户机连接 index号
问题是不是出现在没有用缓存?
请高手能不能讲的再清楚的!谢谢
Server.Socket.Connections[i].SendText(edtSend.Text);//信息转发这句话会出问题。可能会出现找不到第i号客户机的情况