代码之家  ›  专栏  ›  技术社区  ›  Ana Betts

socket.receiveMessageFrom()的端点参数是什么?

  •  3
  • Ana Betts  · 技术社区  · 15 年前

    我正在为iscsi编写一个代理应用程序来做一些诊断工作(想想fiddler for iscsi吧)-我试图一次捕获一个数据包,我不想读取任意大小的数据,最终得到一个和另一个的一半的数据包-我真的希望看到与wire相同的数据类型比如说鲨鱼。在做这个的时候,我用 Socket.ReceiveMessageFrom() .

    但是,其中一个参数被称为“endpoint”,我不太确定该如何处理它。有什么线索吗?这是我的密码,你能告诉我我是不是完全偏离了底线:

    Tuple<byte[], int> readOnePacket(TcpClient conn) {
        var flags = SocketFlags.None;
        EndPoint endpoint = null;   /*** You can't set this to null!! ***/
        byte[] buffer = new byte[10 * 0x100000];
        int offset = 0;
        int bytes_received;
    
        do {
            IPPacketInformation packet_information;
            bytes_received = conn.Client.ReceiveMessageFrom(buffer, offset, BufferSize,
                                                            ref flags, ref endpoint, out packet_information);
    
            if (flags == SocketFlags.Partial) {
                // We only want to transfer full packets
                offset = bytes_received;
                continue;
            }                        
        } while (false);
    
        return new Tuple<byte[], int>(buffer, bytes_received + offset );
    }
    
    2 回复  |  直到 12 年前
        1
  •  1
  •   Bertrand Marron    15 年前

    它不是tcpclient.receiveMessageFrom(),而是socket.receiveMessageFrom()

    如果你看看 documentation ,您将阅读以下内容:

    EndPoint ,通过引用传递, 表示远程服务器。

    编辑 : 设置为空确实是个坏主意。

        2
  •  1
  •   Haspemulator    12 年前

    虽然不是对你的问题的直接回答,但我认为这个答案仍然是有用的(尽管这个问题问了很久)。

    因为我不知道iscsi是通过tcp还是通过纯ip工作,所以我无法为您的问题提供解决方案。但一般来说,tcp是一种面向流的协议,没有“消息”的概念。另一方面,ip是一种面向数据报(即消息)的协议,它有消息的概念。在代码中,您试图从TCP套接字读取“消息”(IP构造),但这将不起作用。是的,TCP基于IP,但IP数据报在TCP级别上不可见。

    您提到的问题(读取完整消息,而不读取下一条消息)仅适用于TCP级别,因为在IP上您确实可以读取一条完整消息。当你想在tcp级别上做同样的事情时,你需要使用一个带有消息支持的协议。通常要实现这一点,您需要有自己的协议,基于TCP,消息如下:

    [消息头][消息正文]

    其中[msg header]包含如下内容:

    [消息类型][消息正文长度]

    msg type和msg body length有固定的长度(例如,msg type为2字节,body length为4字节),msg body可以有可变的长度,因此您可以读取完整的头,然后确定主体的长度,并基于读取的完整体。

    希望这有帮助。