/// <summary> /// Send a Hart Request and handle Delay Retry. /// If no more dr retry, it sends nerwork HART device a flush Dr cmd. /// </summary> /// <param name="Request">byte[] a request byte array</param> /// <param name="ByteCount">ushort request array byte count</param> /// <param name="Timeout">int request timeout in ms</param> /// <returns><see cref="HartIPResponse"/></returns> public HartIPResponse SendHartRequest(byte[] Request, ushort ByteCount, int Timeout = HARTIPConnect.USE_SOCKET_TIMEOUT_DEFAULT) { HartIPRequest Req = HartIPRequest.HartCommandRequest(m_HartIPConn.TransactionId, Request, ByteCount, Timeout); return(SendHartRequest(Req)); }
/// <summary> /// Build a Hart-IP request /// </summary> /// <param name="Command">byte[] request Command byte array /// <para>Array should include the frame, device address, command, byte count, /// data, and checksum bytes.</para>para</param> /// <param name="usByteCount">ushort the specified Command array byte count</param> /// <returns><see cref="HartIPRequest"/></returns> public HartIPRequest BuildHartRequest(byte[] Command, ushort usByteCount) { return(HartIPRequest.HartCommandRequest(TransactionId, Command, usByteCount)); }
/// <summary> /// Build a HartIP Request using the specified request command, request message, /// device type, and device id. It will have frame, device address, command, byte count, /// data, and checksum bytes in the returned HartIPRequest.Command. /// </summary> /// <param name="usReqCmd">ushort Request command</param> /// <param name="ReqMsg">String Request message in Hex string</param> /// <param name="usDeviceType">ushort Device Type</param> /// <param name="nDeviceId">uint Device ID</param> /// <returns><see cref="HartIPRequest"/></returns> public HartIPRequest BuildHartIPRequest(ushort usReqCmd, String ReqMsg, ushort usDeviceType, uint nDeviceId) { String Msg; HartIPRequest HRequest = null; int nDataLen = 0; if (m_HartIPConn == null) { throw new Exception("Call Connect to initialize the network connection first."); } if ((uint)(usReqCmd) > 65536) { Msg = "Invalid HARTIP Request Command."; throw new ArgumentException(Msg); } if (!String.IsNullOrEmpty(ReqMsg)) { ReqMsg = ReqMsg.Replace(" ", ""); nDataLen = ReqMsg.Length; if ((nDataLen > 0) && (nDataLen % 2) != 0) { Msg = "Multiple contiguous bytes must define an even number of hex digits."; throw new ArgumentException(Msg); } } // Check if it is extended command bool bExtendedCmd = (usReqCmd > HARTIPMessage.MAX_SINGLE_BYTE_CMD) ? true : false; byte cCmd = (byte)(bExtendedCmd ? HARTIPMessage.CMD_EXTENDED_CMD : usReqCmd); byte cbyteCount = 9; byte cDataByteCount = 0; int nIndex = 0; int nSubCmdByteCountIndex; // Request bytes byte[] Data = new byte[HARTIPMessage.MAX_REQUEST_MSG_LEN]; Array.Clear(Data, 0, Data.Length); if (nDataLen > 0) { cbyteCount += (byte)(nDataLen / 2); cDataByteCount = (byte)(nDataLen / 2); } // form a request Data[nIndex++] = 0x82; // long frame Data[nIndex++] = (byte)(((usDeviceType >> 8) & 0x3F) | 0x80); Data[nIndex++] = (byte)(usDeviceType & 0x0ff); Data[nIndex++] = (byte)((nDeviceId >> 16) & 0x0ff); Data[nIndex++] = (byte)((nDeviceId >> 8) & 0x0ff); Data[nIndex++] = (byte)(nDeviceId & 0x0ff); Data[nIndex++] = cCmd; // cmd nSubCmdByteCountIndex = nIndex; // skip the byte count nIndex += 1; // if it is extended cmd, put the cmd two bytes in data field first if (bExtendedCmd) { Data[nIndex++] = (byte)((usReqCmd >> 8) & 0x0ff); Data[nIndex++] = (byte)(usReqCmd & 0x0ff); cbyteCount += 2; cDataByteCount += 2; } // set the data byte count value Data[nSubCmdByteCountIndex] = cDataByteCount; int n = 0; byte cY, cW; while (n < nDataLen) { if (HartUtil.HexCharToNibble(ReqMsg[n], out cY)) { if (HartUtil.HexCharToNibble(ReqMsg[n + 1], out cW)) { Data[nIndex++] = (byte)(cY * 16 + cW); n += 2; } else { Msg = String.Format("The character: '{0}' is not allowed in the request data byte value.", ReqMsg[n + 1]); throw new ArgumentException(Msg); } } else { Msg = String.Format("The character: '{0}' is not allowed in the request data byte value.", ReqMsg[n]); throw new ArgumentException(Msg); } } // tunnel messages to attached devices if (RootDevice.DeviceType != usDeviceType && RootDevice.DeviceId != nDeviceId && RootDevice.IsBridgeDevice) { // message is routed into an attached device // wrap the message with command 77 to tunnel to attached device byte[] Data77 = new byte[HARTIPMessage.MAX_REQUEST_MSG_LEN]; Array.Clear(Data77, 0, Data.Length); // command 77 request data HartDevice dev = FindDevice(nDeviceId); Data77[0] = dev.IOCard; Data77[1] = dev.Channel; Data77[2] = 5; // transmit preamble count Array.Copy(Data, 0, Data77, 3, nIndex); nIndex += 3; // send the command 77 to the root device (a gateway or IO) string hex = BitConverter.ToString(Data77).Replace("-", string.Empty); hex = hex.Substring(0, nIndex * 2); return(BuildHartIPRequest(77, hex, RootDevice.DeviceType, RootDevice.DeviceId)); } // Get check sum byte and send the request Data[nIndex] = HartUtil.GetCheckSum(Data, (byte)(cbyteCount - 1)); HRequest = HartIPRequest.HartCommandRequest(m_HartIPConn.TransactionId, Data, cbyteCount); return(HRequest); }