各位大大,本人写的程序是这样的,由于源码太多太多,只能贴有问题的部分,请各位大大,帮忙解决:
操作过程:
选择lisview1的一个选项,listview1的显示方式为vsReport,点击按钮,向远程客户端发送连接命令,由于每一个项代表一个远程的客户端,所以点击该按钮
就代表操作该主机,此处为控制端代码:procedure TForm1.Button5Click(Sender: TObject);
begin  if form1.listview1.Selected <> nil then
  begin
    if listview1.Selected.SubItems.Objects[2] <> nil then
    begin
      showmessage('进程监控已经在运行了!');
      exit;
    end;
    spyitem:=form1.listview1.Selected;
    form1.Enabled:=false;
    sendcmd('014', edit5.text, True);   //  用一个在线套接字,发送消息
    beginspy:=false;
  end;
end;
然后
procedure TForm1.IdTCPServer1Execute(AThread: TIdPeerThread);
var
  RecCMD: string;  pitem:tlistitem;
  rs, ss: TMemoryStream;
  pCmd: array[0..SizeOf(TSpyCmd) - 1] of Byte;
  pBuf: array[0..8191] of Byte;
  Read, Size: Integer;
  //spyobjects:Tobjects;
begin   RecCMD := AThread.Connection.readln(EOL);
  //RecCMD := DecodeBase64(RecCMD);
  //showmessage(reccmd);
  if Length(RecCMD)>5 then Exit;  ... ...
   if AThread.Connection.Tag = 4 then //进程管理
  begin
    UserProc(AThread, RecCMD);
    Exit;
  end;
end;这是 userproc函数的相关代码:
procedure UserProc(AThread: TIdPeerThread; RecCMD: string);
 function getfilesize(str: string): string;
   {=======================进程管理=========================}
  if reccmd = '004' then         //进程管理
  begin
    athread.Connection.Tag:=4;   //此处为远程主机新建的一个套接字,标示为4
    //process_form.show;
    athread.data:=spyitem;
    tonlineinf(spyitem.data^).process_atrhread:=athread;
    athread.Synchronize(form1.show_process);    //sleep(100);
    //while athread.Connection.Connected do
    //begin
  end;
  if reccmd = '012' then         //进程管理
  begin
    if form1.readseverstream(athread,tempstr) then
    begin
      Temp_process:=tstringlist.Create;
      temp_process.Text:=tempstr;
      pitem:=tlistitem(athread.data);
      for i:=0 to temp_process.Count-1 do
      begin
      with tprocess_form(pitem.SubItems.Objects[2]).ListView1.Items.Add do
      begin
        Caption:= form1.centerstr(temp_process[i],'<pr_name>','</pr_name>');
        SubItems.Add(form1.centerstr(temp_process[i],'<pr_id>','</pr_id>'));
        SubItems.Add(form1.centerstr(temp_process[i],'<pr_path>','</pr_path>'));
      end;
      end;                             
      //showmessage(tempstr);    end;
    //end;
  end;
end;这是显示窗体的过程
procedure tform1.show_process;
var
  process_form:Tprocess_form;
begin
  process_form:=Tprocess_form.Create(self);
  //tonlineinf(spyitem.data^).process_atrhread.Data:=spyitem;
  spyitem.SubItems.Objects[2]:=process_form;
  process_form.pitem:=spyitem;  tonlineinf(spyitem.data^).process_atrhread.Connection.Write('004'+EOL);
  form1.Enabled:=true;
  process_form.Show;
end;在下搞不懂的是,点listview1第一个项,能正常工作,可是
点多了listview1项,偶尔会发现listview1某项的数据会被修改
请问如何解决:
listview1的数据结构
主机IP    标识ID    计算机名称   操作系统   
127.0.01   2037      winpc         winxp sp2
...
...
...执行上面操作的时候,会变成这样
主机IP    标识ID    计算机名称   操作系统   
127.0.01   (乱码或者没有数据)      winpc         winxp sp2
...
...
...
里面任决一列的数据都会被改写,改写的数据是随机的

解决方案 »

  1.   

    我明明没有写listview,为什么listview某一项数据被写了,有时还会报内存地址错误``  由于该项数据被改写,会导致我的客户端下线时,无法正常根据客户端下线时,删除相应的项``
      

  2.   

    线程绝对不能碰UI!!!!---这是天条不可触犯!两种方法解决:
     1.线程里Sendmessae,界面窗口来处理消息,刷新屏幕
     2.线程里必须用Synchronize 的方法来刷新屏幕!
      

  3.   

    问题找到了``经过跟踪调试, 指针出错了,
     我的指针指向的是动态数组的元素``  动态数组的内存空间是不连续的`` 
      也就是说动态数组的元素地址会随时变化,我指的时候是一个地址,经过一轮数据操作,元素的头地址会发生变化,指针却仍指向原来的地址,所以强制访问指针的话,指针所指向的内存,有可能是listview1的空间,所以listview1会出现乱码`` 
      贴上出错的代码```结构声明
    type // 服务器的会话信息。
      Tonlineinf = record
        ServerName: string[30];   {服务器主机名称}
        AThread : TIdPeerThread;  {服务器线程}
        Soc: integer;             {服务器线程ID}
        Online: Boolean;          {是否在线}
        ServerAdd: string[15];    {服务器IP地址}
        AdderStr: string;         {地理位置}
        spythread:TIdPeerThread;  {屏幕监控}
        process_atrhread:tidpeerthread;{进程监控}
        telnet_athread:tidpeerthread;{远程telnet}
        keyboard_athread:tidpeerthread;{键盘记录}
        data,data2:pointer;
    end;
    全局变量数组声明:
    OnlineServer: array of Tonlineinf;出错的过程
    procedure   UserProc(AThread:   TIdPeerThread;   RecCMD:   string); 
       if reccmd = '000' then
      begin    AThread.Connection.Tag := 0;
      enterCriticalSection(upline);
        j := -1;
        for i := 1 to OnlineCount do {查找是否有空白项}
        begin
          if not OnlineServer[i-1].Online then
          begin
            j := i - 1; {有,分配它}
            OnlineServer[j].Online := true; {置为在线}
            break;
          end;
        end;    if j = -1 then
        begin {无,新增一个}
          j := OnlineCount;
          inc(OnlineCount);
          Setlength(OnlineServer, OnlineCount);
          OnlineServer[j].Online := True; {置为在用}
        end;    OnlineServer[j].AThread :=AThread;
        onlineserver[j].spythread:=nil;
        onlineserver[j].process_atrhread:=nil;
        onlineserver[j].keyboard_athread:=nil;
        onlineserver[j].telnet_athread:=nil;
        OnlineServer[j].Soc := AThread.ThreadID ;
        OnlineServer[j].ServerAdd := AThread.Connection.Socket.Binding.PeerIP;
        OnlineServer[j].ServerName := AThread.Connection.Socket.Binding.PeerIP + '-' + inttoStr(AThread.ThreadID);    if form1.readseverstream(athread,tempstr) then
        begin
          with form1.ListView1.Items.Add do
          begin
            Caption:= AThread.Connection.Socket.Binding.PeerIP;
            SubItems.Add(inttostr(AThread.ThreadID));
            SubItems.Add(form1.centerstr(tempstr,'<host>','</host>'));
            SubItems.Add(form1.centerstr(tempstr,'<os>','</os>'));
            SubItems.Add('');
            SubItems.Add(form1.centerstr(tempstr,'<sp>','</sp>'));
            SubItems.Add(inttostr(AThread.ThreadID));
            data:=@OnlineServer[j];   //onlineserver为动态数组  //此处出错!!
            OnlineServer[j].data:=subitems;
            OnlineServer[j].data2:=data;
          end;
          //showmessage(tempstr);
        end;... ...
    end;