Better formatting FrontView lines.
Now cycling through each FrontView sensor every 2 seconds.
Fixing character conversion when sending VFD text.
Using special FrontView characters for Celsius and Farenheit.
2 using Microsoft.Win32.SafeHandles;
4 using System.Runtime.InteropServices;
5 using System.Threading;
7 using System.Diagnostics;
14 public enum EFileAccess : uint
20 AccessSystemSecurity = 0x1000000, // AccessSystemAcl access type
21 MaximumAllowed = 0x2000000, // MaximumAllowed access type
24 ReadControl = 0x20000,
27 Synchronize = 0x100000,
29 StandardRightsRequired = 0xF0000,
30 StandardRightsRead = ReadControl,
31 StandardRightsWrite = ReadControl,
32 StandardRightsExecute = ReadControl,
33 StandardRightsAll = 0x1F0000,
34 SpecificRightsAll = 0xFFFF,
36 FILE_READ_DATA = 0x0001, // file & pipe
37 FILE_LIST_DIRECTORY = 0x0001, // directory
38 FILE_WRITE_DATA = 0x0002, // file & pipe
39 FILE_ADD_FILE = 0x0002, // directory
40 FILE_APPEND_DATA = 0x0004, // file
41 FILE_ADD_SUBDIRECTORY = 0x0004, // directory
42 FILE_CREATE_PIPE_INSTANCE = 0x0004, // named pipe
43 FILE_READ_EA = 0x0008, // file & directory
44 FILE_WRITE_EA = 0x0010, // file & directory
45 FILE_EXECUTE = 0x0020, // file
46 FILE_TRAVERSE = 0x0020, // directory
47 FILE_DELETE_CHILD = 0x0040, // directory
48 FILE_READ_ATTRIBUTES = 0x0080, // all
49 FILE_WRITE_ATTRIBUTES = 0x0100, // all
55 GenericRead = 0x80000000,
56 GenericWrite = 0x40000000,
57 GenericExecute = 0x20000000,
58 GenericAll = 0x10000000,
60 SPECIFIC_RIGHTS_ALL = 0x00FFFF,
62 StandardRightsRequired |
69 FILE_READ_ATTRIBUTES |
76 FILE_WRITE_ATTRIBUTES |
81 FILE_GENERIC_EXECUTE =
82 StandardRightsExecute |
83 FILE_READ_ATTRIBUTES |
89 public enum EFileShare : uint
96 /// Enables subsequent open operations on an object to request read access.
97 /// Otherwise, other processes cannot open the object if they request read access.
98 /// If this flag is not specified, but the object has been opened for read access, the function fails.
102 /// Enables subsequent open operations on an object to request write access.
103 /// Otherwise, other processes cannot open the object if they request write access.
104 /// If this flag is not specified, but the object has been opened for write access, the function fails.
108 /// Enables subsequent open operations on an object to request delete access.
109 /// Otherwise, other processes cannot open the object if they request delete access.
110 /// If this flag is not specified, but the object has been opened for delete access, the function fails.
115 public enum ECreationDisposition : uint
118 /// Creates a new file. The function fails if a specified file exists.
122 /// Creates a new file, always.
123 /// If a file exists, the function overwrites the file, clears the existing attributes, combines the specified file attributes,
124 /// and flags with FILE_ATTRIBUTE_ARCHIVE, but does not set the security descriptor that the SECURITY_ATTRIBUTES structure specifies.
128 /// Opens a file. The function fails if the file does not exist.
132 /// Opens a file, always.
133 /// If a file does not exist, the function creates a file as if dwCreationDisposition is CREATE_NEW.
137 /// Opens a file and truncates it so that its size is 0 (zero) bytes. The function fails if the file does not exist.
138 /// The calling process must open the file with the GENERIC_WRITE access right.
144 public enum EFileAttributes : uint
147 Readonly = 0x00000001,
150 Directory = 0x00000010,
151 Archive = 0x00000020,
154 Temporary = 0x00000100,
155 SparseFile = 0x00000200,
156 ReparsePoint = 0x00000400,
157 Compressed = 0x00000800,
158 Offline = 0x00001000,
159 NotContentIndexed = 0x00002000,
160 Encrypted = 0x00004000,
161 Write_Through = 0x80000000,
162 Overlapped = 0x40000000,
163 NoBuffering = 0x20000000,
164 RandomAccess = 0x10000000,
165 SequentialScan = 0x08000000,
166 DeleteOnClose = 0x04000000,
167 BackupSemantics = 0x02000000,
168 PosixSemantics = 0x01000000,
169 OpenReparsePoint = 0x00200000,
170 OpenNoRecall = 0x00100000,
171 FirstPipeInstance = 0x00080000
174 [DllImport("kernel32.dll", SetLastError = true)]
175 public static extern SafeFileHandle CreateNamedPipe(
182 uint nDefaultTimeOut,
183 IntPtr lpSecurityAttributes);
185 [DllImport("kernel32.dll", SetLastError = true)]
186 public static extern int ConnectNamedPipe(
187 SafeFileHandle hNamedPipe,
188 IntPtr lpOverlapped);
190 [DllImport("kernel32.dll", SetLastError = true)]
191 public static extern int DisconnectNamedPipe(
192 SafeFileHandle hNamedPipe);
194 [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)]
195 public static extern SafeFileHandle CreateFile(
197 EFileAccess dwDesiredAccess,
198 EFileShare dwShareMode,
199 IntPtr lpSecurityAttributes,
200 ECreationDisposition dwCreationDisposition,
201 EFileAttributes dwFlagsAndAttributes,
202 IntPtr hTemplateFile);
204 //[DllImport("kernel32.dll", SetLastError = true)]
205 //static extern bool CloseHandle(IntPtr hHandle);
207 public const uint PIPE_ACCESS_DUPLEX = (0x00000003);
208 public const uint FILE_FLAG_OVERLAPPED = (0x40000000);
209 public const uint PIPE_ACCESS_OUTBOUND = (0x00000002);
210 public const uint PIPE_ACCESS_INBOUND = (0x00000001);
211 public const uint PIPE_TYPE_BYTE = (0x00000000);
212 public const uint PIPE_UNLIMITED_INSTANCES = 255;
217 public const int BUFFER_SIZE = 256;
220 public string iPipeNameOutbound;
221 SafeFileHandle iPipeOutbound;
222 public FileStream iStreamOutbound;
224 public string iPipeNameInbound;
225 Thread iThreadInbound;
226 SafeFileHandle iPipeInbound;
227 public FileStream iStreamInbound;
229 private bool iQuit = false;
232 public Server(string aPipeNameOutbound, string aPipeNameInbound)
234 iPipeNameOutbound = aPipeNameOutbound;
235 iPipeNameInbound = aPipeNameInbound;
239 * Start our services.
243 //Start inbound thread to receive messages
244 this.iThreadInbound = new Thread(new ThreadStart(ThreadInbound));
245 this.iThreadInbound.Start();
258 * Inbound thread is receiving messages from our client
260 private void ThreadInbound()
263 //Keep on trying to connect on our read pipe
264 while ((iPipeInbound == null || iPipeInbound.IsInvalid) && !iQuit)
266 Trace.WriteLine("Trying to connect to inbound pipe...");
267 iPipeInbound = CreateFile(iPipeNameInbound, EFileAccess.GenericRead, EFileShare.None, IntPtr.Zero, ECreationDisposition.OpenExisting, EFileAttributes.None, IntPtr.Zero);
268 System.Threading.Thread.Sleep(1000);
272 //Client now connected create our inbound stream
273 if (iPipeInbound!=null && !iPipeInbound.IsInvalid)
275 iStreamInbound = new FileStream(iPipeInbound, FileAccess.Read, BUFFER_SIZE, false);
276 if (iStreamInbound.CanRead)
278 Trace.WriteLine("Inbound stream ready!");
283 //Keep on trying to connect to our write pipe
284 while ((iPipeOutbound == null || iPipeOutbound.IsInvalid) && !iQuit)
286 Trace.WriteLine("Trying to connect to outbound pipe...");
287 iPipeOutbound = CreateFile(iPipeNameOutbound, EFileAccess.GenericWrite, EFileShare.None, IntPtr.Zero, ECreationDisposition.OpenExisting, EFileAttributes.None, IntPtr.Zero);
288 System.Threading.Thread.Sleep(1000);
292 //Client now connected create our stream
293 if (iPipeOutbound!=null && !iPipeOutbound.IsInvalid)
295 iStreamOutbound = new FileStream(iPipeOutbound, FileAccess.Write, BUFFER_SIZE, false);
297 if (iStreamOutbound.CanWrite)
299 Trace.WriteLine("Outbound stream ready!");
305 byte[] buffer = null;
306 ASCIIEncoding encoder = new ASCIIEncoding();
314 buffer = new byte[BUFFER_SIZE];
315 bytesRead = iStreamInbound.Read(buffer, 0, BUFFER_SIZE);
319 //read error has occurred
323 //client has disconnected
327 //fire message received event
328 //if (this.MessageReceived != null)
329 // this.MessageReceived(clientse, encoder.GetString(buffer, 0, bytesRead));
332 for (int i = 0; i < BUFFER_SIZE; i++)
334 //if (buffer[i].ToString("x2") != "cc")
344 byte[] Rc = new byte[ReadLength];
345 Buffer.BlockCopy(buffer, 0, Rc, 0, ReadLength);
347 Trace.WriteLine(encoder.GetString(Rc, 0, ReadLength));
348 Trace.WriteLine("Received " + ReadLength + " Bytes: " + encoder.GetString(Rc, 0, ReadLength));
356 if (iStreamInbound!=null) iStreamInbound.Close();
357 if (iPipeInbound != null) iPipeInbound.Close();
359 if (iStreamOutbound != null) iStreamOutbound.Close();
360 if (iPipeOutbound != null) iPipeOutbound.Close();
364 * Send a message to our client.
366 public void SendMessage(string message)
368 byte[] m8 = new byte[message.Length];
370 foreach (char c in message)
372 m8[i]=System.Convert.ToByte(c);
376 //ASCIIEncoding encoder = new ASCIIEncoding();
377 //byte[] messageBuffer = encoder.GetBytes(message);
379 if (iStreamOutbound != null && iStreamOutbound.CanWrite)
381 //iStreamOutbound.Write(messageBuffer, 0, messageBuffer.Length);
382 iStreamOutbound.Write(m8, 0, message.Length);
383 iStreamOutbound.Flush();