Linux ping c实现

        linux下ping程序的c实现

#include <stdio.h>
#include <stdlib.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <stdint.h>
#include <netdb.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <string.h>
#include <sys/time.h>
#include <errno.h>#define DATA_SIZE 32#define pri_debug printf
#define pri_error printftypedef struct tag_icmp_header
{u_int8_t  type;u_int8_t  code;u_int16_t check_sum;u_int16_t id;u_int16_t seq;
} icmp_header;typedef struct tag_iphdr
{u_int8_t        ip_head_verlen;u_int8_t        ip_tos;unsigned short  ip_length;unsigned short  ip_id;unsigned short  ip_flags;u_int8_t        ip_ttl;u_int8_t        ip_protacol;unsigned short  ip_checksum;int             ip_source;int             ip_destination;
} ip_header;unsigned short generation_checksum(unsigned short * buf, int size)
{unsigned long cksum = 0;while(size > 1){cksum += *buf++;size -= sizeof(unsigned short);}if(size){cksum += *buf++;}cksum =  (cksum>>16) + (cksum & 0xffff);cksum += (cksum>>16);return (unsigned short)(~cksum);
}double get_time_interval(struct timeval * start, struct timeval * end)
{double interval;struct timeval tp;tp.tv_sec = end->tv_sec - start->tv_sec;tp.tv_usec = end->tv_usec - start->tv_usec;if(tp.tv_usec < 0){tp.tv_sec -= 1;tp.tv_usec += 1000000;}interval = tp.tv_sec * 1000 + tp.tv_usec * 0.001;return interval;
}int ping_host_ip(const char * domain)
{int i;int ret = -1;int client_fd;int size = 50 * 1024;struct timeval timeout;char * icmp;in_addr_t dest_ip;icmp_header * icmp_head;struct sockaddr_in dest_socket_addr;if(domain == NULL){pri_debug("ping_host_ip domain is NULL!\n");return ret;}dest_ip = inet_addr(domain);if(dest_ip == INADDR_NONE){struct hostent* p_hostent = gethostbyname(domain);if(p_hostent){dest_ip = (*(in_addr_t*)p_hostent->h_addr);}}client_fd = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);if (client_fd == -1){pri_error("socket error: %s!\n", strerror(errno));return ret;}timeout.tv_sec = 1;timeout.tv_usec = 0;setsockopt(client_fd, SOL_SOCKET, SO_RCVBUF, &size, sizeof(size));if(setsockopt(client_fd, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(struct timeval))){pri_error("setsocketopt SO_RCVTIMEO error!\n");return ret;}if(setsockopt(client_fd, SOL_SOCKET, SO_SNDTIMEO, &timeout, sizeof(struct timeval))){pri_error("setsockopt SO_SNDTIMEO error!\n");return ret;}dest_socket_addr.sin_family = AF_INET;dest_socket_addr.sin_addr.s_addr = dest_ip;dest_socket_addr.sin_port = htons(0);memset(dest_socket_addr.sin_zero, 0, sizeof(dest_socket_addr.sin_zero));icmp = (char *)malloc(sizeof(icmp_header) + DATA_SIZE);memset(icmp, 0, sizeof(icmp_header) + DATA_SIZE);icmp_head = (icmp_header *)icmp;icmp_head->type = 8;icmp_head->code = 0;icmp_head->id = 1;pri_debug("PING %s (%s).\n", domain, inet_ntoa(*((struct in_addr*)&dest_ip)));for(i = 0; i < 3; i++){struct timeval start;struct timeval end;long result;struct sockaddr_in from;socklen_t from_packet_len;long read_length;char recv_buf[1024];icmp_head->seq = htons(i);icmp_head->check_sum = 0;icmp_head->check_sum = generation_checksum((unsigned short*)icmp,sizeof(icmp_header) + DATA_SIZE);gettimeofday(&start, NULL);result = sendto(client_fd, icmp, sizeof(icmp_header) +DATA_SIZE, 0, (struct sockaddr *)&dest_socket_addr,sizeof(dest_socket_addr));if(result == -1){pri_debug("PING: sendto: Network is unreachable\n");continue;}from_packet_len = sizeof(from);memset(recv_buf, 0, sizeof(recv_buf));while(1){read_length = recvfrom(client_fd, recv_buf, 1024, 0,(struct sockaddr*)&from, &from_packet_len);gettimeofday( &end, NULL );if(read_length != -1){ip_header * recv_ip_header = (ip_header*)recv_buf;int ip_ttl = (int)recv_ip_header->ip_ttl;icmp_header * recv_icmp_header = (icmp_header *)(recv_buf +(recv_ip_header->ip_head_verlen & 0x0F) * 4);if(recv_icmp_header->type != 0){pri_error("error type %d received, error code %d \n", recv_icmp_header->type, recv_icmp_header->code);break;}if(recv_icmp_header->id != icmp_head->id){pri_error("some else's packet\n");break;}if(read_length >= (long)(sizeof(ip_header) +sizeof(icmp_header) + DATA_SIZE)){pri_debug("%ld bytes from %s (%s): icmp_seq=%d ttl=%d time=%.2f ms\n",read_length, domain, inet_ntoa(from.sin_addr), recv_icmp_header->seq / 256,ip_ttl, get_time_interval(&start, &end));ret = 0;// 证明网络通畅,后续的包已经不许再需要验证goto PING_EXIT;}break;}else{pri_error("receive data error!\n");break;}}}PING_EXIT:if(NULL != icmp){free(icmp);icmp = NULL;}if(client_fd != -1){close(client_fd);}return ret;
}int main(int argc, char **argv)
{ping_host_ip(argv[1]);
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1544527.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

LoongArch 个人赛一级评测(前递旁路+load阻塞)

目录 LoongArch 个人赛一级评测&#xff08;前递旁路load阻塞&#xff09;声明测试说明 代码修改thinpad_top.vconver_ram.vIF_stage 测试自动评测在线实验 踩坑记录读写使能控制inout类端口的使用方法Vivado生成Bit流文件时出现[Synth 8-91] ambiguous clock in event control…

file zilla server安装以后,client连接,账号登录成功,但是读取目录失败的处理

1、下载 2、连接 开始一直报错&#xff0c;server1.9.1的版本&#xff0c;后来直接下载了汉化版本进行安装&#xff1a; 服务端 - FileZilla中文网 3、报错&#xff1a;登录正常&#xff0c;但是读取目录失败&#xff0c;一开始也是这个错误&#xff0c;后来改成安装低版本的&a…

python之装饰器、迭代器、生成器

装饰器 什么是装饰器&#xff1f; 用来装饰其他函数&#xff0c;即为其他函数添加特定功能的函数。 装饰器的两个基本原则&#xff1a; 装饰器不能修改被装饰函数的源码 装饰器不能修改被装饰函数的调用方式 什么是可迭代对象&#xff1f; 在python的任意对象中&#xff…

Mac使用技巧-来自苹果专人在线辅导服务3

真的太喜欢上苹果专人在线辅导课程了&#xff01;每次感觉都满满收获&#xff01; 目录 一、手势 1.1三指拖移 1.2四指上推 1.3五指快速进入启动台 二、程序坞里的app 1.如何将程序坞中不需要/不常用的app移除&#xff1f; 2.当鼠标放在将程序坞中app时&#xff0c;图标…

到底该不该做副业?这些真相你必须知道!零基础入门到精通,收藏这一篇就够了

天哪&#xff01;根据最新调查显示&#xff0c;超过60%的职场人士正在考虑或已经开始从事副业。 那么&#xff0c;究竟该不该做副业&#xff1f; 第一部分&#xff1a;副业的好处 1. 增加收入 做副业最直接的好处就是可以增加收入。 在经济压力日益增大的今天&#xff0c;…

STMCubeMx——C8T6的串口调试、接收与发送

一、stmCubeMX串口通信的步骤 1、新建一个文件&#xff0c;选择自己的芯片 2、配置时钟 3、配置串口 串口的模式解析可以跳转到以下文章查看 stmCubemx——配置串口时的几种模式-CSDN博客在STM32CubeMX中配置串口&#xff08;USART或UART&#xff09;时&#xff0c;可以设置…

Python连接Kafka并收发数据

目录 一、Kafka 二、发送端&#xff08;生产者&#xff09; 三、接收端&#xff08;消费者&#xff09; 一、Kafka Apache Kafka 是一个开源流处理平台&#xff0c;由 LinkedIn 开发&#xff0c;并于 2011 年成为 Apache 软件基金会的一部分。Kafka 广泛用于构建实时的数据…

soul怎么改ip地址归属地

在数字化时代&#xff0c;社交应用已成为人们日常生活中不可或缺的一部分。Soul&#xff0c;作为一款深受年轻人喜爱的社交APP&#xff0c;以其独特的灵魂社交理念和丰富的互动功能吸引了大量用户。然而&#xff0c;在使用Soul的过程中&#xff0c;不少用户会关注到一个问题——…

详解Web测试和APP测试的区别

&#x1f345; 点击文末小卡片&#xff0c;免费获取软件测试全套资料&#xff0c;资料在手&#xff0c;涨薪更快 最近听到有些朋友说&#xff0c;移动端要比web端稍微难一些&#xff0c;涉及到的细节笔记要多&#xff0c;有转去做web测试的想法&#xff0c;看看在具体测试的…

华为全联接大会2024 | 一文回顾华为云开发者联盟重磅干货

目录 华为开发者空间预置更多工具资源&#xff0c;带来丰富场景案例 携手鲲鹏、鸿蒙、昇腾等根生态&#xff0c;使能开发者创新 学习体验、内容体系全面升级&#xff0c;助力开发者高效学习根技术 参与丰富线上体验活动&#xff0c;赢取精美礼品 在刚刚结束的华为全联接大会…

基于Netty框架的云快充协议+云快充1.5协议+云快充桩直连+桩直连协议

云快充协议云快充1.5协议云快充1.6云快充协议开源代码云快充底层协议云快充桩直连桩直连协议充电桩协议云快充源码 介绍 云快充协议云快充1.5协议云快充1.6云快充协议开源代码云快充底层协议云快充桩直连桩直连协议充电桩协议云快充源码 软件架构 1、提供云快充底层桩直连协…

智能Ai语音机器人的应用价值有哪些?

随着时间的推移&#xff0c;人工智能的发展越来越成熟&#xff0c;智能时代也离人们越来越近&#xff0c;近几年人工智能越来越火爆&#xff0c;人工智能的应用已经开始渗透到各行各业&#xff0c;与生活交融&#xff0c;成为人们无法拒绝&#xff0c;无法失去的一个重要存在。…

Java项目: 基于SpringBoot+mybatis+maven医疗病历交互系统(含源码+数据库+毕业论文)

一、项目简介 本项目是一套基于SpringBootmybatismaven医疗病历交互系统 包含&#xff1a;项目源码、数据库脚本等&#xff0c;该项目附带全部源码可作为毕设使用。 项目都经过严格调试&#xff0c;eclipse或者idea 确保可以运行&#xff01; 该系统功能完善、界面美观、操作简…

全球网安行业缺少350万安全专家? 志愿你别乱填,缺的是专家,不是0经验的牛马

0x00 首先是这个所谓的“高需求”。企业们天天喊着缺人&#xff0c;但当你打开招聘网站&#xff0c;看到的全是“三年经验起步”、“高级专家”。黑人问号&#xff1f;这是在逗我吗&#xff1f;都只想要高级专家&#xff0c;拒绝新手及应届生&#xff0c;没有新手&#xff0c;哪…

舒服了!学大模型必看的学习书籍来了

最近整理了日前市面上一大波大模型的书&#xff0c;已经打包成pdf了&#xff0c;大家有需要的&#xff0c;可以自行添加获取&#xff0c;纯福利&#xff0c;无套路&#xff0c;添加后说明是哪本书&#xff0c;会直接给大家&#xff01;&#xff08;文末获取&#xff09; 部分书…

用于体积医学图像分割的跨视角差异依赖网络|文献速递--基于多模态-半监督深度学习的病理学诊断与病灶分割

Title 题目 Cross-view discrepancy-dependency network for volumetric medical image segmentation 用于体积医学图像分割的跨视角差异依赖网络 01 文献速递介绍 医学图像分割的目标是通过为每个像素分配语义类别&#xff0c;从原始图像中描绘出受试者的解剖结构&#x…

Activiti7《第九式:破气式》——流畅驱动工作流进程。面试题大全

冲冲冲&#xff01;开干 这篇文章将分为九个篇章&#xff0c;带你逐步掌握工作流的核心知识。“破气式”&#xff0c;代表着工作流中的 无形之力&#xff0c;它是贯穿整个流程的 关键驱动 不知不觉已经到了独孤九剑最后一式了&#xff0c;我相信到这里之后各位都已经出神入化…

华为HarmonyOS灵活高效的消息推送服务(Push Kit) -- 10 推送实况窗消息

场景介绍 实况窗是一种帮助用户聚焦正在进行的任务&#xff0c;方便快速查看和即时处理的通知形态。有关实况窗简介、权限申请、开放场景、设计规范等说明&#xff0c;请参见Live View Kit简介。 通过Push Kit发送的实况窗消息支持三种操作类型&#xff0c;分别是&#xff1a…

云手机推荐:五款热门云手机测评!

在云手机市场中&#xff0c;各个品牌层出不穷&#xff0c;让人难以选择。为了帮助你更好地找到适合的云手机应用&#xff0c;我们整理了五款最受欢迎的云手机进行测评。2024年&#xff0c;哪款云手机是你的不二之选&#xff1f;且慢下结论&#xff0c;看看这五款云手机的真实表…

分享一个非常好用的图片压缩的免费网址,及使用方式

一、图片压缩网址&#xff1a; TinyPNG – Compress WebP, PNG and JPEG images intelligently 二、使用方式&#xff08;压缩后的图片在1M以内&#xff09; 1、上传图片 二&#xff0c;下载压缩图片 备注&#xff1a;只能免费压缩5M以内的图片&#xff01;