This is the latest working repository used in our demo video for the Maxim to display temperature readings on Bluetooth

Dependencies:   USBDevice

Committer:
darienf
Date:
Sun May 02 23:09:04 2021 +0000
Revision:
5:bc128a16232f
Parent:
3:36de8b9e4b1a
This is the program that was last used, that has the working temperature and some comments

Who changed what in which revision?

UserRevisionLine numberNew contents of line
darienf 3:36de8b9e4b1a 1 // Copyright 2010-2014 Zach Saw
darienf 3:36de8b9e4b1a 2 //
darienf 3:36de8b9e4b1a 3 // Licensed under the Apache License, Version 2.0 (the "License");
darienf 3:36de8b9e4b1a 4 // you may not use this file except in compliance with the License.
darienf 3:36de8b9e4b1a 5 // You may obtain a copy of the License at
darienf 3:36de8b9e4b1a 6 //
darienf 3:36de8b9e4b1a 7 // http://www.apache.org/licenses/LICENSE-2.0
darienf 3:36de8b9e4b1a 8 //
darienf 3:36de8b9e4b1a 9 // Unless required by applicable law or agreed to in writing, software
darienf 3:36de8b9e4b1a 10 // distributed under the License is distributed on an "AS IS" BASIS,
darienf 3:36de8b9e4b1a 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
darienf 3:36de8b9e4b1a 12 // See the License for the specific language governing permissions and
darienf 3:36de8b9e4b1a 13 // limitations under the License.
darienf 3:36de8b9e4b1a 14
darienf 3:36de8b9e4b1a 15 using System;
darienf 3:36de8b9e4b1a 16 using System.IO;
darienf 3:36de8b9e4b1a 17 using System.IO.Ports;
darienf 3:36de8b9e4b1a 18 using System.Runtime.InteropServices;
darienf 3:36de8b9e4b1a 19 using System.Text;
darienf 3:36de8b9e4b1a 20 using Microsoft.Win32.SafeHandles;
darienf 3:36de8b9e4b1a 21
darienf 3:36de8b9e4b1a 22 namespace SerialPortTester
darienf 3:36de8b9e4b1a 23 {
darienf 3:36de8b9e4b1a 24 public class SerialPortFixer : IDisposable
darienf 3:36de8b9e4b1a 25 {
darienf 3:36de8b9e4b1a 26 public static void Execute(string portName)
darienf 3:36de8b9e4b1a 27 {
darienf 3:36de8b9e4b1a 28 using (new SerialPortFixer(portName))
darienf 3:36de8b9e4b1a 29 {
darienf 3:36de8b9e4b1a 30 }
darienf 3:36de8b9e4b1a 31 }
darienf 3:36de8b9e4b1a 32 #region IDisposable Members
darienf 3:36de8b9e4b1a 33
darienf 3:36de8b9e4b1a 34 public void Dispose()
darienf 3:36de8b9e4b1a 35 {
darienf 3:36de8b9e4b1a 36 if (m_Handle != null)
darienf 3:36de8b9e4b1a 37 {
darienf 3:36de8b9e4b1a 38 m_Handle.Close();
darienf 3:36de8b9e4b1a 39 m_Handle = null;
darienf 3:36de8b9e4b1a 40 }
darienf 3:36de8b9e4b1a 41 }
darienf 3:36de8b9e4b1a 42
darienf 3:36de8b9e4b1a 43 #endregion
darienf 3:36de8b9e4b1a 44
darienf 3:36de8b9e4b1a 45 #region Implementation
darienf 3:36de8b9e4b1a 46
darienf 3:36de8b9e4b1a 47 private const int DcbFlagAbortOnError = 14;
darienf 3:36de8b9e4b1a 48 private const int CommStateRetries = 10;
darienf 3:36de8b9e4b1a 49 private SafeFileHandle m_Handle;
darienf 3:36de8b9e4b1a 50
darienf 3:36de8b9e4b1a 51 private SerialPortFixer(string portName)
darienf 3:36de8b9e4b1a 52 {
darienf 3:36de8b9e4b1a 53 const int dwFlagsAndAttributes = 0x40000000;
darienf 3:36de8b9e4b1a 54 const int dwAccess = unchecked((int) 0xC0000000);
darienf 3:36de8b9e4b1a 55
darienf 3:36de8b9e4b1a 56 if ((portName == null) || !portName.StartsWith("COM", StringComparison.OrdinalIgnoreCase))
darienf 3:36de8b9e4b1a 57 {
darienf 3:36de8b9e4b1a 58 throw new ArgumentException("Invalid Serial Port", "portName");
darienf 3:36de8b9e4b1a 59 }
darienf 3:36de8b9e4b1a 60 SafeFileHandle hFile = CreateFile(@"\\.\" + portName, dwAccess, 0, IntPtr.Zero, 3, dwFlagsAndAttributes,
darienf 3:36de8b9e4b1a 61 IntPtr.Zero);
darienf 3:36de8b9e4b1a 62 if (hFile.IsInvalid)
darienf 3:36de8b9e4b1a 63 {
darienf 3:36de8b9e4b1a 64 WinIoError();
darienf 3:36de8b9e4b1a 65 }
darienf 3:36de8b9e4b1a 66 try
darienf 3:36de8b9e4b1a 67 {
darienf 3:36de8b9e4b1a 68 int fileType = GetFileType(hFile);
darienf 3:36de8b9e4b1a 69 if ((fileType != 2) && (fileType != 0))
darienf 3:36de8b9e4b1a 70 {
darienf 3:36de8b9e4b1a 71 throw new ArgumentException("Invalid Serial Port", "portName");
darienf 3:36de8b9e4b1a 72 }
darienf 3:36de8b9e4b1a 73 m_Handle = hFile;
darienf 3:36de8b9e4b1a 74 InitializeDcb();
darienf 3:36de8b9e4b1a 75 }
darienf 3:36de8b9e4b1a 76 catch
darienf 3:36de8b9e4b1a 77 {
darienf 3:36de8b9e4b1a 78 hFile.Close();
darienf 3:36de8b9e4b1a 79 m_Handle = null;
darienf 3:36de8b9e4b1a 80 throw;
darienf 3:36de8b9e4b1a 81 }
darienf 3:36de8b9e4b1a 82 }
darienf 3:36de8b9e4b1a 83
darienf 3:36de8b9e4b1a 84 [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
darienf 3:36de8b9e4b1a 85 private static extern int FormatMessage(int dwFlags, HandleRef lpSource, int dwMessageId, int dwLanguageId,
darienf 3:36de8b9e4b1a 86 StringBuilder lpBuffer, int nSize, IntPtr arguments);
darienf 3:36de8b9e4b1a 87
darienf 3:36de8b9e4b1a 88 [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
darienf 3:36de8b9e4b1a 89 private static extern bool GetCommState(SafeFileHandle hFile, ref Dcb lpDcb);
darienf 3:36de8b9e4b1a 90
darienf 3:36de8b9e4b1a 91 [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
darienf 3:36de8b9e4b1a 92 private static extern bool SetCommState(SafeFileHandle hFile, ref Dcb lpDcb);
darienf 3:36de8b9e4b1a 93
darienf 3:36de8b9e4b1a 94 [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
darienf 3:36de8b9e4b1a 95 private static extern bool ClearCommError(SafeFileHandle hFile, ref int lpErrors, ref Comstat lpStat);
darienf 3:36de8b9e4b1a 96
darienf 3:36de8b9e4b1a 97 [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
darienf 3:36de8b9e4b1a 98 private static extern SafeFileHandle CreateFile(string lpFileName, int dwDesiredAccess, int dwShareMode,
darienf 3:36de8b9e4b1a 99 IntPtr securityAttrs, int dwCreationDisposition,
darienf 3:36de8b9e4b1a 100 int dwFlagsAndAttributes, IntPtr hTemplateFile);
darienf 3:36de8b9e4b1a 101
darienf 3:36de8b9e4b1a 102 [DllImport("kernel32.dll", SetLastError = true)]
darienf 3:36de8b9e4b1a 103 private static extern int GetFileType(SafeFileHandle hFile);
darienf 3:36de8b9e4b1a 104
darienf 3:36de8b9e4b1a 105 private void InitializeDcb()
darienf 3:36de8b9e4b1a 106 {
darienf 3:36de8b9e4b1a 107 Dcb dcb = new Dcb();
darienf 3:36de8b9e4b1a 108 GetCommStateNative(ref dcb);
darienf 3:36de8b9e4b1a 109 dcb.Flags &= ~(1u << DcbFlagAbortOnError);
darienf 3:36de8b9e4b1a 110 SetCommStateNative(ref dcb);
darienf 3:36de8b9e4b1a 111 }
darienf 3:36de8b9e4b1a 112
darienf 3:36de8b9e4b1a 113 private static string GetMessage(int errorCode)
darienf 3:36de8b9e4b1a 114 {
darienf 3:36de8b9e4b1a 115 StringBuilder lpBuffer = new StringBuilder(0x200);
darienf 3:36de8b9e4b1a 116 if (
darienf 3:36de8b9e4b1a 117 FormatMessage(0x3200, new HandleRef(null, IntPtr.Zero), errorCode, 0, lpBuffer, lpBuffer.Capacity,
darienf 3:36de8b9e4b1a 118 IntPtr.Zero) != 0)
darienf 3:36de8b9e4b1a 119 {
darienf 3:36de8b9e4b1a 120 return lpBuffer.ToString();
darienf 3:36de8b9e4b1a 121 }
darienf 3:36de8b9e4b1a 122 return "Unknown Error";
darienf 3:36de8b9e4b1a 123 }
darienf 3:36de8b9e4b1a 124
darienf 3:36de8b9e4b1a 125 private static int MakeHrFromErrorCode(int errorCode)
darienf 3:36de8b9e4b1a 126 {
darienf 3:36de8b9e4b1a 127 return (int) (0x80070000 | (uint) errorCode);
darienf 3:36de8b9e4b1a 128 }
darienf 3:36de8b9e4b1a 129
darienf 3:36de8b9e4b1a 130 private static void WinIoError()
darienf 3:36de8b9e4b1a 131 {
darienf 3:36de8b9e4b1a 132 int errorCode = Marshal.GetLastWin32Error();
darienf 3:36de8b9e4b1a 133 throw new IOException(GetMessage(errorCode), MakeHrFromErrorCode(errorCode));
darienf 3:36de8b9e4b1a 134 }
darienf 3:36de8b9e4b1a 135
darienf 3:36de8b9e4b1a 136 private void GetCommStateNative(ref Dcb lpDcb)
darienf 3:36de8b9e4b1a 137 {
darienf 3:36de8b9e4b1a 138 int commErrors = 0;
darienf 3:36de8b9e4b1a 139 Comstat comStat = new Comstat();
darienf 3:36de8b9e4b1a 140
darienf 3:36de8b9e4b1a 141 for (int i = 0; i < CommStateRetries; i++)
darienf 3:36de8b9e4b1a 142 {
darienf 3:36de8b9e4b1a 143 if (!ClearCommError(m_Handle, ref commErrors, ref comStat))
darienf 3:36de8b9e4b1a 144 {
darienf 3:36de8b9e4b1a 145 WinIoError();
darienf 3:36de8b9e4b1a 146 }
darienf 3:36de8b9e4b1a 147 if (GetCommState(m_Handle, ref lpDcb))
darienf 3:36de8b9e4b1a 148 {
darienf 3:36de8b9e4b1a 149 break;
darienf 3:36de8b9e4b1a 150 }
darienf 3:36de8b9e4b1a 151 if (i == CommStateRetries - 1)
darienf 3:36de8b9e4b1a 152 {
darienf 3:36de8b9e4b1a 153 WinIoError();
darienf 3:36de8b9e4b1a 154 }
darienf 3:36de8b9e4b1a 155 }
darienf 3:36de8b9e4b1a 156 }
darienf 3:36de8b9e4b1a 157
darienf 3:36de8b9e4b1a 158 private void SetCommStateNative(ref Dcb lpDcb)
darienf 3:36de8b9e4b1a 159 {
darienf 3:36de8b9e4b1a 160 int commErrors = 0;
darienf 3:36de8b9e4b1a 161 Comstat comStat = new Comstat();
darienf 3:36de8b9e4b1a 162
darienf 3:36de8b9e4b1a 163 for (int i = 0; i < CommStateRetries; i++)
darienf 3:36de8b9e4b1a 164 {
darienf 3:36de8b9e4b1a 165 if (!ClearCommError(m_Handle, ref commErrors, ref comStat))
darienf 3:36de8b9e4b1a 166 {
darienf 3:36de8b9e4b1a 167 WinIoError();
darienf 3:36de8b9e4b1a 168 }
darienf 3:36de8b9e4b1a 169 if (SetCommState(m_Handle, ref lpDcb))
darienf 3:36de8b9e4b1a 170 {
darienf 3:36de8b9e4b1a 171 break;
darienf 3:36de8b9e4b1a 172 }
darienf 3:36de8b9e4b1a 173 if (i == CommStateRetries - 1)
darienf 3:36de8b9e4b1a 174 {
darienf 3:36de8b9e4b1a 175 WinIoError();
darienf 3:36de8b9e4b1a 176 }
darienf 3:36de8b9e4b1a 177 }
darienf 3:36de8b9e4b1a 178 }
darienf 3:36de8b9e4b1a 179
darienf 3:36de8b9e4b1a 180 #region Nested type: COMSTAT
darienf 3:36de8b9e4b1a 181
darienf 3:36de8b9e4b1a 182 [StructLayout(LayoutKind.Sequential)]
darienf 3:36de8b9e4b1a 183 private struct Comstat
darienf 3:36de8b9e4b1a 184 {
darienf 3:36de8b9e4b1a 185 public readonly uint Flags;
darienf 3:36de8b9e4b1a 186 public readonly uint cbInQue;
darienf 3:36de8b9e4b1a 187 public readonly uint cbOutQue;
darienf 3:36de8b9e4b1a 188 }
darienf 3:36de8b9e4b1a 189
darienf 3:36de8b9e4b1a 190 #endregion
darienf 3:36de8b9e4b1a 191
darienf 3:36de8b9e4b1a 192 #region Nested type: DCB
darienf 3:36de8b9e4b1a 193
darienf 3:36de8b9e4b1a 194 [StructLayout(LayoutKind.Sequential)]
darienf 3:36de8b9e4b1a 195 private struct Dcb
darienf 3:36de8b9e4b1a 196 {
darienf 3:36de8b9e4b1a 197 public readonly uint DCBlength;
darienf 3:36de8b9e4b1a 198 public readonly uint BaudRate;
darienf 3:36de8b9e4b1a 199 public uint Flags;
darienf 3:36de8b9e4b1a 200 public readonly ushort wReserved;
darienf 3:36de8b9e4b1a 201 public readonly ushort XonLim;
darienf 3:36de8b9e4b1a 202 public readonly ushort XoffLim;
darienf 3:36de8b9e4b1a 203 public readonly byte ByteSize;
darienf 3:36de8b9e4b1a 204 public readonly byte Parity;
darienf 3:36de8b9e4b1a 205 public readonly byte StopBits;
darienf 3:36de8b9e4b1a 206 public readonly byte XonChar;
darienf 3:36de8b9e4b1a 207 public readonly byte XoffChar;
darienf 3:36de8b9e4b1a 208 public readonly byte ErrorChar;
darienf 3:36de8b9e4b1a 209 public readonly byte EofChar;
darienf 3:36de8b9e4b1a 210 public readonly byte EvtChar;
darienf 3:36de8b9e4b1a 211 public readonly ushort wReserved1;
darienf 3:36de8b9e4b1a 212 }
darienf 3:36de8b9e4b1a 213
darienf 3:36de8b9e4b1a 214 #endregion
darienf 3:36de8b9e4b1a 215
darienf 3:36de8b9e4b1a 216 #endregion
darienf 3:36de8b9e4b1a 217 }
darienf 3:36de8b9e4b1a 218
darienf 3:36de8b9e4b1a 219 internal class Program
darienf 3:36de8b9e4b1a 220 {
darienf 3:36de8b9e4b1a 221 private static void Main(string[] args)
darienf 3:36de8b9e4b1a 222 {
darienf 3:36de8b9e4b1a 223 SerialPortFixer.Execute("COM1");
darienf 3:36de8b9e4b1a 224 using (SerialPort port = new SerialPort("COM1"))
darienf 3:36de8b9e4b1a 225 {
darienf 3:36de8b9e4b1a 226 port.Write("test");
darienf 3:36de8b9e4b1a 227 }
darienf 3:36de8b9e4b1a 228 }
darienf 3:36de8b9e4b1a 229 }
darienf 3:36de8b9e4b1a 230 }