7.物联网LWIP之DNS,超时机制,组播,广播

一。DNS域名解析

1.DNS作用

2.DNS API

(1)宏开关

//opt.h
/**
 * LWIP_DNS==1: Turn on DNS module. UDP must be available for DNS
 * transport.
 */

#if !defined LWIP_DNS || defined __DOXYGEN__
#define LWIP_DNS                        1
#endif

(2)配置DNS服务器

<1>dns.c添加代码

//dns.c 需要手动添加
/** DNS server IP address */
#ifndef DNS_SERVER_ADDRESS
extern ip4_addr_t gw;   //网关地址
#define DNS_SERVER_ADDRESS(ipaddr)        (memcpy(ipaddr, &gw, sizeof(ip4_addr_t)))
#endif

#ifdef DNS_SERVER_ADDRESS
  /* initialize default DNS server address */
  ip_addr_t dnsserver;
  DNS_SERVER_ADDRESS(&dnsserver);
  dns_setserver(0, &dnsserver);
#endif /* DNS_SERVER_ADDRESS */

<2>lwip.c修改代码

/**
  * LwIP initialization function
  */
void MX_LWIP_Init(void)
{
  /* IP addresses initialization */
	..........
  /* IP addresses initialization without DHCP (IPv4) */
  IP4_ADDR(&ipaddr, IP_ADDRESS[0], IP_ADDRESS[1], IP_ADDRESS[2], IP_ADDRESS[3]);
  IP4_ADDR(&netmask, NETMASK_ADDRESS[0], NETMASK_ADDRESS[1] , NETMASK_ADDRESS[2], NETMASK_ADDRESS[3]);
  IP4_ADDR(&gw, GATEWAY_ADDRESS[0], GATEWAY_ADDRESS[1], GATEWAY_ADDRESS[2], GATEWAY_ADDRESS[3]);  
  /* Initilialize the LwIP stack with RTOS */
  tcpip_init( NULL, NULL );
   ...............
}

<3>gethostbyname

//netdb.h
/** @ingroup netdbapi */
#define gethostbyname(name) lwip_gethostbyname(name)
struct hostent *lwip_gethostbyname(const char *name);
struct hostent {
    char  *h_name;      /* 正式主机名 */
    char **h_aliases;   /* 主机别名*/
    int    h_addrtype;  /* 主机IP地址类型 */
    int    h_length;    /* 主机IP地址字节长度*/
    char **h_addr_list; /* 主机的IP地址列表*/
};

3.实验:实现DNS解析

二。心跳及超时机制实现

1.setsocketopt

//功能说明:  
/*
获取或者与某个套接字关联的选 项。选项可能存在于多层中,它们总会出现在最上面的套接字层。当操作套接字选项时,选项位于的层和选项的名称必须给出。为了操作套接字层的选项,应该 将层的值指定为SOL_SOCKET。为了操作其它层的选项,控制选项的合适协议号必须给出。例如,为了表示一个选项由协议解析,层应该设定为协议 号TCP。
*/
//函数原型
int getsockopt(int sock, int level, int optname, void *optval, socklen_t *optlen);
int setsockopt(int sock, int level, int optname, const void *optval, socklen_t optlen);
//参数:  
/*
sock:将要被设置或者获取选项的套接字。
level:选项所在的协议层。
optname:需要访问的选项名。
optval:对于getsockopt(),指向返回选项值的缓冲。对于setsockopt(),指向包含新选项值的缓冲。
optlen:对于getsockopt(),作为入口参数时,选项值的最大长度。作为出口参数时,选项值的实际长度。对于setsockopt(),现选项的长度。
*/
//返回说明:  
成功执行时,返回0。失败返回-1
    
//参数详细说明:
/*
level指定控制套接字的层次.可以取三种值:
1)SOL_SOCKET:通用套接字选项.
2)IPPROTO_IP:IP选项.
3)IPPROTO_TCP:TCP选项. 

选项名称        说明                     数据类型
=====================================================================
            SOL_SOCKET
---------------------------------------------------------------------
SO_BROADCAST      允许发送广播数据            int
SO_DEBUG        允许调试                int
SO_DONTROUTE      不查找                   int
SO_ERROR        获得套接字错误             int
SO_KEEPALIVE      保持连接                int
SO_LINGER        延迟关闭连接              struct linger
SO_OOBINLINE      带外数据放入正常数据流         int
SO_RCVBUF        接收缓冲区大小             int
SO_SNDBUF        发送缓冲区大小             int
SO_RCVLOWAT       接收缓冲区下限             int
SO_SNDLOWAT       发送缓冲区下限             int
SO_RCVTIMEO       接收超时                struct timeval
SO_SNDTIMEO       发送超时                struct timeval
SO_REUSERADDR      允许重用本地地址和端口        int
SO_TYPE         获得套接字类型               int
SO_BSDCOMPAT      与BSD系统兼容            int
========================================================================
            IPPROTO_IP
------------------------------------------------------------------------
IP_HDRINCL       在数据包中包含IP首部          int
IP_OPTINOS       IP首部选项               int
IP_TOS         类型
IP_TTL         生存时间                  int
========================================================================
            IPPROTO_IP
------------------------------------------------------------------------
TCP_MAXSEG       TCP最大数据段的大小           int
TCP_NODELAY       不使用Nagle算法               int
=====================================================================


*/
 

2.心跳检测

网线掉了怎么办?

3.TCP Keepalive

(1)setsockopt参数


#define SO_KEEPALIVE   0x0008  /* 保持连接 */                   val = int
#define TCP_KEEPIDLE   0x03    /* 发送心跳空闲周期 S*/           val = int
#define TCP_KEEPINTVL  0x04    /* 发送心跳间隔 S */              val = int
#define TCP_KEEPCNT    0x05    /* 心跳重发次数 */                val = int

(2)宏开关

/**
 * LWIP_TCP_KEEPALIVE==1: Enable TCP_KEEPIDLE, TCP_KEEPINTVL and TCP_KEEPCNT
 * options processing. Note that TCP_KEEPIDLE and TCP_KEEPINTVL have to be set
 * in seconds. (does not require sockets.c, and will affect tcp.c)
 */
#if !defined LWIP_TCP_KEEPALIVE || defined __DOXYGEN__
#define LWIP_TCP_KEEPALIVE              0
#endif

三。组播与广播基础知识

1.组播,广播区分

2.组播与广播实现

注意必须使能项

#if !defined LWIP_IGMP || defined __DOXYGEN__
#define LWIP_IGMP                       1
#endif

(1)广播实现

//SOL_SOCKET
#define SO_BROADCAST   0x0020 /* 广播许可 */                
//val = int

(2)组播实现

//IPPROTO_IP
#define IP_ADD_MEMBERSHIP  3    /*加入组播*/
#define IP_DROP_MEMBERSHIP 4    /*退出组播*/
#define IP_MULTICAST_IF    6    /*组播默认网卡选择*/
#define IP_MULTICAST_LOOP  7    /*组播默认回环*/

//val
typedef struct ip_mreq {
    struct in_addr imr_multiaddr; /* IP multicast address of group */
    struct in_addr imr_interface; /* local IP address of interface */
} ip_mreq;

四。wireshark抓包验证

1.wireshark抓包工具

2.wireshark安装

3.wireshark使用

(1)使用流程

        选择网卡---》过滤配置

(2)过滤器使用方法

<1>比较运算符

    eq, ==    Equal
    ne, !=    Not Equal
    gt, >     Greater Than
    lt, <     Less Than
    ge, >=    Greater than or Equal to
    le, <=    Less than or Equal to

<2>协议字段

#以太网过滤
eth.dst eq ff:ff:ff:ff:ff:ff
#IP地址过滤
ip.dst eq 192.168.1.10
ip.src == 192.168.1.1
#TCP过滤
tcp.port == 6666
# UDP过滤
udp.port == 6666
# http过滤
http.request.method == "POST"

<3>位域操作

# TCP SYN
tcp.flags & 0x02

<4>逻辑表达式

    and, &&   Logical AND
    or,  ||   Logical OR
    not, !    Logical NOT
   # tcp.port == 80 and ip.src == 192.168.2.1

你可能感兴趣的:(物联网)