当客户端断开连接时,dcom服务器出错

linux_client 2003-02-19 10:16:09
DCOM问题:
1、当打开客户端,激活DCOM服务器,
2、当最后一个客户端断开连接时,DCOM服务器关闭,此时出错:run time error 216 at 0043995D,有时候出现错误为:无效的窗口句柄
3、如果是先打开DCOM服务器,则不出现这一问题。


请大虾帮忙!

...全文
68 11 打赏 收藏 转发到动态 举报
写回复
用AI写文章
11 条回复
切换为时间正序
请发表友善的回复…
发表回复
猛禽 2003-02-20
  • 打赏
  • 举报
回复
要有耐心一会就出来了.^_^
linux_client 2003-02-20
  • 打赏
  • 举报
回复
呵呵,为什么我给的分数显示不出来
linux_client 2003-02-20
  • 打赏
  • 举报
回复
谢谢 Raptor!现在问题已经解决!

原来是这样的。我把服务器主窗体在服务器的登录窗体之后创建,因此,客户端要激活服务器,必须先激活登录窗体,因此必须先进入登录窗体,RDM才可以调用。这样用户必须登录服务器,客户端才能调用。具体如下:

Application.Initialize;

Application.CreateForm(TDataModule1, DataModule1);

//显示登录窗体

enterFrm := TenterFrm.Create(Application);
enterFrm.ShowModal;
if enterFrm.isLogin then
begin
enterFrm.Free;

Application.CreateForm(TmainFrm, mainFrm);
Application.CreateForm(TunRegDlg, unRegDlg);

Application.CreateForm(TsearchLogFrm, searchLogFrm);
Application.CreateForm(TconfigDlg, configDlg);
Application.CreateForm(TnewConfigFrm, newConfigFrm);
Application.Run;
end;

再次谢谢Raptor!也谢谢rwdx的参与。分数是Raptor 90分,rwdx10分
猛禽 2003-02-20
  • 打赏
  • 举报
回复
因为最后一个RDM释放前会检查引用计数器,如果为0,则退出程序,退出程序时的释放顺序是先释放FORM,再释放RDM,所以当最后一个客户端断开时,执行deleteUserRecord就会出错,因为这时FORM已经不存在了。但如果先执行中间层,引用计数至少为1,所以不会退出程序,当然也不会错了。
猛禽 2003-02-19
  • 打赏
  • 举报
回复
>我的RemoteModule引用到其它界面的一些变量,这会不会有关系?

跟这个有关系!运行时,RDM会根据每个客户端连接创建新的实例,其创建删除都是由客户端连接自动进行,其它界面的东东一般是固定的,所以二者交互时就会出问题
linux_client 2003-02-19
  • 打赏
  • 举报
回复
应用服务器里有一部分是关于注册表的,但不再remoteModule中.这应该没有关系,我把这部分取消了以后还是一样。

我的RemoteModule引用到其它界面的一些变量,这会不会有关系?


rwdx 2003-02-19
  • 打赏
  • 举报
回复
你的应用服务器里有没有什么特殊的代码
linux_client 2003-02-19
  • 打赏
  • 举报
回复
再次感谢Raptor的回复!

我的程序是一个监测客户端的在线情况。程序里只是是RDM用了FRM里的东东。共有两处,如果我把这两处注销掉,则一切OK。

我的调用具体如下:

1、procedure TLogin.RemoteDataModuleDestroy(Sender: TObject);
begin

mainFrm.deleteUserRecord(currentUserID); //当断开时,从主界面去掉该用户。
onlineUserCount := onlineUserCount-1;
end;

2、procedure TLogin.loginON(const userID, password, machineName,
ipNum: WideString; out isLogin, rUserName, userLevel, rUserPart,
isBirthDay: OleVariant);
begin
.............
mainFrm.insertNewUserRecord(userID,userName,machineName,ipNum);//此处,当用户登录的时候,加入到主界面的用户列表
...................
end;

procedure TmainFrm.insertNewUserRecord(userID, userName, machineName,
IPnum: wideString);
var
newMemberItem:TlistItem;
begin
newMemberItem := userList.Items.Insert(0);
newMemberItem.Caption := userID;
newMemberItem.SubItems.Add(userName);
newMemberItem.SubItems.Add(machineName);
newMemberItem.SubItems.Add(IPnum);
newMemberItem.SubItems.Add(dateTimeToStr(now()));
userList.Refresh;
end;

procedure TmainFrm.deleteUserRecord(userID: wideString);
var i:integer;
begin
for i:=0 to userList.Items.Count -1 do
begin
if userLIst.Items.Item[i].Caption = userID then
begin
userList.Items.Item[i].Delete;
userList.Refresh;
exit;
end
end;
end;

请帮我看一下,问题出在哪?本人不胜感激...
猛禽 2003-02-19
  • 打赏
  • 举报
回复
如果光是RDM用了FORM里的东东关系不大,但如果FORM里也用到了RDM里的东东就有关系了,因为FORM始终存在,都是可以访问的,但RDM在客户端断开时就释放了,如果这里FORM用了RDM里的东东就会出错
linux_client 2003-02-19
  • 打赏
  • 举报
回复
在这个例子里
procedure TLoginDemo.Login(const UserName, Password: WideString);
begin
{ Just add the UserName to the ListBox on Form1 and set the login flag to
true.}
Form1.ListBox1.Items.Add(UserName); //这里也调用到了Form1的界面元素呀?
FLoggedIn := True;
FUserName := UserName;
end;

linux_client 2003-02-19
  • 打赏
  • 举报
回复
Raptor,
谢谢你的回复!但是DELPHI自带的例子demos/midas/login/ 里的Server也是调用到了主界面的变量和控件,但其运行也是好的呀。

1,593

社区成员

发帖
与我相关
我的任务
社区描述
Delphi 网络通信/分布式开发
社区管理员
  • 网络通信/分布式开发社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧