winform 怎么发送文件给GPRS模块

时间:2022-06-10 10:03:01
winform 怎么发送文件给GPRS模块,求各位大侠帮帮忙,我刚接触GPRS通信,TCP协议一定要三次握手么?

14 个解决方案

#1


发个文件地址,过去,让GPRS模块再读取这个地址,获得文件不可以吗

#2


引用 1 楼  的回复:
发个文件地址,过去,让GPRS模块再读取这个地址,获得文件不可以吗

关键是这个地址怎么发送给GPRS呢?我是发送自己机子上的文件给GPRS模块,没有地址

#3


我用的GPRS模块是西门子 MC52iR3

#4


你们有没有服务器?如果有那就好说一些了,pc和gprs模块都通过socket接入服务器,通过服务器中转传输。MC52iR3带有tcp/ip协议栈,可以直接使用模块的socket方面的AT指令。
如果没有服务器,那就要分析pc端的网络接入方式,如果是adsl那么可以实现pc端与gprs模块直接建立socket连接来传输,传输前需要通过短信把pc端的动态公网地址通知gprs模块。
如果是那种小区宽带,就有两个选择,前提条件是pc端也要连接一个gprs模块:
一是租一个网站空间,将文件上传到网站后短信通知gprs模块,gprs模块从网站下载;
二是利用gprs模块的数据数功能(类似传真那样的,可能需要移动网络运行商开通),这一块没做过不太了解。

#5


引用 4 楼  的回复:
你们有没有服务器?如果有那就好说一些了,pc和gprs模块都通过socket接入服务器,通过服务器中转传输。MC52iR3带有tcp/ip协议栈,可以直接使用模块的socket方面的AT指令。
如果没有服务器,那就要分析pc端的网络接入方式,如果是adsl那么可以实现pc端与gprs模块直接建立socket连接来传输,传输前需要通过短信把pc端的动态公网地址通知gprs模块。
如果是那种小区宽……

没有服务器,
传输的时候是通过短信把pc端的动态公网地址和端口发送给gprs模块,
GPRS模块再主动连接winforom程序,连接成功再进行文件传输,利用gprs模块的数据数

如果有服务器,可以给我举个例子么?我第一次接触这个,不知道怎么写。

我们是做主板在线升级,把.bin格式文件传给GPRS模块,GPRS模块再传给主板

#6


这样的程序说大不大说小不小,socket服务器要做到性能与可靠性的完善不是一蹴而就的,我给你贴一个我这里的socket服务器类,仅供借鉴。你最好花更多的时间查阅msdn来完善这方面的知识。
第一部分:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net.Sockets;
using System.Net;
using System.Threading;
using System.Runtime.InteropServices;

namespace nsqserver
{
    [StructLayout(LayoutKind.Sequential)]
    public struct SendSegment
    {
        byte[] sendbuffer;
        SendPacketsElement[] sendelements;
        int offset;
        int count;
        public SendSegment(SendPacketsElement[] elements)
        {
            sendelements = elements;
            sendbuffer = null;
            offset = 0;
            count = 0;
        }
        public SendSegment(byte[] buffer, int ost, int cot)
        {
            sendbuffer = buffer;
            sendelements = null;
            offset = ost;
            count = cot;
        }
        public byte[] SendBuffer { get { return this.sendbuffer; } }
        public SendPacketsElement[] SendElments { get { return this.sendelements; } }
        public int Offset { get { return this.offset; } }
        public int Count { get { return this.count; } }
    }
    public enum RecvHasHeaders
    {
        On,
        Off
    }
    class SocketServer
    {
        byte[] buffers;
        byte[] sendbuffer;
        Socket[] sockets;
        SocketAsyncEventArgs[] sendargs;
        SocketAsyncEventArgs[] recvargs;
        SocketAsyncEventArgs[] acepargs;
        Queue<SendSegment>[] queues;
        Object[] objs;
        int recvbufferlen;
        int sockcount;
        int sendbufferlen;
        int sendindex;
        Object stackobj = new Object();
        RecvHasHeaders[] recvhasheader;
        Socket acceptsock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        public event Func<int, byte[], int, int, int> RecvByteComplete;
        public event Func<int, byte[], int, int, int> RecvNoHeaderComplete;
        public event Action<int> SendPacketsComplete;
        public event Action<int> AcceptComplete;
        public event Action<int> SendComplete;
        public event Action<int> CloseComplete;
        byte[] inValue = new byte[] { 1, 0, 0, 0, 0x88, 0x13, 0, 0, 0x88, 0x13, 0, 0 };
        public SocketServer(int skcount, int rvbufferlen, int sdbufferlen, int queuecount, string ipadr, int port)
        {
            buffers = new byte[skcount * rvbufferlen];
            sendbufferlen = sdbufferlen;
            sendindex = 0;
            sendbuffer = new byte[sdbufferlen];
            sockets = new Socket[skcount];
            sendargs = new SocketAsyncEventArgs[skcount];
            recvargs = new SocketAsyncEventArgs[skcount];
            acepargs = new SocketAsyncEventArgs[skcount];
            queues = new Queue<SendSegment>[skcount];
            objs = new Object[skcount];
            recvhasheader = new RecvHasHeaders[skcount];
            recvbufferlen = rvbufferlen;
            sockcount = skcount;
            acceptsock.Bind(new IPEndPoint(IPAddress.Parse(ipadr), port));
            acceptsock.Listen(100);
            for (int i = 0; i < skcount; i++)
            {
                sockets[i] = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                sendargs[i] = new SocketAsyncEventArgs();
                sendargs[i].UserToken = i;
                recvargs[i] = new SocketAsyncEventArgs();
                recvargs[i].UserToken = i;
                acepargs[i] = new SocketAsyncEventArgs();
                acepargs[i].AcceptSocket = sockets[i];
                acepargs[i].UserToken = i;
                queues[i] = new Queue<SendSegment>(queuecount);
                objs[i] = new Object();
                recvhasheader[i] = RecvHasHeaders.On;
                recvargs[i].SetBuffer(buffers, i * rvbufferlen, 4);
                recvargs[i].Completed += new EventHandler<SocketAsyncEventArgs>(Receive_Completed);
                sendargs[i].Completed += new EventHandler<SocketAsyncEventArgs>(Send_Completed);
                acepargs[i].Completed += new EventHandler<SocketAsyncEventArgs>(Server_Completed);
            }
        }
        public void Sethnheader(int sockindx, RecvHasHeaders rh)
        {
            recvhasheader[sockindx] = rh;
        }
        public void startaccept()
        {
            for (int i = 0; i < sockcount; i++)
                acceptsock.AcceptAsync(acepargs[i]);
        }
        void Server_Completed(object sender, SocketAsyncEventArgs e)
        {
            int asockindx = (int)e.UserToken;
            if (e.SocketError != SocketError.Success)
            {
                disconnectsocket(asockindx);
                return;
            }
            if (e.LastOperation == SocketAsyncOperation.Accept)
            {
                if (AcceptComplete != null)
                    AcceptComplete.Invoke(asockindx);
                sockets[asockindx].IOControl(IOControlCode.KeepAliveValues, inValue, null);
                sockets[asockindx].ReceiveAsync(recvargs[asockindx]);
                return;
            }
            if (e.LastOperation == SocketAsyncOperation.Disconnect)
            {
                e.SetBuffer(null, 0, 0);
                acceptsock.AcceptAsync(e);
                return;
            }
        }

#7


第二部分:

        void Receive_Completed(object sender, SocketAsyncEventArgs e)
        {
            int sockindx = e.Offset / recvbufferlen;
            if (e.SocketError != SocketError.Success)
            {
                disconnectsocket(sockindx);
                return;
            }
            if (e.LastOperation != SocketAsyncOperation.Receive)
            {
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            if (e.BytesTransferred <= 0)
            {
                disconnectsocket(sockindx);
                return;
            }
            if (recvhasheader[sockindx] == RecvHasHeaders.Off)
            {
                int rvlen2 = -1;
                if (RecvNoHeaderComplete != null)
                    rvlen2 = RecvNoHeaderComplete.Invoke(sockindx, e.Buffer, e.Offset, e.BytesTransferred);
                if (recvhasheader[sockindx] == RecvHasHeaders.On)
                    e.SetBuffer(e.Offset, 4);
                else if (rvlen2 > 0)
                    e.SetBuffer(e.Offset, rvlen2);
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            if (e.BytesTransferred != e.Count)
            {
                e.SetBuffer(e.Offset + e.BytesTransferred, e.Count - e.BytesTransferred);
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            int os = sockindx * recvbufferlen;
            int len = BitConverter.ToInt32(buffers, os);
            if (len > recvbufferlen)
            {
                disconnectsocket(sockindx);
                return;
            }
            if (e.Offset % recvbufferlen < 4 && len > 4)
            {
                e.SetBuffer(os + 4, len - 4);
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            int rvlen = -1;
            if (RecvByteComplete != null)
                rvlen = RecvByteComplete.Invoke(sockindx, e.Buffer, os, len);
            if (recvhasheader[sockindx] == RecvHasHeaders.On)
                e.SetBuffer(os, 4);
            else if (rvlen > 0)
                e.SetBuffer(os, rvlen);
            sockets[sockindx].ReceiveAsync(e);
        }
        void Send_Completed(object sender, SocketAsyncEventArgs e)
        {
            if (e.LastOperation != SocketAsyncOperation.Send && e.LastOperation != SocketAsyncOperation.SendPackets)
                return;
            int indx = (int)e.UserToken;
            if (e.SocketError != SocketError.Success)
                return;
            if (e.LastOperation == SocketAsyncOperation.SendPackets && SendPacketsComplete != null)
                SendPacketsComplete.Invoke(indx);
            if (e.LastOperation == SocketAsyncOperation.Send && SendComplete != null)
                SendComplete.Invoke(indx);
            bool busy = false;
            lock (objs[indx])
            {
                queues[indx].Dequeue();
                if (queues[indx].Count > 0)
                    busy = true;
            }
            if (!busy)
                return;
            SendSegment sbuffer = queues[indx].Peek();
            if (sbuffer.SendBuffer != null)
            {
                e.SetBuffer(sbuffer.SendBuffer, sbuffer.Offset, sbuffer.Count);
                try { sockets[indx].SendAsync(e); }
                catch { }
                return;
            }
            e.SendPacketsElements = sbuffer.SendElments;
            try { sockets[indx].SendPacketsAsync(e); }
            catch { }
        }
        public void CloseSocket(int sockindx)
        {
            sockets[sockindx].Shutdown(SocketShutdown.Send);
        }
        void disconnectsocket(int sockindx)
        {
            recvhasheader[sockindx] = RecvHasHeaders.On;
            if (CloseComplete != null)
                CloseComplete.Invoke(sockindx);
            sockets[sockindx].Shutdown(SocketShutdown.Both);
            acepargs[sockindx].DisconnectReuseSocket = true;
            sockets[sockindx].DisconnectAsync(acepargs[sockindx]);
            lock (objs[sockindx])
                queues[sockindx].Clear();
        }
        void SendsSegment(int sockindx, SendSegment ag)
        {
            bool busy = false;
            lock (objs[sockindx])
            {
                if (queues[sockindx].Count > 0)
                    busy = true;
                queues[sockindx].Enqueue(ag);
            }
            if (busy)
                return;
            if (ag.SendBuffer != null)
            {
                sendargs[sockindx].SetBuffer(ag.SendBuffer, ag.Offset, ag.Count);
                try { sockets[sockindx].SendAsync(sendargs[sockindx]); }
                catch { }
                return;
            }
            sendargs[sockindx].SendPacketsElements = ag.SendElments;
            try { sockets[sockindx].SendPacketsAsync(sendargs[sockindx]); }
            catch { }
        }
        public void SendBuffer(int sockindx, byte[] sbuffer, int ost, int len)
        {
            if (len > recvbufferlen)
                return;
            SendsSegment(sockindx, new SendSegment(sbuffer, ost, len));
        }
        public void SendBuffer(List<int> sks, byte[] sbuffer, int ost, int len)
        {
            if (len > recvbufferlen)
                return;
            SendSegment ag = new SendSegment(sbuffer, ost, len);
            foreach (int sockindx in sks)
                SendsSegment(sockindx, ag);
        }
        public void SendPoolByorNot(int sockindx, bool usepool, params object[] objs)
        {
            SendSegment bf = xuliehua(objs, usepool);
            SendsSegment(sockindx, bf);
        }
        public void SendPoolByorNot(List<int> sks, bool usepool, params object[] objs)
        {
            SendSegment bf = xuliehua(objs, usepool);
            foreach (int sockindx in sks)
                SendsSegment(sockindx, bf);
        }
        public void Send(int sockindx, params object[] objs)
        {
            SendPoolByorNot(sockindx, true, objs);
        }
        public void Send(List<int> sks, params object[] objs)
        {
            SendPoolByorNot(sks, true, objs);
        }
        public void SendPackets(int sockindx, SendPacketsElement[] packets)
        {
            SendSegment sg = new SendSegment(packets);
            SendsSegment(sockindx, sg);
        }
        public void SendPackets(List<int> sks, SendPacketsElement[] packets)
        {
            SendSegment sg = new SendSegment(packets);
            foreach (int sockindx in sks)
                SendsSegment(sockindx, sg);
        }

#8


第三部分:

        unsafe public SendSegment xuliehua(object[] objs, bool usepool)
        {
            int len = 0;
            int* tps = stackalloc int[objs.Length];
            for (int i = 0; i < objs.Length; i++)
            {
                if (objs[i] == null)
                {
                    tps[i] = 5;
                    len += 4;
                    continue;
                }
                Type t = objs[i].GetType();
                if (t == typeof(int))
                {
                    tps[i] = 1;
                    len += 8;
                }
                else if (t == typeof(string))
                {
                    tps[i] = 2;
                    len += 8 + ((string)objs[i]).Length * 2;
                }
                else if (t == typeof(double))
                {
                    tps[i] = 3;
                    len += 12;
                }
                else if (t == typeof(DateTime))
                {
                    tps[i] = 4;
                    len += 8;
                }
                else if (t == typeof(bool))
                {
                    tps[i] = 6;
                    len += 8;
                }
                else
                {
                    tps[i] = 7;
                    len += 4;
                }
            }
            len += 4;
            if (len > recvbufferlen)
                throw new ArgumentException("发送长度超出缓冲区长度");
            byte[] bf;
            int bindx = 0;
            if (usepool)
            {
                bf = sendbuffer;
                bindx = getsendindex(len);
            }
            else
                bf = new byte[len];
            fixed (byte* p = bf) { *(int*)(p + bindx) = len; }
            bindx += 4;
            for (int i = 0; i < objs.Length; i++)
            {
                int tp = tps[i];
                if (tp <= 0 || tp > 7)
                {
                    throw new ArgumentException("序列化时参数类型超出规定范围");
                }
                fixed (byte* p = bf) { *(int*)(p + bindx) = tp; }
                bindx += 4;
                if (tp == 1)
                {
                    fixed (byte* p = bf) { *(int*)(p + bindx) = (int)objs[i]; }
                    bindx += 4;
                }
                else if (tp == 2)
                {
                    string s = (string)objs[i];
                    fixed (byte* p = bf) { *(int*)(p + bindx) = s.Length * 2; }
                    bindx += 4;
                    Encoding.Unicode.GetBytes(s, 0, s.Length, bf, bindx);
                    bindx += s.Length * 2;
                }
                else if (tp == 3)
                {
                    fixed (byte* p = bf) { *(double*)(p + bindx) = (double)objs[i]; }
                    bindx += 8;
                }
                else if (tp == 4)
                {
                    fixed (byte* p = bf) { *(uint*)(p + bindx) = Dttoint.toint((DateTime)objs[i]); }
                    bindx += 4;
                }
                else if (tp == 6)
                {
                    fixed (byte* p = bf) { *(bool*)(p + bindx) = (bool)objs[i]; }
                    bindx += 4;
                }
            }
            return new SendSegment(bf, bindx - len, len);
        }
        public object[] fanxulie(byte[] sbuffer, int startindex, int count)
        {
            int index = startindex;
            int endindex = startindex + count;
            int len = 0;
            while (index < endindex)
            {
                int tp = BitConverter.ToInt32(sbuffer, index);
                if (tp <= 0 || tp > 7)
                    throw new ArgumentException("反序列化时参数类型超出规定范围");
                index += 4;
                if (tp == 1 || tp == 4 || tp == 6)
                    index += 4;
                else if (tp == 2)
                {
                    int strlen = BitConverter.ToInt32(sbuffer, index);
                    index += 4;
                    if (strlen < 0 || strlen > startindex + count - index)
                        throw new ArgumentException("反序列化时字符串长度超出缓冲区");
                    index += strlen;
                }
                else if (tp == 3)
                    index += 8;
                len++;
            }
            object[] neirong = new object[len];
            index = startindex;
            len = 0;
            while (index < endindex)
            {
                int tp = BitConverter.ToInt32(sbuffer, index);
                index += 4;
                if (tp == 1)
                {
                    neirong[len] = BitConverter.ToInt32(sbuffer, index);
                    index += 4;
                }
                else if (tp == 2)
                {
                    int strlen = BitConverter.ToInt32(sbuffer, index);
                    index += 4;
                    neirong[len] = Encoding.Unicode.GetString(sbuffer, index, strlen);
                    index += strlen;
                }
                else if (tp == 3)
                {
                    neirong[len] = BitConverter.ToDouble(sbuffer, index);
                    index += 8;
                }
                else if (tp == 4)
                {
                    neirong[len] = Dttoint.todt(BitConverter.ToUInt32(sbuffer, index));
                    index += 4;
                }
                else if (tp == 6)
                {
                    neirong[len] = BitConverter.ToBoolean(sbuffer, index);
                    index += 4;
                }
                else
                    neirong[len] = null;
                len++;
            }
            return neirong;
        }
        int getsendindex(int len)
        {
            int index = (int)(((uint)Interlocked.Add(ref sendindex, len)) % sendbufferlen);
            if (index - len < 0)
                index = (int)(((uint)Interlocked.Add(ref sendindex, len)) % sendbufferlen);
            return index - len;
        }
    }
}

#9


引用 8 楼  的回复:
第三部分:

C# code


        unsafe public SendSegment xuliehua(object[] objs, bool usepool)
        {
            int len = 0;
            int* tps = stackalloc int[objs.Length];
            for……



我们做的是没有服务器的,(通过串口发送短信已经有现成的软件的了,现在我要做的是把这个软件新增一个通过GPRS发送文件的模块)
已经通过短信发送公网动态IP和端口号给GPRS模块了,模块也主动连接了软件,
可是怎么判断模块连接成功,成功之后再发送文件
是不是通过不断的循环读取网络流中的数据,如果读取到GPRS模块返回的成功标识就判断为连接成功

如果返回了成功,发送文件是不是用
socket.Send(Data);
或者
NetworkStream ns = new NetworkStream(socket);                     
StreamReader sr = new StreamReader(ns);                     
StreamWriter sw = new StreamWriter(ns);                     
sw.WriteLine(Data);                  
sw.Flush();  

Data是通过TCP协议组装的数据,我是通过这几天查资料理解的,也不知道是否正确,  请大侠指点指点            

#10


我现在的问题和你的一样,请问你的解决没有呀?

#11


那你看,你现在是从互联网上下载数据,不是上传数据。
你发送联网的at命令到gprs模块,如果gprs给你返回OK,那就表示连接成功。
你把你要下载的文件放到互联网上,从网上下载数据的代码,给你下了下,如果你也是C#的话,应该没有问题的了。
            try
            {
                System.Net.WebRequest wr = System.Net.WebRequest.Create("http://www.hongname.com/mxtp/z/good/zhangmy3/004.jpg");
                wr.Credentials = CredentialCache.DefaultCredentials;
                WebResponse wrp;
                wrp = wr.GetResponse();                
                System.IO.Stream stream = wrp.GetResponseStream();                 
                long count = wrp.ContentLength;
                int curr = 0;
                byte[] bdata = new byte[count];
                do
                {
                    curr += stream.Read(bdata, curr, bdata.Length - curr);
                } while (curr < count);
                System.IO.FileStream fs = new System.IO.FileStream("C:\\a.bin", System.IO.FileMode.OpenOrCreate);
                fs.Write(bdata, 0, bdata.Length);
                fs.Flush();
                stream.Close();
                fs.Close();
            }
            catch(Exception Ex) { }

#12


完全看不懂啊!

#13


引用 11 楼  的回复:
那你看,你现在是从互联网上下载数据,不是上传数据。
你发送联网的at命令到gprs模块,如果gprs给你返回OK,那就表示连接成功。
你把你要下载的文件放到互联网上,从网上下载数据的代码,给你下了下,如果你也是C#的话,应该没有问题的了。
  try
  {
  System.Net.WebRequest wr = System.Net.WebRequest.Create("http:/……



谢谢哦!好久没有来了,问题现在已经解决,之前用了和你的差不多的,不过后来又改了

#14


引用 10 楼  的回复:
我现在的问题和你的一样,请问你的解决没有呀?

不好意思哦!我好久没来了,我现在问题解决了,
我首先发一条带有本地IP地址和端口号的短信给GPRS短信模块,
GPRS短信模块在接收到我发出的短信主动连接
建立一个监听事件监听GPRS短信模块发出的信息,首先监听网络是否连接成功,如果成功就加载bin文件,分解再发送bin文件。

#1


发个文件地址,过去,让GPRS模块再读取这个地址,获得文件不可以吗

#2


引用 1 楼  的回复:
发个文件地址,过去,让GPRS模块再读取这个地址,获得文件不可以吗

关键是这个地址怎么发送给GPRS呢?我是发送自己机子上的文件给GPRS模块,没有地址

#3


我用的GPRS模块是西门子 MC52iR3

#4


你们有没有服务器?如果有那就好说一些了,pc和gprs模块都通过socket接入服务器,通过服务器中转传输。MC52iR3带有tcp/ip协议栈,可以直接使用模块的socket方面的AT指令。
如果没有服务器,那就要分析pc端的网络接入方式,如果是adsl那么可以实现pc端与gprs模块直接建立socket连接来传输,传输前需要通过短信把pc端的动态公网地址通知gprs模块。
如果是那种小区宽带,就有两个选择,前提条件是pc端也要连接一个gprs模块:
一是租一个网站空间,将文件上传到网站后短信通知gprs模块,gprs模块从网站下载;
二是利用gprs模块的数据数功能(类似传真那样的,可能需要移动网络运行商开通),这一块没做过不太了解。

#5


引用 4 楼  的回复:
你们有没有服务器?如果有那就好说一些了,pc和gprs模块都通过socket接入服务器,通过服务器中转传输。MC52iR3带有tcp/ip协议栈,可以直接使用模块的socket方面的AT指令。
如果没有服务器,那就要分析pc端的网络接入方式,如果是adsl那么可以实现pc端与gprs模块直接建立socket连接来传输,传输前需要通过短信把pc端的动态公网地址通知gprs模块。
如果是那种小区宽……

没有服务器,
传输的时候是通过短信把pc端的动态公网地址和端口发送给gprs模块,
GPRS模块再主动连接winforom程序,连接成功再进行文件传输,利用gprs模块的数据数

如果有服务器,可以给我举个例子么?我第一次接触这个,不知道怎么写。

我们是做主板在线升级,把.bin格式文件传给GPRS模块,GPRS模块再传给主板

#6


这样的程序说大不大说小不小,socket服务器要做到性能与可靠性的完善不是一蹴而就的,我给你贴一个我这里的socket服务器类,仅供借鉴。你最好花更多的时间查阅msdn来完善这方面的知识。
第一部分:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net.Sockets;
using System.Net;
using System.Threading;
using System.Runtime.InteropServices;

namespace nsqserver
{
    [StructLayout(LayoutKind.Sequential)]
    public struct SendSegment
    {
        byte[] sendbuffer;
        SendPacketsElement[] sendelements;
        int offset;
        int count;
        public SendSegment(SendPacketsElement[] elements)
        {
            sendelements = elements;
            sendbuffer = null;
            offset = 0;
            count = 0;
        }
        public SendSegment(byte[] buffer, int ost, int cot)
        {
            sendbuffer = buffer;
            sendelements = null;
            offset = ost;
            count = cot;
        }
        public byte[] SendBuffer { get { return this.sendbuffer; } }
        public SendPacketsElement[] SendElments { get { return this.sendelements; } }
        public int Offset { get { return this.offset; } }
        public int Count { get { return this.count; } }
    }
    public enum RecvHasHeaders
    {
        On,
        Off
    }
    class SocketServer
    {
        byte[] buffers;
        byte[] sendbuffer;
        Socket[] sockets;
        SocketAsyncEventArgs[] sendargs;
        SocketAsyncEventArgs[] recvargs;
        SocketAsyncEventArgs[] acepargs;
        Queue<SendSegment>[] queues;
        Object[] objs;
        int recvbufferlen;
        int sockcount;
        int sendbufferlen;
        int sendindex;
        Object stackobj = new Object();
        RecvHasHeaders[] recvhasheader;
        Socket acceptsock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        public event Func<int, byte[], int, int, int> RecvByteComplete;
        public event Func<int, byte[], int, int, int> RecvNoHeaderComplete;
        public event Action<int> SendPacketsComplete;
        public event Action<int> AcceptComplete;
        public event Action<int> SendComplete;
        public event Action<int> CloseComplete;
        byte[] inValue = new byte[] { 1, 0, 0, 0, 0x88, 0x13, 0, 0, 0x88, 0x13, 0, 0 };
        public SocketServer(int skcount, int rvbufferlen, int sdbufferlen, int queuecount, string ipadr, int port)
        {
            buffers = new byte[skcount * rvbufferlen];
            sendbufferlen = sdbufferlen;
            sendindex = 0;
            sendbuffer = new byte[sdbufferlen];
            sockets = new Socket[skcount];
            sendargs = new SocketAsyncEventArgs[skcount];
            recvargs = new SocketAsyncEventArgs[skcount];
            acepargs = new SocketAsyncEventArgs[skcount];
            queues = new Queue<SendSegment>[skcount];
            objs = new Object[skcount];
            recvhasheader = new RecvHasHeaders[skcount];
            recvbufferlen = rvbufferlen;
            sockcount = skcount;
            acceptsock.Bind(new IPEndPoint(IPAddress.Parse(ipadr), port));
            acceptsock.Listen(100);
            for (int i = 0; i < skcount; i++)
            {
                sockets[i] = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                sendargs[i] = new SocketAsyncEventArgs();
                sendargs[i].UserToken = i;
                recvargs[i] = new SocketAsyncEventArgs();
                recvargs[i].UserToken = i;
                acepargs[i] = new SocketAsyncEventArgs();
                acepargs[i].AcceptSocket = sockets[i];
                acepargs[i].UserToken = i;
                queues[i] = new Queue<SendSegment>(queuecount);
                objs[i] = new Object();
                recvhasheader[i] = RecvHasHeaders.On;
                recvargs[i].SetBuffer(buffers, i * rvbufferlen, 4);
                recvargs[i].Completed += new EventHandler<SocketAsyncEventArgs>(Receive_Completed);
                sendargs[i].Completed += new EventHandler<SocketAsyncEventArgs>(Send_Completed);
                acepargs[i].Completed += new EventHandler<SocketAsyncEventArgs>(Server_Completed);
            }
        }
        public void Sethnheader(int sockindx, RecvHasHeaders rh)
        {
            recvhasheader[sockindx] = rh;
        }
        public void startaccept()
        {
            for (int i = 0; i < sockcount; i++)
                acceptsock.AcceptAsync(acepargs[i]);
        }
        void Server_Completed(object sender, SocketAsyncEventArgs e)
        {
            int asockindx = (int)e.UserToken;
            if (e.SocketError != SocketError.Success)
            {
                disconnectsocket(asockindx);
                return;
            }
            if (e.LastOperation == SocketAsyncOperation.Accept)
            {
                if (AcceptComplete != null)
                    AcceptComplete.Invoke(asockindx);
                sockets[asockindx].IOControl(IOControlCode.KeepAliveValues, inValue, null);
                sockets[asockindx].ReceiveAsync(recvargs[asockindx]);
                return;
            }
            if (e.LastOperation == SocketAsyncOperation.Disconnect)
            {
                e.SetBuffer(null, 0, 0);
                acceptsock.AcceptAsync(e);
                return;
            }
        }

#7


第二部分:

        void Receive_Completed(object sender, SocketAsyncEventArgs e)
        {
            int sockindx = e.Offset / recvbufferlen;
            if (e.SocketError != SocketError.Success)
            {
                disconnectsocket(sockindx);
                return;
            }
            if (e.LastOperation != SocketAsyncOperation.Receive)
            {
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            if (e.BytesTransferred <= 0)
            {
                disconnectsocket(sockindx);
                return;
            }
            if (recvhasheader[sockindx] == RecvHasHeaders.Off)
            {
                int rvlen2 = -1;
                if (RecvNoHeaderComplete != null)
                    rvlen2 = RecvNoHeaderComplete.Invoke(sockindx, e.Buffer, e.Offset, e.BytesTransferred);
                if (recvhasheader[sockindx] == RecvHasHeaders.On)
                    e.SetBuffer(e.Offset, 4);
                else if (rvlen2 > 0)
                    e.SetBuffer(e.Offset, rvlen2);
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            if (e.BytesTransferred != e.Count)
            {
                e.SetBuffer(e.Offset + e.BytesTransferred, e.Count - e.BytesTransferred);
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            int os = sockindx * recvbufferlen;
            int len = BitConverter.ToInt32(buffers, os);
            if (len > recvbufferlen)
            {
                disconnectsocket(sockindx);
                return;
            }
            if (e.Offset % recvbufferlen < 4 && len > 4)
            {
                e.SetBuffer(os + 4, len - 4);
                sockets[sockindx].ReceiveAsync(e);
                return;
            }
            int rvlen = -1;
            if (RecvByteComplete != null)
                rvlen = RecvByteComplete.Invoke(sockindx, e.Buffer, os, len);
            if (recvhasheader[sockindx] == RecvHasHeaders.On)
                e.SetBuffer(os, 4);
            else if (rvlen > 0)
                e.SetBuffer(os, rvlen);
            sockets[sockindx].ReceiveAsync(e);
        }
        void Send_Completed(object sender, SocketAsyncEventArgs e)
        {
            if (e.LastOperation != SocketAsyncOperation.Send && e.LastOperation != SocketAsyncOperation.SendPackets)
                return;
            int indx = (int)e.UserToken;
            if (e.SocketError != SocketError.Success)
                return;
            if (e.LastOperation == SocketAsyncOperation.SendPackets && SendPacketsComplete != null)
                SendPacketsComplete.Invoke(indx);
            if (e.LastOperation == SocketAsyncOperation.Send && SendComplete != null)
                SendComplete.Invoke(indx);
            bool busy = false;
            lock (objs[indx])
            {
                queues[indx].Dequeue();
                if (queues[indx].Count > 0)
                    busy = true;
            }
            if (!busy)
                return;
            SendSegment sbuffer = queues[indx].Peek();
            if (sbuffer.SendBuffer != null)
            {
                e.SetBuffer(sbuffer.SendBuffer, sbuffer.Offset, sbuffer.Count);
                try { sockets[indx].SendAsync(e); }
                catch { }
                return;
            }
            e.SendPacketsElements = sbuffer.SendElments;
            try { sockets[indx].SendPacketsAsync(e); }
            catch { }
        }
        public void CloseSocket(int sockindx)
        {
            sockets[sockindx].Shutdown(SocketShutdown.Send);
        }
        void disconnectsocket(int sockindx)
        {
            recvhasheader[sockindx] = RecvHasHeaders.On;
            if (CloseComplete != null)
                CloseComplete.Invoke(sockindx);
            sockets[sockindx].Shutdown(SocketShutdown.Both);
            acepargs[sockindx].DisconnectReuseSocket = true;
            sockets[sockindx].DisconnectAsync(acepargs[sockindx]);
            lock (objs[sockindx])
                queues[sockindx].Clear();
        }
        void SendsSegment(int sockindx, SendSegment ag)
        {
            bool busy = false;
            lock (objs[sockindx])
            {
                if (queues[sockindx].Count > 0)
                    busy = true;
                queues[sockindx].Enqueue(ag);
            }
            if (busy)
                return;
            if (ag.SendBuffer != null)
            {
                sendargs[sockindx].SetBuffer(ag.SendBuffer, ag.Offset, ag.Count);
                try { sockets[sockindx].SendAsync(sendargs[sockindx]); }
                catch { }
                return;
            }
            sendargs[sockindx].SendPacketsElements = ag.SendElments;
            try { sockets[sockindx].SendPacketsAsync(sendargs[sockindx]); }
            catch { }
        }
        public void SendBuffer(int sockindx, byte[] sbuffer, int ost, int len)
        {
            if (len > recvbufferlen)
                return;
            SendsSegment(sockindx, new SendSegment(sbuffer, ost, len));
        }
        public void SendBuffer(List<int> sks, byte[] sbuffer, int ost, int len)
        {
            if (len > recvbufferlen)
                return;
            SendSegment ag = new SendSegment(sbuffer, ost, len);
            foreach (int sockindx in sks)
                SendsSegment(sockindx, ag);
        }
        public void SendPoolByorNot(int sockindx, bool usepool, params object[] objs)
        {
            SendSegment bf = xuliehua(objs, usepool);
            SendsSegment(sockindx, bf);
        }
        public void SendPoolByorNot(List<int> sks, bool usepool, params object[] objs)
        {
            SendSegment bf = xuliehua(objs, usepool);
            foreach (int sockindx in sks)
                SendsSegment(sockindx, bf);
        }
        public void Send(int sockindx, params object[] objs)
        {
            SendPoolByorNot(sockindx, true, objs);
        }
        public void Send(List<int> sks, params object[] objs)
        {
            SendPoolByorNot(sks, true, objs);
        }
        public void SendPackets(int sockindx, SendPacketsElement[] packets)
        {
            SendSegment sg = new SendSegment(packets);
            SendsSegment(sockindx, sg);
        }
        public void SendPackets(List<int> sks, SendPacketsElement[] packets)
        {
            SendSegment sg = new SendSegment(packets);
            foreach (int sockindx in sks)
                SendsSegment(sockindx, sg);
        }

#8


第三部分:

        unsafe public SendSegment xuliehua(object[] objs, bool usepool)
        {
            int len = 0;
            int* tps = stackalloc int[objs.Length];
            for (int i = 0; i < objs.Length; i++)
            {
                if (objs[i] == null)
                {
                    tps[i] = 5;
                    len += 4;
                    continue;
                }
                Type t = objs[i].GetType();
                if (t == typeof(int))
                {
                    tps[i] = 1;
                    len += 8;
                }
                else if (t == typeof(string))
                {
                    tps[i] = 2;
                    len += 8 + ((string)objs[i]).Length * 2;
                }
                else if (t == typeof(double))
                {
                    tps[i] = 3;
                    len += 12;
                }
                else if (t == typeof(DateTime))
                {
                    tps[i] = 4;
                    len += 8;
                }
                else if (t == typeof(bool))
                {
                    tps[i] = 6;
                    len += 8;
                }
                else
                {
                    tps[i] = 7;
                    len += 4;
                }
            }
            len += 4;
            if (len > recvbufferlen)
                throw new ArgumentException("发送长度超出缓冲区长度");
            byte[] bf;
            int bindx = 0;
            if (usepool)
            {
                bf = sendbuffer;
                bindx = getsendindex(len);
            }
            else
                bf = new byte[len];
            fixed (byte* p = bf) { *(int*)(p + bindx) = len; }
            bindx += 4;
            for (int i = 0; i < objs.Length; i++)
            {
                int tp = tps[i];
                if (tp <= 0 || tp > 7)
                {
                    throw new ArgumentException("序列化时参数类型超出规定范围");
                }
                fixed (byte* p = bf) { *(int*)(p + bindx) = tp; }
                bindx += 4;
                if (tp == 1)
                {
                    fixed (byte* p = bf) { *(int*)(p + bindx) = (int)objs[i]; }
                    bindx += 4;
                }
                else if (tp == 2)
                {
                    string s = (string)objs[i];
                    fixed (byte* p = bf) { *(int*)(p + bindx) = s.Length * 2; }
                    bindx += 4;
                    Encoding.Unicode.GetBytes(s, 0, s.Length, bf, bindx);
                    bindx += s.Length * 2;
                }
                else if (tp == 3)
                {
                    fixed (byte* p = bf) { *(double*)(p + bindx) = (double)objs[i]; }
                    bindx += 8;
                }
                else if (tp == 4)
                {
                    fixed (byte* p = bf) { *(uint*)(p + bindx) = Dttoint.toint((DateTime)objs[i]); }
                    bindx += 4;
                }
                else if (tp == 6)
                {
                    fixed (byte* p = bf) { *(bool*)(p + bindx) = (bool)objs[i]; }
                    bindx += 4;
                }
            }
            return new SendSegment(bf, bindx - len, len);
        }
        public object[] fanxulie(byte[] sbuffer, int startindex, int count)
        {
            int index = startindex;
            int endindex = startindex + count;
            int len = 0;
            while (index < endindex)
            {
                int tp = BitConverter.ToInt32(sbuffer, index);
                if (tp <= 0 || tp > 7)
                    throw new ArgumentException("反序列化时参数类型超出规定范围");
                index += 4;
                if (tp == 1 || tp == 4 || tp == 6)
                    index += 4;
                else if (tp == 2)
                {
                    int strlen = BitConverter.ToInt32(sbuffer, index);
                    index += 4;
                    if (strlen < 0 || strlen > startindex + count - index)
                        throw new ArgumentException("反序列化时字符串长度超出缓冲区");
                    index += strlen;
                }
                else if (tp == 3)
                    index += 8;
                len++;
            }
            object[] neirong = new object[len];
            index = startindex;
            len = 0;
            while (index < endindex)
            {
                int tp = BitConverter.ToInt32(sbuffer, index);
                index += 4;
                if (tp == 1)
                {
                    neirong[len] = BitConverter.ToInt32(sbuffer, index);
                    index += 4;
                }
                else if (tp == 2)
                {
                    int strlen = BitConverter.ToInt32(sbuffer, index);
                    index += 4;
                    neirong[len] = Encoding.Unicode.GetString(sbuffer, index, strlen);
                    index += strlen;
                }
                else if (tp == 3)
                {
                    neirong[len] = BitConverter.ToDouble(sbuffer, index);
                    index += 8;
                }
                else if (tp == 4)
                {
                    neirong[len] = Dttoint.todt(BitConverter.ToUInt32(sbuffer, index));
                    index += 4;
                }
                else if (tp == 6)
                {
                    neirong[len] = BitConverter.ToBoolean(sbuffer, index);
                    index += 4;
                }
                else
                    neirong[len] = null;
                len++;
            }
            return neirong;
        }
        int getsendindex(int len)
        {
            int index = (int)(((uint)Interlocked.Add(ref sendindex, len)) % sendbufferlen);
            if (index - len < 0)
                index = (int)(((uint)Interlocked.Add(ref sendindex, len)) % sendbufferlen);
            return index - len;
        }
    }
}

#9


引用 8 楼  的回复:
第三部分:

C# code


        unsafe public SendSegment xuliehua(object[] objs, bool usepool)
        {
            int len = 0;
            int* tps = stackalloc int[objs.Length];
            for……



我们做的是没有服务器的,(通过串口发送短信已经有现成的软件的了,现在我要做的是把这个软件新增一个通过GPRS发送文件的模块)
已经通过短信发送公网动态IP和端口号给GPRS模块了,模块也主动连接了软件,
可是怎么判断模块连接成功,成功之后再发送文件
是不是通过不断的循环读取网络流中的数据,如果读取到GPRS模块返回的成功标识就判断为连接成功

如果返回了成功,发送文件是不是用
socket.Send(Data);
或者
NetworkStream ns = new NetworkStream(socket);                     
StreamReader sr = new StreamReader(ns);                     
StreamWriter sw = new StreamWriter(ns);                     
sw.WriteLine(Data);                  
sw.Flush();  

Data是通过TCP协议组装的数据,我是通过这几天查资料理解的,也不知道是否正确,  请大侠指点指点            

#10


我现在的问题和你的一样,请问你的解决没有呀?

#11


那你看,你现在是从互联网上下载数据,不是上传数据。
你发送联网的at命令到gprs模块,如果gprs给你返回OK,那就表示连接成功。
你把你要下载的文件放到互联网上,从网上下载数据的代码,给你下了下,如果你也是C#的话,应该没有问题的了。
            try
            {
                System.Net.WebRequest wr = System.Net.WebRequest.Create("http://www.hongname.com/mxtp/z/good/zhangmy3/004.jpg");
                wr.Credentials = CredentialCache.DefaultCredentials;
                WebResponse wrp;
                wrp = wr.GetResponse();                
                System.IO.Stream stream = wrp.GetResponseStream();                 
                long count = wrp.ContentLength;
                int curr = 0;
                byte[] bdata = new byte[count];
                do
                {
                    curr += stream.Read(bdata, curr, bdata.Length - curr);
                } while (curr < count);
                System.IO.FileStream fs = new System.IO.FileStream("C:\\a.bin", System.IO.FileMode.OpenOrCreate);
                fs.Write(bdata, 0, bdata.Length);
                fs.Flush();
                stream.Close();
                fs.Close();
            }
            catch(Exception Ex) { }

#12


完全看不懂啊!

#13


引用 11 楼  的回复:
那你看,你现在是从互联网上下载数据,不是上传数据。
你发送联网的at命令到gprs模块,如果gprs给你返回OK,那就表示连接成功。
你把你要下载的文件放到互联网上,从网上下载数据的代码,给你下了下,如果你也是C#的话,应该没有问题的了。
  try
  {
  System.Net.WebRequest wr = System.Net.WebRequest.Create("http:/……



谢谢哦!好久没有来了,问题现在已经解决,之前用了和你的差不多的,不过后来又改了

#14


引用 10 楼  的回复:
我现在的问题和你的一样,请问你的解决没有呀?

不好意思哦!我好久没来了,我现在问题解决了,
我首先发一条带有本地IP地址和端口号的短信给GPRS短信模块,
GPRS短信模块在接收到我发出的短信主动连接
建立一个监听事件监听GPRS短信模块发出的信息,首先监听网络是否连接成功,如果成功就加载bin文件,分解再发送bin文件。