> 백엔드 개발 > C#.Net 튜토리얼 > C#에서 직렬 통신을 구현하는 방법

C#에서 직렬 통신을 구현하는 방법

大家讲道理
풀어 주다: 2016-11-10 10:20:59
원래의
1949명이 탐색했습니다.

일반적으로 C#에서 직렬 포트 통신을 구현하는 방법에는 네 가지가 있습니다.
첫째: MSCOMM 제어를 통한 가장 간단하고 편리한 방법입니다. 그러나 기능을 자유롭게 제어하는 ​​것은 어렵습니다. 동시에 이 제어는 시스템 자체에 포함되어 있지 않으므로 등록이 필요하므로 이 기사의 범위를 벗어납니다. 한 외국 네티즌이 작성한 튜토리얼인 http://www.devhood.com/tutorials/tutorial_details.aspx?tutorial_id=320을 방문해 보세요. 저자는 매우 열성적으로 이메일을 보냈고 그는 신속하게 응답했습니다.

두 번째: Microsoft는 .NET의 P/Invoke 호출 방법을 기반으로 구현된 새로운 직렬 포트 제어를 .NET에서 출시했습니다. 자세한 내용은 Microsoft 웹사이트(http://msdn.microsoft)를 참조하세요. 자세한 내용은 com/msdnmag/issues/02/10/NETSerialComm/default.aspx를 참조하세요.

셋째: 타사 컨트롤을 사용하지만 일반적으로 비용을 지불해야 하며 이는 실용적이지 않으며 고려되지 않습니다.

넷째: API를 사용하여 직렬 통신을 직접 작성합니다. 더 어렵지만 우리가 원하는 다양한 기능을 구현하는 것이 편리합니다

이 기사에서는 네 번째 방법을 사용하여 직렬 통신을 구현하지만 직접 작성하는 대신 외국 네티즌의 방법을 사용합니다. 기성품 패키지 좋은 클래스 라이브러리이지만 기능이 간단해서 충분합니다.

전체 터미널 문자 메시지 작업 중에 직렬 포트와 통신하는 데는 직렬 포트 열기, 쓰기, 읽기, 닫기의 네 가지 기능만 사용됩니다. 다음은 클래스 라이브러리에 있는 네 가지 함수에 대한 정의입니다.

직렬 포트 열기:

함수 프로토타입: public void Open()

참고: 포트 열기가 미리 설정되어 있습니다

예:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

using JustinIO;

    

static JustinIO.CommPort ss_port = new JustinIO.CommPort();

ss_port.PortNum = COM1; //端口号

ss_port.BaudRate = 19200; //串口通信波特率

ss_port.ByteSize = 8; //数据位

ss_port.Parity = 0; //奇偶校验

ss_port.StopBits = 1;//停止位

ss_port.ReadTimeout = 1000; //读超时

try

{

 if (ss_port.Opened)

 {

  ss_port.Close();

  ss_port.Open(); //打开串口

 }

 else

 {

  ss_port.Open();//打开串口

 }

 return true;

}

catch(Exception e) 

{

 MessageBox.Show("错误:" + e.Message);

 return false;

}

로그인 후 복사

직렬 포트 쓰기:

기능 프로토타입 : public void Write( byte[] WriteBytes)

WriteBytes는 통신을 위해 문자열을 바이트 배열로 변환해야 합니다.

예:

ss_port.Write(Encoding.ASCII.GetBytes("AT+CGMIr")) //휴대폰 브랜드 가져오기

직렬 포트 읽기:

함수 프로토타입: public byte[] Read(int NumBytes)

NumBytes 캐시 번호 읽기 , 읽기는 바이트 배열이므로 실제 응용 프로그램에서는 문자 변환이 필요합니다

예:

문자열 응답 = Encoding.ASCII. GetString(ss_port .Read(128)); //128바이트 버퍼 읽기

직렬 포트 닫기:

함수 프로토타입: ss_port. Close( )

예:

ss_port.Close()

길이로 인해 직렬 포트 통신은 광범위한 주제를 다루고 있으며 여기서는 이에 대해서만 다루겠습니다.

이미 SMS 단말기에 필요한 다양한 원시 기술을 이해했으며 이제 우리의 기술을 시험해 볼 시간입니다.

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

122

123

124

125

126

127

128

129

130

131

132

133

134

135

136

137

138

139

140

141

142

143

144

145

146

147

148

149

150

151

152

153

154

155

156

157

158

159

160

161

162

163

164

165

166

167

168

169

170

171

172

173

174

175

176

177

178

179

180

181

182

183

184

185

186

187

188

189

190

191

192

193

194

195

196

197

198

199

200

201

202

203

204

205

206

207

208

209

210

211

212

213

214

215

216

217

218

219

220

221

222

223

224

225

226

227

228

229

230

231

232

233

234

using System;

using System.Runtime.InteropServices;

    

namespace BusApp

{

 /// <summary>

 /// 

 /// </summary>

 public class mycom

 {

  public mycom()

  {

   // 

   // TODO: 在此处添加构造函数逻辑

   //

  }

  public int PortNum; //1,2,3,4

  public int BaudRate; //1200,2400,4800,9600

  public byte ByteSize; //8 bits

  public byte Parity; // 0-4=no,odd,even,mark,space 

  public byte StopBits; // 0,1,2 = 1, 1.5, 2 

  public int ReadTimeout; //10

      

  //comm port win32 file handle

  private int hComm = -1;

      

  public bool Opened = false;

       

  //win32 api constants

  private const uint GENERIC_READ = 0x80000000;

  private const uint GENERIC_WRITE = 0x40000000;

  private const int OPEN_EXISTING = 3;  

  private const int INVALID_HANDLE_VALUE = -1;

      

  [StructLayout(LayoutKind.Sequential)]

   private struct DCB 

  {

   //taken from c struct in platform sdk 

   public int DCBlength;           // sizeof(DCB) 

   public int BaudRate;            // current baud rate 

   public int fBinary;          // binary mode, no EOF check 

   public int fParity;          // enable parity checking 

   public int fOutxCtsFlow;      // CTS output flow control 

   public int fOutxDsrFlow;      // DSR output flow control 

   public int fDtrControl;       // DTR flow control type 

   public int fDsrSensitivity;   // DSR sensitivity 

   public int fTXContinueOnXoff; // XOFF continues Tx 

   public int fOutX;          // XON/XOFF out flow control 

   public int fInX;           // XON/XOFF in flow control 

   public int fErrorChar;     // enable error replacement 

   public int fNull;          // enable null stripping 

   public int fRtsControl;     // RTS flow control 

   public int fAbortOnError;   // abort on error 

   public int fDummy2;        // reserved 

   public ushort wReserved;          // not currently used 

   public ushort XonLim;             // transmit XON threshold 

   public ushort XoffLim;            // transmit XOFF threshold 

   public byte ByteSize;           // number of bits/byte, 4-8 

   public byte Parity;             // 0-4=no,odd,even,mark,space 

   public byte StopBits;           // 0,1,2 = 1, 1.5, 2 

   public char XonChar;            // Tx and Rx XON character 

   public char XoffChar;           // Tx and Rx XOFF character 

   public char ErrorChar;          // error replacement character 

   public char EofChar;            // end of input character 

   public char EvtChar;            // received event character 

   public ushort wReserved1;         // reserved; do not use 

  }

    

  [StructLayout(LayoutKind.Sequential)]

   private struct COMMTIMEOUTS 

  {  

   public int ReadIntervalTimeout; 

   public int ReadTotalTimeoutMultiplier; 

   public int ReadTotalTimeoutConstant; 

   public int WriteTotalTimeoutMultiplier; 

   public int WriteTotalTimeoutConstant; 

  

    

  [StructLayout(LayoutKind.Sequential)] 

   private struct OVERLAPPED 

  

   public int  Internal; 

   public int  InternalHigh; 

   public int  Offset; 

   public int  OffsetHigh; 

   public int hEvent; 

  }  

      

  [DllImport("kernel32.dll")]

  private static extern int CreateFile(

   string lpFileName,                         // file name

   uint dwDesiredAccess,                      // access mode

   int dwShareMode,                          // share mode

   int lpSecurityAttributes, // SD

   int dwCreationDisposition,                // how to create

   int dwFlagsAndAttributes,                 // file attributes

   int hTemplateFile                        // handle to template file

   );

  [DllImport("kernel32.dll")]

  private static extern bool GetCommState(

   int hFile,  // handle to communications device

   ref DCB lpDCB    // device-control block

   ); 

  [DllImport("kernel32.dll")]

  private static extern bool BuildCommDCB(

   string lpDef,  // device-control string

   ref DCB lpDCB     // device-control block

   );

  [DllImport("kernel32.dll")]

  private static extern bool SetCommState(

   int hFile,  // handle to communications device

   ref DCB lpDCB    // device-control block

   );

  [DllImport("kernel32.dll")]

  private static extern bool GetCommTimeouts(

   int hFile,                  // handle to comm device

   ref COMMTIMEOUTS lpCommTimeouts  // time-out values

   ); 

  [DllImport("kernel32.dll")] 

  private static extern bool SetCommTimeouts(

   int hFile,                  // handle to comm device

   ref COMMTIMEOUTS lpCommTimeouts  // time-out values

   );

  [DllImport("kernel32.dll")]

  private static extern bool ReadFile(

   int hFile,                // handle to file

   byte[] lpBuffer,             // data buffer

   int nNumberOfBytesToRead,  // number of bytes to read

   ref int lpNumberOfBytesRead, // number of bytes read

   ref OVERLAPPED lpOverlapped    // overlapped buffer

   );

  [DllImport("kernel32.dll")] 

  private static extern bool WriteFile(

   int hFile,                    // handle to file

   byte[] lpBuffer,                // data buffer

   int nNumberOfBytesToWrite,     // number of bytes to write

   ref int lpNumberOfBytesWritten,  // number of bytes written

   ref OVERLAPPED lpOverlapped        // overlapped buffer

   );

  [DllImport("kernel32.dll")]

  private static extern bool CloseHandle(

   int hObject   // handle to object

   );

      

  public void Open() 

  {

       

   DCB dcbCommPort = new DCB();

   COMMTIMEOUTS ctoCommPort = new COMMTIMEOUTS(); 

       

       

   // OPEN THE COMM PORT.

    

        

   hComm = CreateFile("COM" + PortNum ,GENERIC_READ | GENERIC_WRITE,0, 0,OPEN_EXISTING,0,0);

      

   // IF THE PORT CANNOT BE OPENED, BAIL OUT.

   if(hComm == INVALID_HANDLE_VALUE) 

   {

    throw(new ApplicationException("Comm Port Can Not Be Opened"));

   }

      

   // SET THE COMM TIMEOUTS.

       

   GetCommTimeouts(hComm,ref ctoCommPort);

   ctoCommPort.ReadTotalTimeoutConstant = ReadTimeout;

   ctoCommPort.ReadTotalTimeoutMultiplier = 0;

   ctoCommPort.WriteTotalTimeoutMultiplier = 0;

   ctoCommPort.WriteTotalTimeoutConstant = 0;  

   SetCommTimeouts(hComm,ref ctoCommPort);

      

   // SET BAUD RATE, PARITY, WORD SIZE, AND STOP BITS.

   // THERE ARE OTHER WAYS OF DOING SETTING THESE BUT THIS IS THE EASIEST.

   // IF YOU WANT TO LATER ADD CODE FOR OTHER BAUD RATES, REMEMBER

   // THAT THE ARGUMENT FOR BuildCommDCB MUST BE A POINTER TO A STRING.

   // ALSO NOTE THAT BuildCommDCB() DEFAULTS TO NO HANDSHAKING.

      

   dcbCommPort.DCBlength = Marshal.SizeOf(dcbCommPort);

   GetCommState(hComm, ref dcbCommPort);

   dcbCommPort.BaudRate=BaudRate;

   dcbCommPort.Parity=Parity;

   dcbCommPort.ByteSize=ByteSize;

   dcbCommPort.StopBits=StopBits;

   SetCommState(hComm, ref dcbCommPort);

        

   Opened = true;

        

  }

      

  public void Close() 

  {

   if (hComm!=INVALID_HANDLE_VALUE) 

   {

    CloseHandle(hComm);

                Opened=false;

   }

  }

      

  public byte[] Read(int NumBytes) 

  {

   byte[] BufBytes;

   byte[] OutBytes;

   BufBytes = new byte[NumBytes];

   if (hComm!=INVALID_HANDLE_VALUE) 

   {

    OVERLAPPED ovlCommPort = new OVERLAPPED();

    int BytesRead=0;

    ReadFile(hComm,BufBytes,NumBytes,ref BytesRead,ref ovlCommPort);

    OutBytes = new byte[BytesRead];

    Array.Copy(BufBytes,OutBytes,BytesRead);

   

   else 

   {

    throw(new ApplicationException("Comm Port Not Open"));

   }

   return OutBytes;

  }

      

  public int Write(byte[] WriteBytes) 

  {

   int BytesWritten = 0;

   if (hComm!=INVALID_HANDLE_VALUE) 

   {

    OVERLAPPED ovlCommPort = new OVERLAPPED();

    WriteFile(hComm,WriteBytes,WriteBytes.Length,ref BytesWritten,ref ovlCommPort);

   }

   else 

   {

    throw(new ApplicationException("Comm Port Not Open"));

   }  

   return BytesWritten;

  }

 }

}

로그인 후 복사


원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
최신 이슈
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿