首页 > 编程语言 >物联网项目-温湿度之 TCP 协议包C#版

物联网项目-温湿度之 TCP 协议包C#版

时间:2023-09-10 10:07:33浏览次数:43  
标签:Convert string 16 C# 温湿度 TCP ToString byte data

0、背景

本协议包参考车联网TCP 组包格式,C#写测试客户端。

1、代码

主函数

static void Main(string[] args)
        {
            //TestData.LoginData();
            //TestData.PostData();
            //Console.ReadLine();
            //return;
            byte[] re;
            
            MyTcpClient.Connect();
            
            
            Console.WriteLine("输入任意字符并回车用以发送登录数据 >");
            Console.ReadLine();
            //send//向服务器端发送消息
            re = System.Text.Encoding.ASCII.GetBytes(TestData.LoginData());
            //re = StringTool.strToToHexByte(TestData.LoginData());
            MyTcpClient.SendMsg(re);
            Console.WriteLine("登录发送完毕");
            Console.WriteLine("输入任意字符并回车用以发送检测数据 >");
            Console.ReadLine();
            for(int i = 0; i < 5; i++)
            {
                //re = StringTool.strToToHexByte(TestData.PostData());
                re = System.Text.Encoding.ASCII.GetBytes(TestData.PostData());
                MyTcpClient.SendMsg(re);
                Thread.Sleep(2000);//不加这个会粘包
            }
            Console.WriteLine("输入任意字符并回车用以发送检测数据 >");
            Console.ReadLine();
            //客户端发送消息登出 主动关闭连接
        }

Tcp Client

public class MyTcpClient
    {
        static int defaultPort = 7738;
        static string defaultIp = "10.1.31.31";

        private static Socket clientSocket = null;
        private static Thread thread = null;
        /// <summary>
        /// 连接服务器端
        /// </summary>
        public static void Connect()
        {
            int.TryParse(System.Configuration.ConfigurationManager.AppSettings["serverport"], out defaultPort);
            if (false == string.IsNullOrEmpty(System.Configuration.ConfigurationManager.AppSettings["serverip"]))
            {
                defaultIp = System.Configuration.ConfigurationManager.AppSettings["serverip"];
            }
            clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            IPAddress ip = IPAddress.Parse(defaultIp);
            IPEndPoint endPoint = new IPEndPoint(ip, defaultPort);
            clientSocket.Connect(endPoint);
            thread = new Thread(ReceMsg);
            thread.IsBackground = true;
            thread.Start();
        }
        /// <summary>
        /// 接收服务器端数据
        /// </summary>
        private static void ReceMsg()
        {
            while (true)
            {
                try
                {
                    byte[] buffer = new byte[1024];
                    int length = clientSocket.Receive(buffer);
                    Console.WriteLine("连接状态:" + clientSocket.Connected);
                    if (clientSocket.Connected == false)
                    {
                        return;
                    }
                    byte[] buf = new byte[length];
                    Array.Copy(buffer, buf, length);
                    Console.WriteLine("接收消息>");
                    Console.WriteLine(System.Text.Encoding.ASCII.GetString(buf));// StringTool.byteToHexStr(buf));
                }catch(SocketException ex)
                {
                    Console.WriteLine(ex.Message);
                    if (ex.ErrorCode == 10054)
                    {
                        return;
                    }
                }
            }
        }

        public static void SendMsg(string msg)
        {
            clientSocket.Send(Encoding.ASCII.GetBytes(msg));
        }

        public static void SendMsg(byte[] buffer)
        {
            clientSocket.Send(buffer);
        }
    }

组包测试

public class TestData
    {
        public static string LoginData()
        {
            string head = StringTool.StringToHexString("##", UTF8Encoding.ASCII);//0 起始符号
            string cmd = "";
            cmd += "01";//2 命令标识
            cmd += "FE";//3 应答标志
            cmd += StringTool.StringToHexString("SKYWELLIT00000003", UTF8Encoding.ASCII).ToUpper();//4 唯一识别码 主板程序编号

            cmd += "01";//21 数据单元加密方式 01 不加密

            string dataLength = ""; //22 数据单元长度 WORD
            string data = "";
            DateTime dt = DateTime.Now;
            data += Convert.ToString(19, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Month, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Day, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Hour, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Minute, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Second, 16).PadLeft(2, '0');

            string s2 = Convert.ToString(2001, 16).ToUpper();//登录流水号
            s2 = s2.PadLeft(4, '0');
            data += s2;

            data += StringTool.StringToHexString("898600MFSSYYGXXXXX03", Encoding.ASCII).ToUpper();

            data += StringTool.StringToHexString("1", UTF8Encoding.ASCII); //温度
            data += StringTool.StringToHexString("1", UTF8Encoding.ASCII); //湿度
            data += StringTool.StringToHexString("0", UTF8Encoding.ASCII); //烟雾
            data += StringTool.StringToHexString("0", UTF8Encoding.ASCII); //水浸
            data += StringTool.StringToHexString("0", UTF8Encoding.ASCII);//电力
            data += StringTool.StringToHexString("0", UTF8Encoding.ASCII);//入侵
            dataLength = Convert.ToString(data.Length, 16);
            Console.WriteLine(dataLength);
            dataLength = dataLength.PadLeft(4, '0');
            string check = StringTool.GetBCCXorCode(StringTool.strToToHexByte(cmd + dataLength + data));
            string s = head + cmd + dataLength + data + check;
            return s;
        }

        public static string PostData()
        {
            string head = StringTool.StringToHexString("##", UTF8Encoding.ASCII);//0 起始符号
            string cmd = "";
            cmd += "02";//2 命令标识 01 登录 02 实时信息上报
            cmd += "FE";//3 应答标志
            cmd += StringTool.StringToHexString("SKYWELLIT00000003", UTF8Encoding.ASCII);//4 唯一识别码 主板程序编号

            cmd += "01";//21 数据单元加密方式 01 不加密

            string dataLength = ""; //22 数据单元长度 WORD
            string data = "";
            DateTime dt = DateTime.Now;
            
            data += Convert.ToString(19, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Month, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Day, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Hour, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Minute, 16).PadLeft(2, '0');
            data += Convert.ToString(dt.Second, 16).PadLeft(2, '0');
            
            data += "01";
            data += Convert.ToString(22).PadLeft(2, '0').PadRight(4,'0'); //温度
            data += "02";
            data += Convert.ToString(28).PadLeft(2, '0').PadRight(4, '0'); //湿度
            
            dataLength = Convert.ToString(data.Length, 16);
            dataLength = dataLength.PadLeft(4, '0');
            string check = StringTool.GetBCCXorCode(StringTool.strToToHexByte(cmd + dataLength + data));
            string s = head + cmd + dataLength + data + check;
            return s;
        }
    }
    
    public class StringTool
    {
        /// <summary>
        /// 将字符串转为16进制字符,允许中文
        /// </summary>
        /// <param name="s"></param>
        /// <param name="encode"></param>
        /// <returns></returns>
        public static string StringToHexString(string s, Encoding encode)
        {
            byte[] b = encode.GetBytes(s);//按照指定编码将string编程字节数组
            string result = string.Empty;
            for (int i = 0; i < b.Length; i++)//逐字节变为16进制字符
            {
                result += Convert.ToString(b[i], 16);
            }
            return result;
        }
        /// <summary>
        /// 将16进制字符串转为字符串
        /// </summary>
        /// <param name="hs"></param>
        /// <param name="encode"></param>
        /// <returns></returns>
        public static string HexStringToString(string hs, Encoding encode)
        {
            string strTemp = "";
            byte[] b = new byte[hs.Length / 2];
            for (int i = 0; i < hs.Length / 2; i++)
            {
                strTemp = hs.Substring(i * 2, 2);
                b[i] = Convert.ToByte(strTemp, 16);
            }
            //按照指定编码将字节数组变为字符串
            return encode.GetString(b);
        }
        /// <summary>
        /// 将byte[]转为16进制字符串
        /// </summary>
        /// <param name="bytes"></param>
        /// <returns></returns>
        public static string byteToHexStr(byte[] bytes)
        {
            string returnStr = "";
            if (bytes != null)
            {
                for (int i = 0; i < bytes.Length; i++)
                {
                    returnStr += bytes[i].ToString("X2");
                }
            }
            return returnStr;
        }

        /// <summary>
        /// 将16进制的字符串转为byte[]
        /// </summary>
        /// <param name="hexString"></param>
        /// <returns></returns>
        public static byte[] strToToHexByte(string hexString)
        {
            hexString = hexString.Replace(" ", "");
            if ((hexString.Length % 2) != 0)
                hexString = "0" + hexString;
            byte[] returnBytes = new byte[hexString.Length / 2];
            for (int i = 0; i < returnBytes.Length; i++)
                returnBytes[i] = Convert.ToByte(hexString.Substring(i * 2, 2), 16);
            return returnBytes;
        }

        /// <summary>
        /// BCC和校验代码返回16进制
        /// </summary>
        /// <param name="data">需要校验的数据包</param>
        /// <returns></returns>
        public static string GetBCCXorCode(byte[] data)
        {
            byte CheckCode = 0;
            int len = data.Length;
            for (int i = 0; i < len; i++)
            {
                CheckCode ^= data[i];
                System.Console.WriteLine(data[i]);
            }
            System.Console.WriteLine(CheckCode);
            return Convert.ToString(CheckCode, 16).ToUpper();
        }

        /// <summary>
        /// BCC和校验代码
        /// </summary>
        /// <param name="data">需要校验的数据包</param>
        /// <returns></returns>
        public static byte Get_CheckXor(byte[] data)
        {
            byte CheckCode = 0;
            int len = data.Length;
            for (int i = 0; i < len; i++)
            {
                CheckCode ^= data[i];
            }
            return CheckCode;
        }
    }

标签:Convert,string,16,C#,温湿度,TCP,ToString,byte,data
From: https://blog.51cto.com/u_16249230/7423526

相关文章

  • 系统入门C语言的寄存器
    你好,我是悦创。本篇为C语言一对一辅导笔记节选,我们来系统地了解C语言中与寄存器相关的内容。1.什么是寄存器?寄存器是位于CPU内部的小型、高速的存储单元,它们的访问速度远高于主内存。在执行程序时,常用的数据和指令经常被加载到这些寄存器中,以加速程序的运行。2.register关键字在......
  • 1783_CMD启动MATLAB同时执行一个脚本
    全部学习汇总:GitHub-GreyZhang/g_matlab:MATLABonceusedtobemydailytool.AftermanyyearswhenIgobackandreadmyoldlearningnotesIfeltmaybeIstillneeditinthefuture.So,startthisrepotokeepsomeofmyoldlearningnotesservralyearsa......
  • 达梦数据库教程:DM8性能诊断(内存、CPU、磁盘、网络、AWR日志和接口日志诊断)
    性能诊断一、前言1.1概念性能诊断用于了解操作系统以及数据库的各项性能指标是否达到要求,以满足系统正常运行需要。通过性能诊断,可以更好地了解系统资源的使用情况、以及数据库的状态,提前避免由于性能不足引发的各种问题。性能诊断在数据库运维中具有极大的实用价值。性能诊断包括......
  • 达梦数据库教程:docker安装DM8数据库
    安装前准备软硬件版本终端X86-64架构Docker2023年6月版下载Docker安装包请在达梦数据库官网下载Docker安装包。导入安装包拷贝安装包到/opt目录下,执行以下命令导入安装包:dockerload-idm8_20230808_rev197096_x86_rh6_64_single.tar结果显示如下:导入完成后,可以使用doc......
  • 达梦数据库教程:DM8数据迁移工具使用教程(oracle迁移至DM8)
    DM数据迁移工具DM数据迁移工具DMDTS提供了主流大型数据库迁移到DM、DM到DM、文件迁移到DM以及DM迁移到文件等功能。得益于DM数据库对目前主流大型关系型数据库系统有着业界领先的兼容性,在存储层面、语法层面、接口层面和它们保持高度兼容,借助于DM图形界面且采用向......
  • 医院信息化、数字医学影像、DICOM、PACS
    PACS系统适合卫生院、民营医院、二甲或以下公立医院的放射科、超声科使用。功能强大且简洁,性能优异,具备MPR(三维重建)、VR(容积重建)、胶片打印功能,能够快速部署。支持DR、CT、磁共振提供DICOM服务,支持临床医生工作站提供报告和影像浏览服务,系统支持与HIS、体检融合,从对方服务器获取......
  • Flink 1.17教程:输出算子之输出到MySQL(JDBC)
    输出到MySQL(JDBC)写入数据的MySQL的测试步骤如下。(1)添加依赖添加MySQL驱动:mysqlmysql-connector-java8.0.27官方还未提供flink-connector-jdbc的1.17.0的正式依赖,暂时从apachesnapshot仓库下载,pom文件中指定仓库路径:apache-snapshotsapachesnapshotshttps://repository.a......
  • QT7331 14bit 2 通道3/2.6/2GS/s ADC + 16bit 2 通道12.6GS/s DAC FMC AD/DA 子卡
    概要QT7331是一款高分辨率、高采样率的ADC+DACFMC子板。它同时支持2路14位3.0/2.6/2.0GS/s的A/D通道输入和2路16位12.6GS/s的D/A通道输出,全功率模拟-3dB输入带宽可达9GHz。QT7331A为3GSPS采样率,QT7331B为2.6GSPS采样率,QT7331C为2GSPS采样率。本板卡支持触发输入或者输出;内参考、......
  • C语言求1000以内所有的水仙花数
    求1000以内所有的水仙花数何为水仙花数一个3位整数的各位数字的立方之和等于这个整数,称之为“水仙花数”。例如:153是水仙花数,因为153=1*1*1+5*5*5+3*3*3。先看代码#include<stdio.h>#include<math.h>intmain(){inti,a,b,c,d;for(i=100;i<1000;i++)......
  • FMC AD/DA 子卡 1 通道4GSPS 12bit ADC 采集 1 通道12.8GSPS 16bit DAC 回放
    概要QT7332是一款集成单通道ADC采集和单通道DAC回放的FMC板卡,ADC(ADC12J4000)转换速率最高为4GSPS,ADC位数12bit,DAC(AD9162)转换速率最高为12.8GSPS,DAC位数16bit;板卡支持触发输出/触发输入可调;触发/同步可选;采样时钟源支持内部参考时钟、外部参考时钟、外部采样时钟三种方式,可通过2个......