Ejemplo n.º 1
0
        /// <summary>
        /// Raises the APDU Received event
        /// </summary>
        /// <param name="apdu">The apdu that was received</param>
        //  Revision History
        //  MM/DD/YY who Version Issue# Description
        //  -------- --- ------- ------ ---------------------------------------
        //  05/21/13 RCG 2.80.32 N/A    Created

        private void OnAPDUReceived(xDLMSAPDU apdu)
        {
            if (APDUReceived != null && apdu != null)
            {
                APDUReceived(this, new APDUEventArguments(apdu));
            }
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Sends an APDU to the connected device
        /// </summary>
        /// <param name="apdu">The APDU to send</param>
        //  Revision History
        //  MM/DD/YY who Version Issue# Description
        //  -------- --- ------- ------ ---------------------------------------
        //  05/21/13 RCG 2.80.32 N/A    Created

        public void SendAPDU(xDLMSAPDU apdu)
        {
            if (IsOpen && apdu != null)
            {
                WPDU Wrapper = new WPDU(ClientPort, ServerPort, apdu.Data);

                m_Logger.WriteLine(Logger.LoggingLevel.Detailed, "Sending APDU. Type: " + EnumDescriptionRetriever.RetrieveDescription(apdu.Tag));

                Send(Wrapper.Data);
            }
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Parses the data for any APDU's
        /// </summary>
        //  Revision History
        //  MM/DD/YY who Version Issue# Description
        //  -------- --- ------- ------ ---------------------------------------
        //  02/04/12 RCG 2.70.63 N/A    Created

        private void ParseAPDUData()
        {
            try
            {
                lock (m_HighLevelDataBuffer)
                {
                    while (m_HighLevelDataBuffer.Count > 0)
                    {
                        // The first byte should be the APDU tag
                        xDLMSAPDU    NewAPDU         = xDLMSAPDU.Create((xDLMSTags)m_HighLevelDataBuffer[0]);
                        CipheredAPDU NewCipheredAPDU = NewAPDU as CipheredAPDU;

                        if (NewAPDU != null)
                        {
                            // Set up the security settings for a Ciphered APDU
                            if (NewCipheredAPDU != null)
                            {
                                if (CipheredAPDU.IsTagGlobalCipher(NewCipheredAPDU.Tag))
                                {
                                    NewCipheredAPDU.BlockCipherKey = GlobalEncryptionKey;
                                }
                                else if (CipheredAPDU.IsTagDedicatedCipher(NewCipheredAPDU.Tag))
                                {
                                    NewCipheredAPDU.BlockCipherKey = DedicatedEncryptionKey;
                                }

                                if (PendingDecryptAuthenticationKey != null)
                                {
                                    NewCipheredAPDU.AuthenticationKey = PendingDecryptAuthenticationKey;
                                }
                                else
                                {
                                    NewCipheredAPDU.AuthenticationKey = DecryptAuthenticationKey;
                                }

                                NewCipheredAPDU.ApTitle = ServerApTitle;

                                m_LastFrameCounterReceived = NewCipheredAPDU.FrameCounter;
                            }

                            // We found a valid APDU tag so we can try to parse it. We already checked the first byte so just use the rest
                            MemoryStream DataStream = new MemoryStream(m_HighLevelDataBuffer.ToArray());

                            NewAPDU.Parse(DataStream);

                            // Remove the data that has been parsed
                            m_HighLevelDataBuffer.RemoveRange(0, (int)DataStream.Position);

                            m_Logger.WriteLine(Logger.LoggingLevel.Detailed, "APDU Received. Type: " + EnumDescriptionRetriever.RetrieveDescription(NewAPDU.Tag));

                            if (NewCipheredAPDU != null)
                            {
                                xDLMSAPDU UncipheredAPDU = null;

                                if (PendingDecryptAuthenticationKey != null)
                                {
                                    // We are in the middle of a key exchange so we could get a message using either the pending key or
                                    // the previous key. We need to attempt the Pending key first
                                    try
                                    {
                                        UncipheredAPDU = NewCipheredAPDU.UncipheredAPDU;
                                    }
                                    catch (Exception)
                                    {
                                        m_Logger.WriteLine(Logger.LoggingLevel.Detailed, "Unciphering failed using the Pending Authentication Key. Using previous key.");
                                    }

                                    if (UncipheredAPDU == null)
                                    {
                                        // Try it with the previous key
                                        NewCipheredAPDU.AuthenticationKey = DecryptAuthenticationKey;
                                        UncipheredAPDU = NewCipheredAPDU.UncipheredAPDU;
                                    }
                                }
                                else
                                {
                                    UncipheredAPDU = NewCipheredAPDU.UncipheredAPDU;
                                }

                                // Send up the Unciphered APDU
                                OnAPDUReceived(UncipheredAPDU);
                            }
                            else
                            {
                                OnAPDUReceived(NewAPDU);
                            }
                        }
                        else
                        {
                            // The tag is not valid so lets get rid of the byte and move on
                            m_HighLevelDataBuffer.RemoveAt(0);
                        }
                    }
                }
            }
            catch (Exception e)
            {
                // This most likely means that we don't have all of the data yet for a specific message
                // so do nothing and hope the rest of the data comes in soon.
                m_Logger.WriteLine(Logger.LoggingLevel.Detailed, "Exception while parsing an APDU. Waiting for more data. Message: " + e.Message);
            }
        }
Ejemplo n.º 4
0
        /// <summary>
        /// Constructor
        /// </summary>
        /// <param name="apdu">The APDU for the event</param>
        //  Revision History
        //  MM/DD/YY who Version Issue# Description
        //  -------- --- ------- ------ ---------------------------------------
        //  05/21/13 RCG 2.80.32 N/A    Created

        public APDUEventArguments(xDLMSAPDU apdu)
            : base()
        {
            m_APDU = apdu;
        }