ARTSPConnection::performConnect函数完成RTSP流的连接

    xiaoxiao2021-03-25  149

    void ARTSPConnection::performConnect(const sp<AMessage> &reply, AString host, unsigned port) { //传递来的参数reply消息的引用,此消息的消息名为"conn",消息的处理者是MyHandler //调用gethostbyname(host.c_str()函数将AString类型表示的主机号转换成hostent类型的结构体,这是一个系统函数,没有深究,后面研究了的话会分享给大家 struct hostent *ent = gethostbyname(host.c_str()); if (ent == NULL) { ALOGE("Unknown host %s", host.c_str()); //如果ent的值为NULL说明无法完成转换,在reply消息的"result"字段设置错误码-ENOENT //该消息的消息名为"conn",消息的处理者是MyHandler,因此会在MyHandler::onMessageReceived的case "conn"处理分支处理 //在处理分支上会检查设置的"result"字段的错误码 reply->setInt32("result", -ENOENT); reply->post(); //连接不成功,将状态设置为DISCONNECTED mState = DISCONNECTED; return; } //调用系统函数socket创建一个网络套机字,并将返回的套接字描述符赋值给mSocket成员变量 //关于系统函数socket,大家可以在网上查一下相关资料的介绍 mSocket = socket(AF_INET, SOCK_STREAM, 0); if (mUIDValid) { HTTPBase::RegisterSocketUserTag(mSocket, mUID, (uint32_t)*(uint32_t*) "RTSP"); HTTPBase::RegisterSocketUserMark(mSocket, mUID); } //调用函数MakeSocketBlocking将创建的网络套接字设置为非阻塞状态,因为下面需要完成本地与主机的连接 MakeSocketBlocking(mSocket, false); //创建一个sockaddr_in类型的结构体remote //将remote结构体的sin_zero域内存清零,并设置相应的域 //关于sockaddr_in类型结构体的定义: /*struct sockaddr_in *{ * short sin_family;/*Address family一般来说AF_INET(地址族)PF_INET(协议族)*/ * unsigned short sin_port;/*Port number(必须要采用网络数据格式,普通数字可以用htons()函数转换成网络数据格式的数字)*/ * struct in_addr sin_addr;/*IP address in network byte order(Internet address)*/ * unsigned char sin_zero[8];/*Same size as struct sockaddr没有实际意义,只是为了 跟SOCKADDR结构在内存中对齐*/ *}; */ struct sockaddr_in remote; memset(remote.sin_zero, 0, sizeof(remote.sin_zero)); remote.sin_family = AF_INET; remote.sin_addr.s_addr = *(in_addr_t *)ent->h_addr; remote.sin_port = htons(port); //调用系统函数connect来完成RTSP流的连接,返回值err标识连接的状态 int err = ::connect( mSocket, (const struct sockaddr *)&remote, sizeof(remote)); //向reply消息设置"server-ip"字段,该字段的值是一个32位的整数 reply->setInt32("server-ip", ntohl(remote.sin_addr.s_addr)); if (err < 0) { //系统函数connect的返回值err小于零说明没有成功连接,进行相应的处理 //这里不分析具体的错误处理流程 //需要注意的是,连接不成功,需要调用close(mSocket)函数来关闭创建的套接字 if (errno == EINPROGRESS) { sp<AMessage> msg = new AMessage(kWhatCompleteConnection, this); msg->setMessage("reply", reply); msg->setInt32("connection-id", mConnectionID); msg->post(); return; } reply->setInt32("result", -errno); mState = DISCONNECTED; if (mUIDValid) { HTTPBase::UnRegisterSocketUserTag(mSocket); HTTPBase::UnRegisterSocketUserMark(mSocket); } close(mSocket); mSocket = -1; } else { //系统函数connect的返回值err大于等于零说明成功连接 //设置"result"字段的值为OK,状态mState设置为CONNECTED状态 //mNextCSeq的值设置为1,表示从序列号从1开始接收数据 reply->setInt32("result", OK); mState = CONNECTED; mNextCSeq = 1; //调用postReceiveReponseEvent()函数启动一个不断向服务端发送请求,接收服务端的响应并进行处里的这样一个循环 //具体的实现机制后续向大家介绍 postReceiveReponseEvent(); } //将reply消息发送出去,对该消息的处理是在MyHandler::onMessageReceived的case "conn"分支 reply->post(); }
    转载请注明原文地址: https://ju.6miu.com/read-2374.html

    最新回复(0)